KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > SnowMailClient > view > actions > PreviewAllAction


1 package SnowMailClient.view.actions;
2
3 import java.awt.Toolkit JavaDoc;
4 import java.awt.Dimension JavaDoc;
5 import java.awt.EventQueue JavaDoc;
6 import java.awt.BorderLayout JavaDoc;
7 import SnowMailClient.MailEngine.*;
8 import SnowMailClient.*;
9 import SnowMailClient.model.*;
10 import SnowMailClient.model.accounts.*;
11 import SnowMailClient.view.*;
12 import SnowMailClient.view.dialogs.*;
13 import SnowMailClient.Language.Language;
14 import SnowMailClient.utils.*;
15 import snow.utils.gui.*;
16 import SnowMailClient.view.MessagesPreview.*;
17 import snow.lookandfeel.*;
18
19 import java.awt.event.*;
20 import javax.swing.*;
21 import javax.swing.text.*;
22 import javax.swing.event.*;
23 import java.util.*;
24 import java.text.*;
25 import java.io.*;
26
27 /** Action to preview all mails (retrieve all mail headers).
28    Display them in a table overview and allow selected to be downloaded.
29    Show spam probability based on header.
30    Very useful to clean mailboxes and reduce traffic.
31
32    TODO: absolute ugly things here: redesign all
33 */

