xref: /AOO41X/main/scripting/examples/java/Newsgroup/PostNewsgroup.java (revision cd519653a6b6a9e2ff38774da567b1ae7cbeddbb)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 import java.awt.*;
23 import java.awt.event.*;
24 import javax.swing.*;
25 import javax.swing.border.*;
26 import java.util.Vector;
27 import com.sun.star.script.framework.runtime.XScriptContext;
28 
29 
30 public class PostNewsgroup extends JFrame
31 {
32 
33     // Post to newsgroup objects
34     private NewsGroup[] subscribedNewsgroups = null;
35     private XScriptContext xscriptcontext = null;
36 
37     private final int FRAMEX = 300;
38     private final int FRAMEY = 300;
39     private final int TEXTBOXWIDTH = 300;
40     private final int TEXTBOXHEIGHT = 24;
41     private final int TEXTAREAHEIGHT = 70;
42     private final int BUTTONWIDTH = 80;
43     private final int BUTTONHEIGHT = 30;
44 
45     private PostNewsgroup window = null;
46     private JComboBox newsgroupComboBox = null;
47     private JTextField hostTextField = null;
48     private JTextField replyTextField = null;
49     private JTextField subjectTextField = null;
50     private JTextArea commentTextArea = null;
51     private JRadioButton officeHtmlButton = null;
52     private JRadioButton officeButton = null;
53     private JRadioButton htmlButton = null;
54     private JButton postButton = null;
55     private JButton cancelButton = null;
56 
57     // JFrame for launch progress dialog
58     private StatusWindow statusWindow = null;
59     private String statusLine = "";
60 
61     // Tool tip text
62     private final String newsgroupText = "Newsgroup name";
63     private final String hostText = "Newsgroup host/server name";
64     private final String replyText = "Email address to reply to";
65     private final String subjectText = "Subject title for the mail";
66     private final String commentText = "Additional comment on mail";
67     private final String officeHtmlText = "Post as both Office and HTML attachments";
68     private final String officeText = "Post as Office attachment only";
69     private final String htmlText = "Post as HTML attachment only";
70     private final String postText = "Post to newsgroup";
71     private final String cancelText = "Cancel post to newsgroup";
72 
73 
post( XScriptContext xsc )74     public void post( XScriptContext xsc )
75     {
76         xscriptcontext = xsc;
77         window = this;
78 
79         // create mailcap and mimetypes files (fix for classloader problem)
80         MimeConfiguration.createFiles( xscriptcontext );
81 
82         this.setTitle( "Post Document To Newsgroup" );
83         this.setLocation( FRAMEX, FRAMEY );
84 
85         this.addFocusListener( new FocusAdapter()
86         {
87             public void focusGained( FocusEvent event )
88             {
89                 System.out.println( "Focus gained" );
90                 window.update( window.getGraphics() );
91             }
92 
93             public void focusLost( FocusEvent event )
94                         {
95                 System.out.println( "Focus lost" );
96                         }
97         });
98 
99         Container container = getContentPane();
100         container.setLayout( new GridBagLayout() );;
101         GridBagConstraints constraints = new GridBagConstraints();
102         constraints.fill = GridBagConstraints.BOTH;
103 
104         JPanel labelPanel = constructLabelPanel();
105         JPanel textPanel = constructTextPanel();
106         JPanel optionPanel = constructOptionPanel();
107         JPanel buttonPanel = constructButtonPanel();
108 
109         constraints.gridx = 0;
110         constraints.gridy = 0;
111         constraints.gridwidth = 1;
112         constraints.gridheight = 3;
113         constraints.insets = new Insets( 15, 15, 5, 5 );
114         container.add( labelPanel, constraints );
115 
116         constraints.gridx = 1;
117         constraints.gridy = 0;
118         constraints.gridwidth = 4;
119         constraints.gridheight = 3;
120         constraints.insets = new Insets( 15, 5, 5, 15 );
121         container.add( textPanel, constraints );
122 
123         constraints.gridx = 0;
124         constraints.gridy = 3;
125         constraints.gridwidth = 5;
126         constraints.gridheight = 1;
127         constraints.insets = new Insets( 5, 15, 5, 15 );
128         container.add( optionPanel, constraints );
129 
130         constraints.gridx = 0;
131         constraints.gridy = 4;
132         constraints.gridwidth = 5;
133         constraints.gridheight = 1;
134         constraints.insets = new Insets( 5, 5, 5, 5 );
135         container.add( buttonPanel, constraints );
136 
137         this.pack();
138         this.setResizable( false );
139         this.setVisible( true );
140     }
141 
142 
constructLabelPanel()143     private JPanel constructLabelPanel()
144     {
145         JLabel newsgroupLabel = new JLabel( "Newsgroup:" );
146         JLabel hostLabel = new JLabel( "Host:" );
147         JLabel replyLabel = new JLabel( "Reply:" );
148         JLabel subjectLabel = new JLabel( "Subject:" );
149         JLabel commentLabel = new JLabel( "Comment:" );
150 
151         newsgroupLabel.setToolTipText( newsgroupText );
152         hostLabel.setToolTipText( hostText );
153         replyLabel.setToolTipText( replyText );
154         subjectLabel.setToolTipText( subjectText );
155         commentLabel.setToolTipText( commentText );
156 
157         JPanel newsgroupPanel = new JPanel();
158         newsgroupPanel.setLayout( new BorderLayout() );
159         newsgroupPanel.add( newsgroupLabel, "West" );
160         JPanel hostPanel = new JPanel();
161         hostPanel.setLayout( new BorderLayout() );
162         hostPanel.add( hostLabel, "West" );
163         JPanel replyPanel = new JPanel();
164         replyPanel.setLayout( new BorderLayout() );
165         replyPanel.add( replyLabel, "West" );
166         JPanel subjectPanel = new JPanel();
167         subjectPanel.setLayout( new BorderLayout() );
168         subjectPanel.add( subjectLabel, "West" );
169         JPanel commentPanel = new JPanel();
170         commentPanel.setLayout( new BorderLayout() );
171         commentPanel.add( commentLabel, "West" );
172         JPanel emptyPanel = new JPanel();
173 
174         final int labelWidth = 80;
175         newsgroupPanel.setPreferredSize( new Dimension( labelWidth, TEXTBOXHEIGHT ) );
176         hostPanel.setPreferredSize( new Dimension( labelWidth, TEXTBOXHEIGHT ) );
177         replyPanel.setPreferredSize( new Dimension( labelWidth, TEXTBOXHEIGHT ) );
178         subjectPanel.setPreferredSize( new Dimension( labelWidth, TEXTBOXHEIGHT ) );
179         commentPanel.setPreferredSize( new Dimension( labelWidth, TEXTBOXHEIGHT ) );
180 
181         JPanel panel = new JPanel();
182         panel.setLayout( new GridBagLayout() );
183         GridBagConstraints constraints = new GridBagConstraints();
184         constraints.fill = GridBagConstraints.BOTH;
185         constraints.insets = new Insets( 5, 5, 5, 5 );
186 
187         constraints.gridx = 0;
188         constraints.gridy = 0;
189         constraints.gridwidth = 1;
190         constraints.gridheight = 1;
191         constraints.weightx = constraints.weighty = 0.0;
192         panel.add( newsgroupPanel, constraints );
193 
194         constraints.gridx = 0;
195         constraints.gridy = 1;
196         constraints.gridwidth = 1;
197         constraints.gridheight = 1;
198         panel.add( hostPanel, constraints );
199 
200         constraints.gridx = 0;
201         constraints.gridy = 2;
202         constraints.gridwidth = 1;
203         constraints.gridheight = 1;
204         panel.add( replyPanel, constraints );
205 
206         constraints.gridx = 0;
207         constraints.gridy = 3;
208         constraints.gridwidth = 1;
209         constraints.gridheight = 1;
210         panel.add( subjectPanel, constraints );
211 
212         constraints.gridx = 0;
213         constraints.gridy = 4;
214         constraints.gridwidth = 1;
215         constraints.gridheight = 1;
216         panel.add( commentPanel, constraints );
217 
218         constraints.gridx = 0;
219         constraints.gridy = 5;
220         constraints.gridwidth = 1;
221         constraints.gridheight = 1;
222         constraints.weightx = constraints.weighty = 1.0;
223         panel.add( emptyPanel, constraints );
224 
225         return panel;
226     }
227 
228 
constructTextPanel()229     private JPanel constructTextPanel()
230     {
231         hostTextField = new JTextField();
232                 hostTextField.setPreferredSize( new Dimension( TEXTBOXWIDTH, TEXTBOXHEIGHT ) );
233                 hostTextField.setToolTipText( hostText );
234         hostTextField.setBorder( new EtchedBorder() );
235 
236         //optionPanel.setBorder( new TitledBorder( new EtchedBorder(), "Document Format" ) );
237         newsgroupComboBox = getNewsgroupCombo();
238 
239         replyTextField = new JTextField();
240         replyTextField.setPreferredSize( new Dimension( TEXTBOXWIDTH, TEXTBOXHEIGHT ) );
241         replyTextField.setToolTipText( replyText );
242         replyTextField.setBorder( new EtchedBorder() );
243 
244         subjectTextField = new JTextField();
245         subjectTextField.setPreferredSize( new Dimension( TEXTBOXWIDTH, TEXTBOXHEIGHT ) );
246         subjectTextField.setToolTipText( subjectText );
247         subjectTextField.setBorder( new EtchedBorder() );
248 
249         commentTextArea = new JTextArea();
250         commentTextArea.setPreferredSize( new Dimension( TEXTBOXWIDTH, TEXTAREAHEIGHT ) );
251         commentTextArea.setToolTipText( commentText );
252         commentTextArea.setBorder( new EtchedBorder() );
253 
254         JPanel panel = new JPanel();
255         panel.setLayout( new GridBagLayout() );
256         GridBagConstraints constraints = new GridBagConstraints();
257         constraints.fill = GridBagConstraints.BOTH;
258         constraints.insets = new Insets( 5, 5, 5, 5 );
259 
260         constraints.gridx = 0;
261         constraints.gridy = 0;
262         constraints.gridwidth = 1;
263         constraints.gridheight = 1;
264         panel.add( newsgroupComboBox, constraints );
265 
266         constraints.gridx = 0;
267         constraints.gridy = 1;
268         constraints.gridwidth = 1;
269         constraints.gridheight = 1;
270         panel.add( hostTextField, constraints );
271 
272         constraints.gridx = 0;
273         constraints.gridy = 2;
274         constraints.gridwidth = 1;
275         constraints.gridheight = 1;
276         panel.add( replyTextField, constraints );
277 
278         constraints.gridx = 0;
279         constraints.gridy = 3;
280         constraints.gridwidth = 1;
281         constraints.gridheight = 1;
282         panel.add( subjectTextField, constraints );
283 
284         constraints.gridx = 0;
285         constraints.gridy = 4;
286         constraints.gridwidth = 1;
287         constraints.gridheight = 2;
288         panel.add( commentTextArea, constraints );
289 
290         return panel;
291     }
292 
293 
getNewsgroupCombo()294     private JComboBox getNewsgroupCombo()
295     {
296         newsgroupComboBox = new JComboBox();
297         //newsgroupComboBox.setBorder( new EtchedBorder() );
298 
299         newsgroupComboBox.addActionListener(new ActionListener()
300         {
301                 public void actionPerformed(ActionEvent e)
302                 {
303                 // when newsgroup is selected
304                 if( subscribedNewsgroups != null )
305                 {
306                     int position = newsgroupComboBox.getSelectedIndex();
307                     if( position != -1 )
308                     {
309                         hostTextField.setText( subscribedNewsgroups[ position ].getHostName() );
310                         newsgroupComboBox.setToolTipText( "Newsgroup name: " + subscribedNewsgroups[ position ].getNewsgroupName() + "  (Host name: " + subscribedNewsgroups[ position ].getHostName() + ")" );
311                     }
312                 }
313             }
314         });
315 
316         NewsGroup groupToSend = null;
317         SubscribedNewsgroups newsgroups = new SubscribedNewsgroups();
318         subscribedNewsgroups = newsgroups.getNewsGroups();
319 
320         // Test for no .mozilla or no subscribed newsgroups
321         // subscribedNewsgroups = null;
322 
323         if( subscribedNewsgroups == null )
324         {
325             //System.out.println( "Couldn't find any subscibed newsgroups in .mozilla" );
326             JOptionPane.showMessageDialog( window, "No subscribed newsgroups found in mozilla/netscape profile \nPlease enter newsgroup and host name",
327                             "Newsgroups Information", JOptionPane.INFORMATION_MESSAGE );
328         }
329         else
330         {
331             // Copy all newsgroups into a vector for comparison
332             // Alter entries (to include host name) if duplication is found
333             Vector vector = new Vector( subscribedNewsgroups.length );
334             for(int i=0; i < subscribedNewsgroups.length; i++ )
335             {
336                 vector.add( subscribedNewsgroups[i].getNewsgroupName() );
337             }
338             // Compare and alter
339             for(int i=0; i < subscribedNewsgroups.length; i++ )
340             {
341                 // check if combo box already has a newsgroup with same name
342                 // then add host name to differentiate
343                 for(int j=0; j < subscribedNewsgroups.length; j++ )
344                 {
345                     if( j != i && subscribedNewsgroups[j].getNewsgroupName().equalsIgnoreCase( subscribedNewsgroups[i].getNewsgroupName() ) )
346                     {
347                         vector.set( j, subscribedNewsgroups[j].getNewsgroupName() + "  (" + subscribedNewsgroups[j].getHostName() + ")" );
348                         vector.set( i, subscribedNewsgroups[i].getNewsgroupName() + "  (" + subscribedNewsgroups[i].getHostName() + ")" );
349                     }
350                 }
351             }
352             // Copy converted newsgroups from vector to combo box
353             for(int i=0; i < subscribedNewsgroups.length; i++ )
354             {
355                 newsgroupComboBox.addItem( vector.elementAt(i) );
356             }
357         }// else
358 
359         newsgroupComboBox.setPreferredSize( new Dimension( TEXTBOXWIDTH, TEXTBOXHEIGHT ) );
360         newsgroupComboBox.setEditable( true );
361 
362         return newsgroupComboBox;
363     }
364 
365 
366 
constructOptionPanel()367     private JPanel constructOptionPanel()
368     {
369         officeHtmlButton = new JRadioButton( "Office and HTML", true );
370         officeHtmlButton.setToolTipText( officeHtmlText );
371 
372         officeButton = new JRadioButton( "Office" );
373         officeButton.setToolTipText( officeText );
374 
375         htmlButton = new JRadioButton( "HTML" );
376         htmlButton.setToolTipText( htmlText );
377 
378         JRadioButton[] rbuttons = { officeHtmlButton, officeButton, htmlButton };
379         ButtonGroup radioButtonGroup = new ButtonGroup();
380         for( int i=0; i < rbuttons.length; i++ )
381         {
382             radioButtonGroup.add( rbuttons[i] );
383         }
384 
385         JPanel optionPanel = new JPanel();
386         //optionPanel.setLayout( new GridLayout( 1, 3, 20, 0 ) );
387         optionPanel.setBorder( new TitledBorder( new EtchedBorder(), "Document Format" ) );
388         optionPanel.setLayout( new GridBagLayout() );
389         GridBagConstraints constraints = new GridBagConstraints();
390         constraints.fill = GridBagConstraints.BOTH;
391 
392         constraints.gridx = 0;
393                 constraints.gridy = 0;
394                 constraints.gridwidth = 1;
395                 constraints.gridheight = 1;
396         constraints.insets = new Insets( 5, 5, 5, 30 );
397                 optionPanel.add( officeHtmlButton, constraints );
398 
399         constraints.gridx = 1;
400                 constraints.gridy = 0;
401                 constraints.gridwidth = 1;
402                 constraints.gridheight = 1;
403         constraints.insets = new Insets( 5, 20, 5, 30 );
404                 optionPanel.add( officeButton, constraints );
405 
406         constraints.gridx = 2;
407                 constraints.gridy = 0;
408                 constraints.gridwidth = 1;
409                 constraints.gridheight = 1;
410         constraints.insets = new Insets( 5, 20, 5, 5 );
411                 optionPanel.add( htmlButton, constraints );
412 
413                 return optionPanel;
414     }
415 
416 
417 
sendingActions()418     public boolean sendingActions()
419     {
420             // posting actions
421             // Validate the data
422             if( isValidData() )
423             {
424                 // Create status window
425                 StatusWindow statusWindow = new StatusWindow( window,  "Posting to Newsgroup", FRAMEX, FRAMEY );
426 
427                 statusWindow.setVisible( true );
428                 //statusWindow.requestFocusInWindow();
429                 statusLine = "Ready to send...";
430                 statusWindow.setStatus( 0, statusLine );
431 
432                 // Get the boolean values for HTML/Office document
433                 // params: ( XScriptContext, StatusWindow, html document, office document )
434 
435                 boolean html = false;
436                 boolean office = false;
437                 if( officeHtmlButton.isSelected() ) { html = true; office = true; }
438                 if( officeButton.isSelected() ) { office = true; html = false; }
439                 if( htmlButton.isSelected() ) { html = true; office = false; }
440 
441                 OfficeAttachment officeAttach = new OfficeAttachment( xscriptcontext, statusWindow, html, office );
442 
443                 statusLine = "Getting user input";
444                 statusWindow.setStatus( 2, statusLine );
445                 // Get replyto, subject, comment from textboxes
446                 String replyto = replyTextField.getText();
447                 String subject = subjectTextField.getText();
448                 String comment = commentTextArea.getText();
449 
450                 // Get newsgroup from combo box (corresponding position)
451                 String host = "";
452                 String group = "";
453                 int position = newsgroupComboBox.getSelectedIndex();
454                 if( subscribedNewsgroups == null || position == -1 )
455                 {
456                     host = hostTextField.getText();
457                     group = newsgroupComboBox.getSelectedItem().toString();
458                 }
459                 else
460                 {
461                     //int position = newsgroupComboBox.getSelectedIndex();
462                     host = subscribedNewsgroups[ position ].getHostName();
463                     group = subscribedNewsgroups[ position ].getNewsgroupName();
464                 }
465 
466                 statusLine = "Creating sender object";
467                 statusWindow.setStatus( 3, statusLine );
468                 Sender sender = new Sender( statusWindow, officeAttach, replyto, subject, comment, host, group );
469                 if( !sender.sendMail() )
470                 {
471                     //System.out.println( "Should end here (?)" );
472                     statusWindow.enableCancelButton( true );
473                     officeAttach.cleanUpOnError();
474                     return false;
475                 }
476 
477                 statusLine = "Send is complete";
478                 statusWindow.setStatus( 14, statusLine );
479             }
480             else
481             {
482                 //System.out.println( "Non valid data" );
483                 return false;
484             }
485             return true;
486     }
487 
488 
constructButtonPanel()489     private JPanel constructButtonPanel()
490     {
491         Action postAction = new AbstractAction() {
492             public void actionPerformed( ActionEvent event ) {
493                 // posting actions
494                 sendingActions();
495             }// actionPerformed
496         };
497 
498         Action cancelAction = new AbstractAction() {
499                         public void actionPerformed( ActionEvent event ) {
500                                 // cancelling actions
501                 window.dispose();
502                         }
503                 };
504 
505         postButton = new JButton();
506         postButton.setAction( postAction );
507         postButton.setToolTipText( postText );
508         postButton.setText( "Post" );
509         postButton.setPreferredSize( new Dimension( BUTTONWIDTH + 20, BUTTONHEIGHT ) );
510 
511         cancelButton = new JButton();
512         cancelButton.setAction( cancelAction );
513         cancelButton.setToolTipText( cancelText );
514         cancelButton.setText( "Cancel" );
515         cancelButton.setPreferredSize( new Dimension( BUTTONWIDTH + 20, BUTTONHEIGHT ) );
516 
517         JSeparator sep = new JSeparator( SwingConstants.HORIZONTAL );
518 
519         JPanel buttonPanel = new JPanel();
520         buttonPanel.setLayout( new GridBagLayout() );
521         GridBagConstraints constraints = new GridBagConstraints();
522         constraints.fill = GridBagConstraints.BOTH;
523         constraints.insets = new Insets( 5, 5, 5, 5 );
524 
525         JPanel emptyPanel1 = new JPanel();
526         emptyPanel1.setPreferredSize( new Dimension( BUTTONWIDTH, BUTTONHEIGHT ) );
527 
528         JPanel emptyPanel2 = new JPanel();
529         emptyPanel2.setPreferredSize( new Dimension( BUTTONWIDTH, BUTTONHEIGHT ) );
530 
531         constraints.gridx = 0;
532                 constraints.gridy = 0;
533                 constraints.gridwidth = 4;
534                 constraints.gridheight = 1;
535                 buttonPanel.add( sep, constraints );
536 
537         constraints.gridx = 0;
538                 constraints.gridy = 1;
539                 constraints.gridwidth = 1;
540                 constraints.gridheight = 1;
541                 buttonPanel.add( emptyPanel1, constraints );
542 
543                 constraints.gridx = 1;
544                 constraints.gridy = 1;
545                 constraints.gridwidth = 1;
546                 constraints.gridheight = 1;
547                 buttonPanel.add( emptyPanel2, constraints );
548 
549         constraints.gridx = 2;
550         constraints.gridy = 1;
551         constraints.gridwidth = 1;
552         constraints.gridheight = 1;
553         buttonPanel.add( postButton, constraints );
554 
555         constraints.gridx = 3;
556         constraints.gridy = 1;
557         constraints.gridwidth = 1;
558         constraints.gridheight = 1;
559         constraints.insets = new Insets( 5, 5, 5, 0 );
560         buttonPanel.add( cancelButton, constraints );
561 
562                 return buttonPanel;
563     }
564 
565 
enableButtons( boolean enable )566     public void enableButtons( boolean enable )
567     {
568         if( enable )
569         {
570             postButton.setEnabled( true );
571             cancelButton.setEnabled( true );
572         }
573         else
574         {
575             postButton.setEnabled( false );
576             cancelButton.setEnabled( false );
577         }
578     }
579 
580 
isValidData()581     private boolean isValidData()
582     {
583         // newsgroupComboBox must not be blank (format? dots and whitespace)
584         String newsgroupString = "";
585         int position = newsgroupComboBox.getSelectedIndex();
586         if( subscribedNewsgroups == null || position == -1 )
587         {
588             newsgroupString = newsgroupComboBox.getSelectedItem().toString();
589         }
590         else
591         {
592             //int position = newsgroupComboBox.getSelectedIndex();
593             newsgroupString = subscribedNewsgroups[ position ].getNewsgroupName();
594         }
595         if( newsgroupString.length() == 0 )
596         {
597             //System.out.println( "Please enter a newsgroup name" );
598             newsgroupComboBox.requestFocus();
599             JOptionPane.showMessageDialog( window, "Please enter a newsgroup name", "Input Error", JOptionPane.ERROR_MESSAGE );
600             return false;
601         }
602 
603 
604         // hostTextField must not be blank (format?)
605         String  hostString = hostTextField.getText();
606                 if( hostString.length() == 0 )
607                 {
608             //System.out.println( "Please enter a hostname" );
609             hostTextField.requestFocus();
610             JOptionPane.showMessageDialog( window, "Please enter a hostname", "Input Error", JOptionPane.ERROR_MESSAGE );
611                         return false;
612                 }
613 
614 
615         // replyTextField must have <string>@<string>.<string>
616         // (string at least 2 chars long)
617         // consider <s>.<s>@<s>.<s>.<s> format? (array of dot positons?)
618         String replyString = replyTextField.getText();
619         int atPos = replyString.indexOf( "@" );
620         int dotPos = replyString.lastIndexOf( "." );
621         int length = replyString.length();
622         //System.out.println( "length: " + length + "\n atPos: " + atPos + "\n dotPos: " + dotPos );
623         if( length == 0 || atPos == -1 || dotPos == -1 || atPos < 2 || dotPos < atPos || dotPos + 2 == length || atPos + 2 == dotPos || atPos != replyString.lastIndexOf( "@" ) || replyString.indexOf(" ") != -1 )
624         {
625             //System.out.println( "Please enter a valid reply to email address" );
626             replyTextField.requestFocus();
627             JOptionPane.showMessageDialog( window, "Please enter a valid reply to email address", "Input Error", JOptionPane.ERROR_MESSAGE );
628             return false;
629         }
630 
631 
632         // subjectTextField must not be blank?
633         String subjectString = subjectTextField.getText();
634         if( subjectString.length() == 0 )
635         {
636             //System.out.println( "Please enter subject title" );
637             subjectTextField.requestFocus();
638             JOptionPane.showMessageDialog( window, "Please enter subject title", "Input Error", JOptionPane.ERROR_MESSAGE );
639             return false;
640         }
641 
642         // details are valid
643         return true;
644     }
645 
646 }
647