34 public final class PreviewAllAction extends AbstractAction implements Runnable JavaDoc
35 {
36
37   // when non null, a preview exists and is already active.
38
private PreviewDialog previewDialog;
39
40   public PreviewAllAction()
41   {
42        super(Language.translate("Preview"));
43
44        putValue(AbstractAction.SMALL_ICON, SnowMailClientApp.loadImageIcon("pics/messagespreview.PNG"));
45        putValue(AbstractAction.ACCELERATOR_KEY, KeyStroke.getKeyStroke( KeyEvent.VK_E, KeyEvent.CTRL_MASK ) );
46   }
47
48    /** when the button is pressed or the ctrl+E pressed.
49        Only active one time.
50        Always called from EDT
51    */

52    public synchronized void actionPerformed(ActionEvent actionEvent)
53    {
54      // previewDialog nullity is used to detect if a window is already active.
55
System.out.println("PreviewAllAction.actionPerformed");
56      if(previewDialog!=null)
57      {
58         System.out.println("preview dialog already exists");
59         previewDialog.setVisible(true);
60         return;
61      }
62
63      // no already existing => create
64
final PreviewModel previewModel = new PreviewModel();
65      previewDialog = new PreviewDialog( SnowMailClientApp.getInstance(), previewModel, true ); // modal ?
66

67      // BE VERY CAREFUL...
68
Thread JavaDoc t = new Thread JavaDoc(this);
69      t.setName("Preview all action");
70      t.start();
71    }
72
73
74    private final void onClosingPreviewDialog(final List<MailAccount> accounts)
75    {
76       if(previewDialog==null) return;
77
78       //SnowMailClientApp.getInstance().getProperties().saveComponentSizeInINIFile(previewDialog, "AllMailPreviewDialog");
79
previewDialog = null;
80
81       // terminate
82
closeConnections(accounts);
83    }
84
85    private void terminatePreview(final List<MailAccount> accounts)
86    {
87       previewDialog = null;
88
89       // terminate
90
closeConnections(accounts);
91    }
92
93    private final void closeConnections(final List<MailAccount> accounts)
94    {
95       if(accounts==null) return;
96       for(MailAccount ma : accounts)
97       {
98          ma.closePOPConnection();
99       }
100    }
101
102    boolean hasErrors = false;
103
104    /** run in a thread. Fills the preview model with the messages
105    */

106    public void run()
107    {
108       // 1) Collect all accounts to read
109

110       MailAccounts accounts = SnowMailClientApp.getInstance().getAccounts();
111       final Vector<MailAccount> accountsToRead = new Vector<MailAccount>();
112       for(int i=0; i<accounts.getRowCount(); i++)
113       {
114         MailAccount ma = accounts.getAccount(i);
115         if(ma.getUseToReadMails())
116         {
117           accountsToRead.add(ma);
118         }
119       }
120
121       // 2) Look on all for the number of new mails (this will pop up the password dialogs...)
122

123       final JDialog dialog = new JDialog(SnowMailClientApp.getInstance(),
124           Language.translate("Preview of % accounts to read", ""+accountsToRead.size()),
125           false); // [Oct2005] no more modal
126

127       dialog.getContentPane().setLayout(new BorderLayout JavaDoc());
128
129       final AccountLog doc = new AccountLog();
130
131       SimpleAttributeSet set = new SimpleAttributeSet();
132       TabSet ts = new TabSet(new TabStop[]{ new TabStop(250,TabStop.ALIGN_LEFT,TabStop.LEAD_NONE)});
133       set.addAttribute( StyleConstants.TabSet, ts);
134       doc.doc.setParagraphAttributes(0, doc.doc.getLength(), set, true);
135
136       JTextPane textPane = new JTextPane(doc.doc);
137       JScrollPane jsp = new JScrollPane(textPane);
138       jsp.setOpaque(false);
139       jsp.getViewport().setOpaque(false);
140       textPane.setOpaque(false);
141       textPane.setEditable(false);
142       dialog.getContentPane().add(jsp, BorderLayout.CENTER);
143
144       final CloseControlPanel ccp = new CloseControlPanel(dialog, true, true,
145                  Language.translate("View headers"));
146       ccp.getOkButton().setVisible(false);
147       dialog.getContentPane().add(ccp, BorderLayout.SOUTH);
148
149       dialog.setSize(650, 350);
150       SnowMailClientApp.centerComponentOnMainFrame(dialog);
151       EventQueue.invokeLater(new Runnable JavaDoc()
152       {
153          public void run()
154          {
155             dialog.setVisible(true);
156          }
157       });
158
159       final Vector<MailAccount> accountsWithNewMails = new Vector<MailAccount>();
160       final long[] totLength = new long[1];
161       final int[] totMails = new int[1];
162
163       Vector<Thread JavaDoc> readThreads = new Vector<Thread JavaDoc>();
164
165       hasErrors = false;
166
167    rl:for(MailAccount _ma: accountsToRead)
168       {
169          if(ccp.getWasCancelled()) break rl;
170
171          final MailAccount ma = _ma;
172
173          Thread JavaDoc rt = new Thread JavaDoc() { public void run()
174          {
175            try
176            {
177              int[] count = ma.getCheckedPopConnection().getNumberOfMessages();
178              doc.append( "\r\n" + ma.getAddress() + ":\t" +
179                (count[0]!=1 ?
180                   Language.translate("% new messages", ""+count[0])
181                 : Language.translate("1 new message"))
182              );
183
184              doc.append( "\t("+MailMessageUtils.formatSize(count[1])+")" );
185
186              totMails[0] += count[0];
187              totLength[0] += count[1];
188
189              if(count[0]>0)
190              {
191                accountsWithNewMails.add(ma);
192              }
193            }
194            catch(Exception JavaDoc e)
195            {
196              //e.printStackTrace();
197
doc.append("\r\n" + ma.getAddress() + ":\t");
198              doc.appendError(e.getMessage());
199              hasErrors = true;
200            }
201          }};
202          rt.setPriority(Thread.NORM_PRIORITY-1);
203          rt.start();
204          readThreads.add(rt);
205       }
206
207       // wait for all completed
208
for(Thread JavaDoc t : readThreads)
209       {
210          try{
211            t.join();
212          } catch(Exception JavaDoc ex) {}
213       }
214
215
216       if(ccp.getWasCancelled())
217       {
218          doc.appendError("\nOperation cancelled.");
219          dialog.setVisible(false);
220          terminatePreview(accountsToRead);
221       }
222       else if(totMails[0]>0)
223       {
224          if(!hasErrors)
225          {
226            dialog.setVisible(false);
227            launchPreview(totMails[0], totLength[0], accountsWithNewMails);
228          }
229          else
230          {
231            ccp.getOkButton().setVisible(true);
232            // has errors => wait on close
233
dialog.addWindowListener(new WindowAdapter()
234            {
235                boolean closed = false;
236                @Override JavaDoc public void windowClosed(WindowEvent we)
237                {
238                  if(closed) return;
239                  closed=true;
240                  launch();
241                }
242                @Override JavaDoc public void windowClosing(WindowEvent we)
243                {
244                  if(closed) return;
245                  closed=true;
246                  launch();
247                }
248
249                void launch()
250                {
251                  if(ccp.getWasCancelled())
252                  {
253                     terminatePreview(accountsToRead);
254                     return;
255                  }
256                  launchPreview(totMails[0], totLength[0], accountsWithNewMails);
257                }
258            });
259          }
260       }
261       else
262       {
263          // no mails...
264
// nothing, let the dialog run
265
System.out.println("no mails");
266          // Feb2005: added this missing close op !
267
dialog.addWindowListener(new WindowAdapter()
268            {
269                boolean closed = false;
270                @Override JavaDoc public void windowClosed(WindowEvent we)
271                {
272                  if(closed) return;
273                  close();
274                }
275                @Override JavaDoc public void windowClosing(WindowEvent we)
276                {
277                  if(closed) return;
278                  close();
279                }
280
281                void close()
282                {
283                  terminatePreview(accountsToRead);
284                }
285            });
286       }
287    }
288
289
290    private void launchPreview(int totalNumberOfMails, long totSize, final List<MailAccount> accounts)
291    {
292       Dimension JavaDoc screen = Toolkit.getDefaultToolkit().getScreenSize();
293       SnowMailClientApp.getInstance().getProperties().setComponentSizeFromINIFile(
294           previewDialog, "AllMailPreviewDialog",
295           (int) Math.min(ThemesManager.getLabelFontSize()*80, screen.getWidth()),
296           (int) Math.min(ThemesManager.getLabelFontSize()*55, screen.getHeight()),
297           ThemesManager.getLabelFontSize()*5,
298           ThemesManager.getLabelFontSize()*5
299       );
300
301       if(previewDialog.getWidth()<100 || previewDialog.getHeight()<100)
302       {
303          previewDialog.setSize(
304            (int) Math.min(ThemesManager.getLabelFontSize()*80, screen.getWidth()),
305            (int) Math.min(ThemesManager.getLabelFontSize()*55, screen.getHeight()));
306          previewDialog.setLocationRelativeTo(null);
307       }
308
309       previewDialog.addWindowListener(new WindowAdapter()
310       {
311          @Override JavaDoc public void windowClosed(WindowEvent e)
312          {
313             onClosingPreviewDialog(accounts);
314          }
315
316          @Override JavaDoc public void windowClosing(WindowEvent e)
317          {
318             onClosingPreviewDialog(accounts);
319          }
320       });
321
322
323       EventQueue.invokeLater(new Runnable JavaDoc() { public void run()
324       {
325         // no more modal !!
326
previewDialog.setVisible(true);
327
328         // on closing, the action onClosingPreviewDialog() will be called
329
}});
330
331       previewDialog.setMaximalMessageNumber(totalNumberOfMails);
332       previewDialog.setStatusLabelText(
333                Language.translate("You have % new messages", ""+totalNumberOfMails)
334              + (totalNumberOfMails>0?" ("+MailMessageUtils.formatSize(totSize) + ")":"")
335       );
336
337       final List<Thread JavaDoc> readThreads = new ArrayList<Thread JavaDoc>();
338       for(MailAccount _ma : accounts)
339       {
340         // each in his own thread
341
final MailAccount ma = _ma;
342         Thread JavaDoc tr = new Thread JavaDoc() { public void run()
343         {
344           try
345           {
346             downloadHeaders(ma, previewDialog);
347           }
348           catch(Exception JavaDoc e)
349           {
350             e.printStackTrace();
351           }
352         }};
353         tr.setPriority(Thread.NORM_PRIORITY-1);
354         readThreads.add(tr);
355         tr.start();
356       }
357
358       // wait for completion (but don't block the EDT !
359
Thread JavaDoc t = new Thread JavaDoc() { public void run() {
360         for(Thread JavaDoc tr: readThreads)
361         {
362            try
363            {
364               tr.join();
365            }
366            catch(Exception JavaDoc ex) {}
367         }
368
369         // can have been closed !
370
if(previewDialog==null) return;
371
372         previewDialog.setMessageProgressInvisible();
373       }};
374       t.setPriority(Thread.NORM_PRIORITY-1);
375       t.start();
376    }
377
378
379
380    private void downloadHeaders(MailAccount account, final PreviewDialog previewDialog) throws Exception JavaDoc
381    {
382         SecurePopConnection spop = account.getCheckedPopConnection();
383         String JavaDoc[] messUIDLS = spop.getMessagesUIDLs();
384         int[] messSizes = spop.getSizes_from_MessagesLIST(spop.getMessagesLIST_());
385
386         for(int i=0; i<messSizes.length; i++)
387         {
388            previewDialog._incrementMessageProgress(1);
389            String JavaDoc messHeaderText = spop.getMessageTop(messUIDLS[i], 0);
390            try
391            {
392              String JavaDoc uidl = messUIDLS[i];
393              long size = messSizes[i];
394
395              final PreviewHeader header = new PreviewHeader(account, uidl, size);
396
397              Header.parseHeader(new NumberedLineReader(messHeaderText), header);
398
399              EventQueue.invokeLater(new Runnable JavaDoc()
400              { public void run()
401                {
402                  previewDialog.getPreviewModel().addMessageHeader(header);
403                }
404              });
405            }
406            catch(Exception JavaDoc e)
407            {
408              e.printStackTrace();
409            }
410         }
411    }
412
413 } // PreviewAllAction
Popular Tags