2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
5 * This file is part of Jalview.
7 * Jalview is free software: you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation, either version 3
10 * of the License, or (at your option) any later version.
12 * Jalview is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty
14 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
19 * The Jalview Authors are detailed in the 'AUTHORS' file.
23 import jalview.api.AlignViewportI;
24 import jalview.api.AlignmentViewPanel;
25 import jalview.bin.Cache;
26 import jalview.bin.Jalview;
27 import jalview.io.DataSourceType;
28 import jalview.io.FileFormat;
29 import jalview.io.FileFormatException;
30 import jalview.io.FileFormatI;
31 import jalview.io.FileLoader;
32 import jalview.io.IdentifyFile;
33 import jalview.io.JalviewFileChooser;
34 import jalview.io.JalviewFileView;
35 import jalview.jbgui.GSplitFrame;
36 import jalview.jbgui.GStructureViewer;
37 import jalview.structure.StructureSelectionManager;
38 import jalview.util.ImageMaker;
39 import jalview.util.MessageManager;
40 import jalview.util.Platform;
41 import jalview.viewmodel.AlignmentViewport;
42 import jalview.ws.params.ParamManager;
44 import java.awt.BorderLayout;
45 import java.awt.Color;
46 import java.awt.Dimension;
47 import java.awt.FontMetrics;
48 import java.awt.Graphics;
49 import java.awt.GridLayout;
50 import java.awt.Point;
51 import java.awt.Rectangle;
52 import java.awt.Toolkit;
53 import java.awt.Window;
54 import java.awt.datatransfer.Clipboard;
55 import java.awt.datatransfer.ClipboardOwner;
56 import java.awt.datatransfer.DataFlavor;
57 import java.awt.datatransfer.Transferable;
58 import java.awt.dnd.DnDConstants;
59 import java.awt.dnd.DropTargetDragEvent;
60 import java.awt.dnd.DropTargetDropEvent;
61 import java.awt.dnd.DropTargetEvent;
62 import java.awt.dnd.DropTargetListener;
63 import java.awt.event.ActionEvent;
64 import java.awt.event.ActionListener;
65 import java.awt.event.FocusEvent;
66 import java.awt.event.FocusListener;
67 import java.awt.event.KeyEvent;
68 import java.awt.event.MouseAdapter;
69 import java.awt.event.MouseEvent;
70 import java.awt.event.MouseListener;
71 import java.awt.event.WindowAdapter;
72 import java.awt.event.WindowEvent;
73 import java.beans.PropertyChangeEvent;
74 import java.beans.PropertyChangeListener;
75 import java.beans.PropertyVetoException;
76 import java.io.BufferedInputStream;
78 import java.io.FileOutputStream;
80 import java.util.ArrayList;
81 import java.util.Hashtable;
82 import java.util.List;
83 import java.util.StringTokenizer;
84 import java.util.Vector;
85 import java.util.concurrent.ExecutorService;
86 import java.util.concurrent.Executors;
87 import java.util.concurrent.Semaphore;
89 import javax.swing.AbstractAction;
90 import javax.swing.DefaultDesktopManager;
91 import javax.swing.DesktopManager;
92 import javax.swing.JButton;
93 import javax.swing.JComboBox;
94 import javax.swing.JComponent;
95 import javax.swing.JDesktopPane;
96 import javax.swing.JFrame;
97 import javax.swing.JInternalFrame;
98 import javax.swing.JLabel;
99 import javax.swing.JMenuItem;
100 import javax.swing.JOptionPane;
101 import javax.swing.JPanel;
102 import javax.swing.JPopupMenu;
103 import javax.swing.JProgressBar;
104 import javax.swing.KeyStroke;
105 import javax.swing.SwingUtilities;
106 import javax.swing.event.HyperlinkEvent;
107 import javax.swing.event.HyperlinkEvent.EventType;
108 import javax.swing.event.MenuEvent;
109 import javax.swing.event.MenuListener;
116 * @version $Revision: 1.155 $
118 public class Desktop extends jalview.jbgui.GDesktop implements
119 DropTargetListener, ClipboardOwner, IProgressIndicator,
120 jalview.api.StructureSelectionManagerProvider
123 private JalviewChangeSupport changeSupport = new JalviewChangeSupport();
126 * news reader - null if it was never started.
128 private BlogReader jvnews = null;
130 private File projectFile;
134 * @see jalview.gui.JalviewChangeSupport#addJalviewPropertyChangeListener(java.beans.PropertyChangeListener)
136 public void addJalviewPropertyChangeListener(
137 PropertyChangeListener listener)
139 changeSupport.addJalviewPropertyChangeListener(listener);
143 * @param propertyName
145 * @see jalview.gui.JalviewChangeSupport#addJalviewPropertyChangeListener(java.lang.String,
146 * java.beans.PropertyChangeListener)
148 public void addJalviewPropertyChangeListener(String propertyName,
149 PropertyChangeListener listener)
151 changeSupport.addJalviewPropertyChangeListener(propertyName, listener);
155 * @param propertyName
157 * @see jalview.gui.JalviewChangeSupport#removeJalviewPropertyChangeListener(java.lang.String,
158 * java.beans.PropertyChangeListener)
160 public void removeJalviewPropertyChangeListener(String propertyName,
161 PropertyChangeListener listener)
163 changeSupport.removeJalviewPropertyChangeListener(propertyName,
167 /** Singleton Desktop instance */
168 public static Desktop instance;
170 public static MyDesktopPane desktop;
172 static int openFrameCount = 0;
174 static final int xOffset = 30;
176 static final int yOffset = 30;
178 public static jalview.ws.jws1.Discoverer discoverer;
180 public static Object[] jalviewClipboard;
182 public static boolean internalCopy = false;
184 static int fileLoadingCount = 0;
186 class MyDesktopManager implements DesktopManager
189 private DesktopManager delegate;
191 public MyDesktopManager(DesktopManager delegate)
193 this.delegate = delegate;
197 public void activateFrame(JInternalFrame f)
201 delegate.activateFrame(f);
202 } catch (NullPointerException npe)
204 Point p = getMousePosition();
205 instance.showPasteMenu(p.x, p.y);
210 public void beginDraggingFrame(JComponent f)
212 delegate.beginDraggingFrame(f);
216 public void beginResizingFrame(JComponent f, int direction)
218 delegate.beginResizingFrame(f, direction);
222 public void closeFrame(JInternalFrame f)
224 delegate.closeFrame(f);
228 public void deactivateFrame(JInternalFrame f)
230 delegate.deactivateFrame(f);
234 public void deiconifyFrame(JInternalFrame f)
236 delegate.deiconifyFrame(f);
240 public void dragFrame(JComponent f, int newX, int newY)
246 delegate.dragFrame(f, newX, newY);
250 public void endDraggingFrame(JComponent f)
252 delegate.endDraggingFrame(f);
256 public void endResizingFrame(JComponent f)
258 delegate.endResizingFrame(f);
262 public void iconifyFrame(JInternalFrame f)
264 delegate.iconifyFrame(f);
268 public void maximizeFrame(JInternalFrame f)
270 delegate.maximizeFrame(f);
274 public void minimizeFrame(JInternalFrame f)
276 delegate.minimizeFrame(f);
280 public void openFrame(JInternalFrame f)
282 delegate.openFrame(f);
286 public void resizeFrame(JComponent f, int newX, int newY, int newWidth,
293 delegate.resizeFrame(f, newX, newY, newWidth, newHeight);
297 public void setBoundsForFrame(JComponent f, int newX, int newY,
298 int newWidth, int newHeight)
300 delegate.setBoundsForFrame(f, newX, newY, newWidth, newHeight);
303 // All other methods, simply delegate
308 * Creates a new Desktop object.
313 * A note to implementors. It is ESSENTIAL that any activities that might
314 * block are spawned off as threads rather than waited for during this
318 doVamsasClientCheck();
320 groovyShell = new JMenuItem();
321 groovyShell.setText(MessageManager.getString("label.groovy_console"));
322 groovyShell.addActionListener(new ActionListener()
325 public void actionPerformed(ActionEvent e)
327 groovyShell_actionPerformed();
330 toolsMenu.add(groovyShell);
331 groovyShell.setVisible(true);
333 doConfigureStructurePrefs();
334 setTitle("Jalview " + jalview.bin.Cache.getProperty("VERSION"));
335 setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
336 boolean selmemusage = jalview.bin.Cache.getDefault("SHOW_MEMUSAGE",
338 boolean showjconsole = jalview.bin.Cache.getDefault(
339 "SHOW_JAVA_CONSOLE", false);
340 desktop = new MyDesktopPane(selmemusage);
341 if (Platform.isAMac())
343 desktop.setDoubleBuffered(false);
345 showMemusage.setSelected(selmemusage);
346 desktop.setBackground(Color.white);
347 getContentPane().setLayout(new BorderLayout());
348 // alternate config - have scrollbars - see notes in JAL-153
349 // JScrollPane sp = new JScrollPane();
350 // sp.getViewport().setView(desktop);
351 // getContentPane().add(sp, BorderLayout.CENTER);
352 getContentPane().add(desktop, BorderLayout.CENTER);
353 desktop.setDragMode(JDesktopPane.OUTLINE_DRAG_MODE);
355 // This line prevents Windows Look&Feel resizing all new windows to maximum
356 // if previous window was maximised
357 desktop.setDesktopManager(new MyDesktopManager(
358 new DefaultDesktopManager()));
360 Rectangle dims = getLastKnownDimensions("");
367 Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
368 setBounds((screenSize.width - 900) / 2,
369 (screenSize.height - 650) / 2, 900, 650);
371 jconsole = new Console(this, showjconsole);
372 // add essential build information
373 jconsole.setHeader("Jalview Version: "
374 + jalview.bin.Cache.getProperty("VERSION") + "\n"
375 + "Jalview Installation: "
376 + jalview.bin.Cache.getDefault("INSTALLATION", "unknown")
377 + "\n" + "Build Date: "
378 + jalview.bin.Cache.getDefault("BUILD_DATE", "unknown") + "\n"
379 + "Java version: " + System.getProperty("java.version") + "\n"
380 + System.getProperty("os.arch") + " "
381 + System.getProperty("os.name") + " "
382 + System.getProperty("os.version"));
384 showConsole(showjconsole);
386 showNews.setVisible(false);
388 this.addWindowListener(new WindowAdapter()
391 public void windowClosing(WindowEvent evt)
398 this.addMouseListener(ma = new MouseAdapter()
401 public void mousePressed(MouseEvent evt)
403 if (evt.isPopupTrigger())
405 showPasteMenu(evt.getX(), evt.getY());
409 desktop.addMouseListener(ma);
411 this.addFocusListener(new FocusListener()
415 public void focusLost(FocusEvent e)
417 // TODO Auto-generated method stub
422 public void focusGained(FocusEvent e)
424 Cache.log.debug("Relaying windows after focus gain");
425 // make sure that we sort windows properly after we gain focus
426 instance.relayerWindows();
429 this.setDropTarget(new java.awt.dnd.DropTarget(desktop, this));
430 // Spawn a thread that shows the splashscreen
431 SwingUtilities.invokeLater(new Runnable()
441 // Thread off a new instance of the file chooser - this reduces the time it
442 // takes to open it later on.
443 new Thread(new Runnable()
448 Cache.log.debug("Filechooser init thread started.");
449 FileFormat fileFormat = FileFormat.valueOf(Cache
450 .getProperty("DEFAULT_FILE_FORMAT"));
451 new JalviewFileChooser(Cache.getProperty("LAST_DIRECTORY"),
452 // jalview.io.AppletFormatAdapter.READABLE_EXTENSIONS,
453 // jalview.io.AppletFormatAdapter.READABLE_FNAMES,
455 Cache.log.debug("Filechooser init thread finished.");
458 // Add the service change listener
459 changeSupport.addJalviewPropertyChangeListener("services",
460 new PropertyChangeListener()
464 public void propertyChange(PropertyChangeEvent evt)
466 Cache.log.debug("Firing service changed event for "
467 + evt.getNewValue());
468 JalviewServicesChanged(evt);
474 public void doConfigureStructurePrefs()
476 // configure services
477 StructureSelectionManager ssm = StructureSelectionManager
478 .getStructureSelectionManager(this);
479 if (jalview.bin.Cache.getDefault(Preferences.ADD_SS_ANN, true))
481 ssm.setAddTempFacAnnot(jalview.bin.Cache.getDefault(
482 Preferences.ADD_TEMPFACT_ANN, true));
483 ssm.setProcessSecondaryStructure(jalview.bin.Cache.getDefault(
484 Preferences.STRUCT_FROM_PDB, true));
485 ssm.setSecStructServices(jalview.bin.Cache.getDefault(
486 Preferences.USE_RNAVIEW, true));
490 ssm.setAddTempFacAnnot(false);
491 ssm.setProcessSecondaryStructure(false);
492 ssm.setSecStructServices(false);
496 public void checkForNews()
498 final Desktop me = this;
499 // Thread off the news reader, in case there are connection problems.
500 addDialogThread(new Runnable()
505 Cache.log.debug("Starting news thread.");
507 jvnews = new BlogReader(me);
508 showNews.setVisible(true);
509 Cache.log.debug("Completed news thread.");
515 protected void showNews_actionPerformed(ActionEvent e)
517 showNews(showNews.isSelected());
520 void showNews(boolean visible)
523 Cache.log.debug((visible ? "Showing" : "Hiding") + " news.");
524 showNews.setSelected(visible);
525 if (visible && !jvnews.isVisible())
527 new Thread(new Runnable()
532 long now = System.currentTimeMillis();
533 Desktop.instance.setProgressBar(
534 MessageManager.getString("status.refreshing_news"), now);
535 jvnews.refreshNews();
536 Desktop.instance.setProgressBar(null, now);
545 * recover the last known dimensions for a jalview window
548 * - empty string is desktop, all other windows have unique prefix
549 * @return null or last known dimensions scaled to current geometry (if last
550 * window geom was known)
552 Rectangle getLastKnownDimensions(String windowName)
554 // TODO: lock aspect ratio for scaling desktop Bug #0058199
555 Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
556 String x = jalview.bin.Cache.getProperty(windowName + "SCREEN_X");
557 String y = jalview.bin.Cache.getProperty(windowName + "SCREEN_Y");
558 String width = jalview.bin.Cache.getProperty(windowName
560 String height = jalview.bin.Cache.getProperty(windowName
562 if ((x != null) && (y != null) && (width != null) && (height != null))
564 int ix = Integer.parseInt(x), iy = Integer.parseInt(y), iw = Integer
565 .parseInt(width), ih = Integer.parseInt(height);
566 if (jalview.bin.Cache.getProperty("SCREENGEOMETRY_WIDTH") != null)
568 // attempt #1 - try to cope with change in screen geometry - this
569 // version doesn't preserve original jv aspect ratio.
570 // take ratio of current screen size vs original screen size.
571 double sw = ((1f * screenSize.width) / (1f * Integer
572 .parseInt(jalview.bin.Cache
573 .getProperty("SCREENGEOMETRY_WIDTH"))));
574 double sh = ((1f * screenSize.height) / (1f * Integer
575 .parseInt(jalview.bin.Cache
576 .getProperty("SCREENGEOMETRY_HEIGHT"))));
577 // rescale the bounds depending upon the current screen geometry.
578 ix = (int) (ix * sw);
579 iw = (int) (iw * sw);
580 iy = (int) (iy * sh);
581 ih = (int) (ih * sh);
582 while (ix >= screenSize.width)
584 jalview.bin.Cache.log
585 .debug("Window geometry location recall error: shifting horizontal to within screenbounds.");
586 ix -= screenSize.width;
588 while (iy >= screenSize.height)
590 jalview.bin.Cache.log
591 .debug("Window geometry location recall error: shifting vertical to within screenbounds.");
592 iy -= screenSize.height;
594 jalview.bin.Cache.log.debug("Got last known dimensions for "
595 + windowName + ": x:" + ix + " y:" + iy + " width:" + iw
598 // return dimensions for new instance
599 return new Rectangle(ix, iy, iw, ih);
604 private void doVamsasClientCheck()
606 if (jalview.bin.Cache.vamsasJarsPresent())
608 setupVamsasDisconnectedGui();
609 VamsasMenu.setVisible(true);
610 final Desktop us = this;
611 VamsasMenu.addMenuListener(new MenuListener()
613 // this listener remembers when the menu was first selected, and
614 // doesn't rebuild the session list until it has been cleared and
616 boolean refresh = true;
619 public void menuCanceled(MenuEvent e)
625 public void menuDeselected(MenuEvent e)
631 public void menuSelected(MenuEvent e)
635 us.buildVamsasStMenu();
640 vamsasStart.setVisible(true);
644 void showPasteMenu(int x, int y)
646 JPopupMenu popup = new JPopupMenu();
647 JMenuItem item = new JMenuItem(
648 MessageManager.getString("label.paste_new_window"));
649 item.addActionListener(new ActionListener()
652 public void actionPerformed(ActionEvent evt)
659 popup.show(this, x, y);
666 Clipboard c = Toolkit.getDefaultToolkit().getSystemClipboard();
667 Transferable contents = c.getContents(this);
669 if (contents != null)
671 String file = (String) contents
672 .getTransferData(DataFlavor.stringFlavor);
674 FileFormatI format = new IdentifyFile().identify(file,
675 DataSourceType.PASTE);
677 new FileLoader().LoadFile(file, DataSourceType.PASTE, format);
680 } catch (Exception ex)
683 .println("Unable to paste alignment from system clipboard:\n"
689 * Adds and opens the given frame to the desktop
700 public static synchronized void addInternalFrame(
701 final JInternalFrame frame, String title, int w, int h)
703 addInternalFrame(frame, title, true, w, h, true);
707 * Add an internal frame to the Jalview desktop
714 * When true, display frame immediately, otherwise, caller must call
715 * setVisible themselves.
721 public static synchronized void addInternalFrame(
722 final JInternalFrame frame, String title, boolean makeVisible,
725 addInternalFrame(frame, title, makeVisible, w, h, true);
729 * Add an internal frame to the Jalview desktop and make it visible
742 public static synchronized void addInternalFrame(
743 final JInternalFrame frame, String title, int w, int h,
746 addInternalFrame(frame, title, true, w, h, resizable);
750 * Add an internal frame to the Jalview desktop
757 * When true, display frame immediately, otherwise, caller must call
758 * setVisible themselves.
766 public static synchronized void addInternalFrame(
767 final JInternalFrame frame, String title, boolean makeVisible,
768 int w, int h, boolean resizable)
771 // TODO: allow callers to determine X and Y position of frame (eg. via
773 // TODO: consider fixing method to update entries in the window submenu with
774 // the current window title
776 frame.setTitle(title);
777 if (frame.getWidth() < 1 || frame.getHeight() < 1)
781 // THIS IS A PUBLIC STATIC METHOD, SO IT MAY BE CALLED EVEN IN
782 // A HEADLESS STATE WHEN NO DESKTOP EXISTS. MUST RETURN
783 // IF JALVIEW IS RUNNING HEADLESS
784 // ///////////////////////////////////////////////
786 || (System.getProperty("java.awt.headless") != null && System
787 .getProperty("java.awt.headless").equals("true")))
794 frame.setVisible(makeVisible);
795 frame.setClosable(true);
796 frame.setResizable(resizable);
797 frame.setMaximizable(resizable);
798 frame.setIconifiable(resizable);
799 if (Platform.isAMac())
801 frame.setIconifiable(false);
802 frame.setFrameIcon(null);
803 // frame.setDesktopIcon(null);
804 frame.setDoubleBuffered(false);
806 if (frame.getX() < 1 && frame.getY() < 1)
808 frame.setLocation(xOffset * openFrameCount, yOffset
809 * ((openFrameCount - 1) % 10) + yOffset);
812 final JMenuItem menuItem = new JMenuItem(title);
813 frame.addInternalFrameListener(new javax.swing.event.InternalFrameAdapter()
816 public void internalFrameActivated(
817 javax.swing.event.InternalFrameEvent evt)
819 JInternalFrame itf = desktop.getSelectedFrame();
828 public void internalFrameClosed(
829 javax.swing.event.InternalFrameEvent evt)
831 PaintRefresher.RemoveComponent(frame);
833 windowMenu.remove(menuItem);
834 JInternalFrame itf = desktop.getSelectedFrame();
843 menuItem.addActionListener(new ActionListener()
846 public void actionPerformed(ActionEvent e)
850 frame.setSelected(true);
851 frame.setIcon(false);
852 } catch (java.beans.PropertyVetoException ex)
858 menuItem.addMouseListener(new MouseListener()
862 public void mouseReleased(MouseEvent e)
867 public void mousePressed(MouseEvent e)
872 public void mouseExited(MouseEvent e)
876 frame.setSelected(false);
877 } catch (PropertyVetoException e1)
883 public void mouseEntered(MouseEvent e)
887 frame.setSelected(true);
888 } catch (PropertyVetoException e1)
894 public void mouseClicked(MouseEvent e)
900 windowMenu.add(menuItem);
906 frame.setSelected(true);
907 frame.requestFocus();
908 } catch (java.beans.PropertyVetoException ve)
910 } catch (java.lang.ClassCastException cex)
913 .warn("Squashed a possible GUI implementation error. If you can recreate this, please look at http://issues.jalview.org/browse/JAL-869",
919 public void lostOwnership(Clipboard clipboard, Transferable contents)
923 Desktop.jalviewClipboard = null;
926 internalCopy = false;
930 public void dragEnter(DropTargetDragEvent evt)
935 public void dragExit(DropTargetEvent evt)
940 public void dragOver(DropTargetDragEvent evt)
945 public void dropActionChanged(DropTargetDragEvent evt)
956 public void drop(DropTargetDropEvent evt)
958 boolean success = true;
959 Transferable t = evt.getTransferable();
960 List<String> files = new ArrayList<String>();
961 List<DataSourceType> protocols = new ArrayList<DataSourceType>();
965 Desktop.transferFromDropTarget(files, protocols, evt, t);
966 } catch (Exception e)
976 for (int i = 0; i < files.size(); i++)
978 String file = files.get(i).toString();
979 DataSourceType protocol = (protocols == null) ? DataSourceType.FILE
981 FileFormatI format = null;
983 if (file.endsWith(".jar"))
985 format = FileFormat.Jalview;
990 format = new IdentifyFile().identify(file, protocol);
993 new FileLoader().LoadFile(file, protocol, format);
996 } catch (Exception ex)
1001 evt.dropComplete(success); // need this to ensure input focus is properly
1002 // transfered to any new windows created
1012 public void inputLocalFileMenuItem_actionPerformed(AlignViewport viewport)
1014 FileFormat fileFormat = FileFormat.valueOf(Cache
1015 .getProperty("DEFAULT_FILE_FORMAT"));
1016 JalviewFileChooser chooser = new JalviewFileChooser(
1017 Cache.getProperty("LAST_DIRECTORY"),
1018 // AppletFormatAdapter.READABLE_EXTENSIONS,
1019 // AppletFormatAdapter.READABLE_FNAMES,
1022 chooser.setFileView(new JalviewFileView());
1023 chooser.setDialogTitle(MessageManager
1024 .getString("label.open_local_file"));
1025 chooser.setToolTipText(MessageManager.getString("action.open"));
1027 int value = chooser.showOpenDialog(this);
1029 if (value == JalviewFileChooser.APPROVE_OPTION)
1031 String choice = chooser.getSelectedFile().getPath();
1032 Cache.setProperty("LAST_DIRECTORY", chooser
1033 .getSelectedFile().getParent());
1035 FileFormatI format = null;
1036 if (chooser.getSelectedFormat() != null
1037 && chooser.getSelectedFormat() == FileFormat.Jalview)
1039 format = FileFormat.Jalview;
1045 format = new IdentifyFile().identify(choice, DataSourceType.FILE);
1046 } catch (FileFormatException e)
1052 if (viewport != null)
1054 new FileLoader().LoadFile(viewport, choice, DataSourceType.FILE,
1059 new FileLoader().LoadFile(choice, DataSourceType.FILE, format);
1069 * @throws FileFormatException
1072 public void inputURLMenuItem_actionPerformed(AlignViewport viewport)
1073 throws FileFormatException
1075 // This construct allows us to have a wider textfield
1077 JLabel label = new JLabel(
1078 MessageManager.getString("label.input_file_url"));
1079 final JComboBox history = new JComboBox();
1081 JPanel panel = new JPanel(new GridLayout(2, 1));
1084 history.setPreferredSize(new Dimension(400, 20));
1085 history.setEditable(true);
1086 history.addItem("http://www.");
1088 String historyItems = jalview.bin.Cache.getProperty("RECENT_URL");
1092 if (historyItems != null)
1094 st = new StringTokenizer(historyItems, "\t");
1096 while (st.hasMoreTokens())
1098 history.addItem(st.nextElement());
1102 int reply = JOptionPane.showInternalConfirmDialog(desktop, panel,
1103 MessageManager.getString("label.input_alignment_from_url"),
1104 JOptionPane.OK_CANCEL_OPTION);
1106 if (reply != JOptionPane.OK_OPTION)
1111 String url = history.getSelectedItem().toString();
1113 if (url.toLowerCase().endsWith(".jar"))
1115 if (viewport != null)
1117 new FileLoader().LoadFile(viewport, url, DataSourceType.URL,
1118 FileFormat.Jalview);
1122 new FileLoader().LoadFile(url, DataSourceType.URL,
1123 FileFormat.Jalview);
1128 FileFormatI format = new IdentifyFile().identify(url,
1129 DataSourceType.URL);
1131 if (format.equals("URL NOT FOUND"))
1133 JOptionPane.showInternalMessageDialog(Desktop.desktop,
1134 MessageManager.formatMessage("label.couldnt_locate",
1135 new Object[] { url }), MessageManager
1136 .getString("label.url_not_found"),
1137 JOptionPane.WARNING_MESSAGE);
1142 if (viewport != null)
1145 .LoadFile(viewport, url, DataSourceType.URL, format);
1149 new FileLoader().LoadFile(url, DataSourceType.URL, format);
1155 * Opens the CutAndPaste window for the user to paste an alignment in to
1158 * - if not null, the pasted alignment is added to the current
1159 * alignment; if null, to a new alignment window
1162 public void inputTextboxMenuItem_actionPerformed(
1163 AlignmentViewPanel viewPanel)
1165 CutAndPasteTransfer cap = new CutAndPasteTransfer();
1166 cap.setForInput(viewPanel);
1167 Desktop.addInternalFrame(cap,
1168 MessageManager.getString("label.cut_paste_alignmen_file"),
1178 Dimension screen = Toolkit.getDefaultToolkit().getScreenSize();
1180 .setProperty("SCREENGEOMETRY_WIDTH", screen.width + "");
1181 jalview.bin.Cache.setProperty("SCREENGEOMETRY_HEIGHT", screen.height
1183 storeLastKnownDimensions("", new Rectangle(getBounds().x,
1184 getBounds().y, getWidth(), getHeight()));
1186 if (jconsole != null)
1188 storeLastKnownDimensions("JAVA_CONSOLE_", jconsole.getBounds());
1189 jconsole.stopConsole();
1193 storeLastKnownDimensions("JALVIEW_RSS_WINDOW_", jvnews.getBounds());
1196 if (dialogExecutor != null)
1198 dialogExecutor.shutdownNow();
1200 closeAll_actionPerformed(null);
1202 if (groovyConsole != null)
1204 // suppress a possible repeat prompt to save script
1205 groovyConsole.setDirty(false);
1206 groovyConsole.exit();
1211 private void storeLastKnownDimensions(String string, Rectangle jc)
1213 jalview.bin.Cache.log.debug("Storing last known dimensions for "
1214 + string + ": x:" + jc.x + " y:" + jc.y + " width:" + jc.width
1215 + " height:" + jc.height);
1217 jalview.bin.Cache.setProperty(string + "SCREEN_X", jc.x + "");
1218 jalview.bin.Cache.setProperty(string + "SCREEN_Y", jc.y + "");
1219 jalview.bin.Cache.setProperty(string + "SCREEN_WIDTH", jc.width + "");
1220 jalview.bin.Cache.setProperty(string + "SCREEN_HEIGHT", jc.height + "");
1230 public void aboutMenuItem_actionPerformed(ActionEvent e)
1232 // StringBuffer message = getAboutMessage(false);
1233 // JOptionPane.showInternalMessageDialog(Desktop.desktop,
1235 // message.toString(), "About Jalview", JOptionPane.INFORMATION_MESSAGE);
1236 new Thread(new Runnable()
1241 new SplashScreen(true);
1246 public StringBuffer getAboutMessage(boolean shortv)
1248 StringBuffer message = new StringBuffer();
1249 message.append("<html>");
1252 message.append("<h1><strong>Version: "
1253 + jalview.bin.Cache.getProperty("VERSION") + "</strong></h1>");
1254 message.append("<strong>Last Updated: <em>"
1255 + jalview.bin.Cache.getDefault("BUILD_DATE", "unknown")
1256 + "</em></strong>");
1262 message.append("<strong>Version "
1263 + jalview.bin.Cache.getProperty("VERSION")
1264 + "; last updated: "
1265 + jalview.bin.Cache.getDefault("BUILD_DATE", "unknown"));
1268 if (jalview.bin.Cache.getDefault("LATEST_VERSION", "Checking").equals(
1271 message.append("<br>...Checking latest version...</br>");
1273 else if (!jalview.bin.Cache.getDefault("LATEST_VERSION", "Checking")
1274 .equals(jalview.bin.Cache.getProperty("VERSION")))
1276 boolean red = false;
1277 if (jalview.bin.Cache.getProperty("VERSION").toLowerCase()
1278 .indexOf("automated build") == -1)
1281 // Displayed when code version and jnlp version do not match and code
1282 // version is not a development build
1283 message.append("<div style=\"color: #FF0000;font-style: bold;\">");
1286 message.append("<br>!! Version "
1287 + jalview.bin.Cache.getDefault("LATEST_VERSION",
1289 + " is available for download from "
1290 + jalview.bin.Cache.getDefault("www.jalview.org",
1291 "http://www.jalview.org") + " !!");
1294 message.append("</div>");
1297 message.append("<br>Authors: "
1299 .getDefault("AUTHORFNAMES",
1300 "The Jalview Authors (See AUTHORS file for current list)")
1301 + "<br><br>Development managed by The Barton Group, University of Dundee, Scotland, UK.<br>"
1302 + "<br><br>For help, see the FAQ at <a href=\"http://www.jalview.org/faq\">www.jalview.org/faq</a> and/or join the jalview-discuss@jalview.org mailing list"
1303 + "<br><br>If you use Jalview, please cite:"
1304 + "<br>Waterhouse, A.M., Procter, J.B., Martin, D.M.A, Clamp, M. and Barton, G. J. (2009)"
1305 + "<br>Jalview Version 2 - a multiple sequence alignment editor and analysis workbench"
1306 + "<br>Bioinformatics doi: 10.1093/bioinformatics/btp033"
1318 public void documentationMenuItem_actionPerformed(ActionEvent e)
1322 Help.showHelpWindow();
1323 } catch (Exception ex)
1329 public void closeAll_actionPerformed(ActionEvent e)
1331 JInternalFrame[] frames = desktop.getAllFrames();
1332 for (int i = 0; i < frames.length; i++)
1336 frames[i].setClosed(true);
1337 } catch (java.beans.PropertyVetoException ex)
1341 System.out.println("ALL CLOSED");
1342 if (v_client != null)
1344 // TODO clear binding to vamsas document objects on close_all
1348 * reset state of singleton objects as appropriate (clear down session state
1349 * when all windows are closed)
1351 StructureSelectionManager ssm = StructureSelectionManager
1352 .getStructureSelectionManager(this);
1360 public void raiseRelated_actionPerformed(ActionEvent e)
1362 reorderAssociatedWindows(false, false);
1366 public void minimizeAssociated_actionPerformed(ActionEvent e)
1368 reorderAssociatedWindows(true, false);
1371 void closeAssociatedWindows()
1373 reorderAssociatedWindows(false, true);
1379 * @seejalview.jbgui.GDesktop#garbageCollect_actionPerformed(java.awt.event.
1383 protected void garbageCollect_actionPerformed(ActionEvent e)
1385 // We simply collect the garbage
1386 jalview.bin.Cache.log.debug("Collecting garbage...");
1388 jalview.bin.Cache.log.debug("Finished garbage collection.");
1395 * jalview.jbgui.GDesktop#showMemusage_actionPerformed(java.awt.event.ActionEvent
1399 protected void showMemusage_actionPerformed(ActionEvent e)
1401 desktop.showMemoryUsage(showMemusage.isSelected());
1408 * jalview.jbgui.GDesktop#showConsole_actionPerformed(java.awt.event.ActionEvent
1412 protected void showConsole_actionPerformed(ActionEvent e)
1414 showConsole(showConsole.isSelected());
1417 Console jconsole = null;
1420 * control whether the java console is visible or not
1424 void showConsole(boolean selected)
1426 showConsole.setSelected(selected);
1427 // TODO: decide if we should update properties file
1428 Cache.setProperty("SHOW_JAVA_CONSOLE", Boolean.valueOf(selected)
1430 jconsole.setVisible(selected);
1433 void reorderAssociatedWindows(boolean minimize, boolean close)
1435 JInternalFrame[] frames = desktop.getAllFrames();
1436 if (frames == null || frames.length < 1)
1441 AlignmentViewport source = null, target = null;
1442 if (frames[0] instanceof AlignFrame)
1444 source = ((AlignFrame) frames[0]).getCurrentView();
1446 else if (frames[0] instanceof TreePanel)
1448 source = ((TreePanel) frames[0]).getViewPort();
1450 else if (frames[0] instanceof PCAPanel)
1452 source = ((PCAPanel) frames[0]).av;
1454 else if (frames[0].getContentPane() instanceof PairwiseAlignPanel)
1456 source = ((PairwiseAlignPanel) frames[0].getContentPane()).av;
1461 for (int i = 0; i < frames.length; i++)
1464 if (frames[i] == null)
1468 if (frames[i] instanceof AlignFrame)
1470 target = ((AlignFrame) frames[i]).getCurrentView();
1472 else if (frames[i] instanceof TreePanel)
1474 target = ((TreePanel) frames[i]).getViewPort();
1476 else if (frames[i] instanceof PCAPanel)
1478 target = ((PCAPanel) frames[i]).av;
1480 else if (frames[i].getContentPane() instanceof PairwiseAlignPanel)
1482 target = ((PairwiseAlignPanel) frames[i].getContentPane()).av;
1485 if (source == target)
1491 frames[i].setClosed(true);
1495 frames[i].setIcon(minimize);
1498 frames[i].toFront();
1502 } catch (java.beans.PropertyVetoException ex)
1517 protected void preferences_actionPerformed(ActionEvent e)
1529 public void saveState_actionPerformed(ActionEvent e)
1531 JalviewFileChooser chooser = new JalviewFileChooser(
1532 jalview.bin.Cache.getProperty("LAST_DIRECTORY"),
1533 new String[] { "jvp" }, new String[] { "Jalview Project" },
1536 chooser.setFileView(new JalviewFileView());
1537 chooser.setDialogTitle(MessageManager.getString("label.save_state"));
1539 int value = chooser.showSaveDialog(this);
1541 if (value == JalviewFileChooser.APPROVE_OPTION)
1543 final Desktop me = this;
1544 final java.io.File choice = chooser.getSelectedFile();
1545 setProjectFile(choice);
1547 new Thread(new Runnable()
1552 // TODO: refactor to Jalview desktop session controller action.
1553 setProgressBar(MessageManager.formatMessage(
1554 "label.saving_jalview_project",
1555 new Object[] { choice.getName() }), choice.hashCode());
1556 jalview.bin.Cache.setProperty("LAST_DIRECTORY",
1557 choice.getParent());
1558 // TODO catch and handle errors for savestate
1559 // TODO prevent user from messing with the Desktop whilst we're saving
1562 new Jalview2XML().saveState(choice);
1563 } catch (OutOfMemoryError oom)
1565 new OOMWarning("Whilst saving current state to "
1566 + choice.getName(), oom);
1567 } catch (Exception ex)
1570 "Problems whilst trying to save to " + choice.getName(),
1572 JOptionPane.showMessageDialog(me, MessageManager.formatMessage(
1573 "label.error_whilst_saving_current_state_to",
1574 new Object[] { choice.getName() }), MessageManager
1575 .getString("label.couldnt_save_project"),
1576 JOptionPane.WARNING_MESSAGE);
1578 setProgressBar(null, choice.hashCode());
1584 private void setProjectFile(File choice)
1586 this.projectFile = choice;
1589 public File getProjectFile()
1591 return this.projectFile;
1601 public void loadState_actionPerformed(ActionEvent e)
1603 JalviewFileChooser chooser = new JalviewFileChooser(
1604 jalview.bin.Cache.getProperty("LAST_DIRECTORY"), new String[] {
1605 "jvp", "jar" }, new String[] { "Jalview Project",
1606 "Jalview Project (old)" }, "Jalview Project");
1607 chooser.setFileView(new JalviewFileView());
1608 chooser.setDialogTitle(MessageManager.getString("label.restore_state"));
1610 int value = chooser.showOpenDialog(this);
1612 if (value == JalviewFileChooser.APPROVE_OPTION)
1614 final File selectedFile = chooser.getSelectedFile();
1615 setProjectFile(selectedFile);
1616 final String choice = selectedFile.getAbsolutePath();
1617 jalview.bin.Cache.setProperty("LAST_DIRECTORY",
1618 selectedFile.getParent());
1619 new Thread(new Runnable()
1625 MessageManager.formatMessage(
1626 "label.loading_jalview_project",
1627 new Object[] { choice }), choice.hashCode());
1630 new Jalview2XML().loadJalviewAlign(choice);
1631 } catch (OutOfMemoryError oom)
1633 new OOMWarning("Whilst loading project from " + choice, oom);
1634 } catch (Exception ex)
1636 Cache.log.error("Problems whilst loading project from "
1638 JOptionPane.showMessageDialog(Desktop.desktop, MessageManager
1640 "label.error_whilst_loading_project_from",
1641 new Object[] { choice }), MessageManager
1642 .getString("label.couldnt_load_project"),
1643 JOptionPane.WARNING_MESSAGE);
1645 setProgressBar(null, choice.hashCode());
1652 public void inputSequence_actionPerformed(ActionEvent e)
1654 new SequenceFetcher(this);
1657 JPanel progressPanel;
1659 ArrayList<JPanel> fileLoadingPanels = new ArrayList<JPanel>();
1661 public void startLoading(final String fileName)
1663 if (fileLoadingCount == 0)
1665 fileLoadingPanels.add(addProgressPanel(MessageManager.formatMessage(
1666 "label.loading_file", new Object[] { fileName })));
1671 private JPanel addProgressPanel(String string)
1673 if (progressPanel == null)
1675 progressPanel = new JPanel(new GridLayout(1, 1));
1676 totalProgressCount = 0;
1677 instance.getContentPane().add(progressPanel, BorderLayout.SOUTH);
1679 JPanel thisprogress = new JPanel(new BorderLayout(10, 5));
1680 JProgressBar progressBar = new JProgressBar();
1681 progressBar.setIndeterminate(true);
1683 thisprogress.add(new JLabel(string), BorderLayout.WEST);
1685 thisprogress.add(progressBar, BorderLayout.CENTER);
1686 progressPanel.add(thisprogress);
1687 ((GridLayout) progressPanel.getLayout())
1688 .setRows(((GridLayout) progressPanel.getLayout()).getRows() + 1);
1689 ++totalProgressCount;
1690 instance.validate();
1691 return thisprogress;
1694 int totalProgressCount = 0;
1696 private void removeProgressPanel(JPanel progbar)
1698 if (progressPanel != null)
1700 synchronized (progressPanel)
1702 progressPanel.remove(progbar);
1703 GridLayout gl = (GridLayout) progressPanel.getLayout();
1704 gl.setRows(gl.getRows() - 1);
1705 if (--totalProgressCount < 1)
1707 this.getContentPane().remove(progressPanel);
1708 progressPanel = null;
1715 public void stopLoading()
1718 if (fileLoadingCount < 1)
1720 while (fileLoadingPanels.size() > 0)
1722 removeProgressPanel(fileLoadingPanels.remove(0));
1724 fileLoadingPanels.clear();
1725 fileLoadingCount = 0;
1730 public static int getViewCount(String alignmentId)
1732 AlignmentViewport[] aps = getViewports(alignmentId);
1733 return (aps == null) ? 0 : aps.length;
1738 * @param alignmentId
1739 * - if null, all sets are returned
1740 * @return all AlignmentPanels concerning the alignmentId sequence set
1742 public static AlignmentPanel[] getAlignmentPanels(String alignmentId)
1744 if (Desktop.desktop == null)
1746 // no frames created and in headless mode
1747 // TODO: verify that frames are recoverable when in headless mode
1750 List<AlignmentPanel> aps = new ArrayList<AlignmentPanel>();
1751 AlignFrame[] frames = getAlignFrames();
1756 for (AlignFrame af : frames)
1758 for (AlignmentPanel ap : af.alignPanels)
1760 if (alignmentId == null
1761 || alignmentId.equals(ap.av.getSequenceSetId()))
1767 if (aps.size() == 0)
1771 AlignmentPanel[] vap = aps.toArray(new AlignmentPanel[aps.size()]);
1776 * get all the viewports on an alignment.
1778 * @param sequenceSetId
1779 * unique alignment id (may be null - all viewports returned in that
1781 * @return all viewports on the alignment bound to sequenceSetId
1783 public static AlignmentViewport[] getViewports(String sequenceSetId)
1785 List<AlignmentViewport> viewp = new ArrayList<AlignmentViewport>();
1786 if (desktop != null)
1788 AlignFrame[] frames = Desktop.getAlignFrames();
1790 for (AlignFrame afr : frames)
1792 if (sequenceSetId == null
1793 || afr.getViewport().getSequenceSetId()
1794 .equals(sequenceSetId))
1796 if (afr.alignPanels != null)
1798 for (AlignmentPanel ap : afr.alignPanels)
1800 if (sequenceSetId == null
1801 || sequenceSetId.equals(ap.av.getSequenceSetId()))
1809 viewp.add(afr.getViewport());
1813 if (viewp.size() > 0)
1815 return viewp.toArray(new AlignmentViewport[viewp.size()]);
1822 * Explode the views in the given frame into separate AlignFrame
1826 public void explodeViews(AlignFrame af)
1828 int size = af.alignPanels.size();
1834 for (int i = 0; i < size; i++)
1836 AlignmentPanel ap = af.alignPanels.get(i);
1837 AlignFrame newaf = new AlignFrame(ap);
1840 * Restore the view's last exploded frame geometry if known. Multiple
1841 * views from one exploded frame share and restore the same (frame)
1842 * position and size.
1844 Rectangle geometry = ap.av.getExplodedGeometry();
1845 if (geometry != null)
1847 newaf.setBounds(geometry);
1850 ap.av.setGatherViewsHere(false);
1852 addInternalFrame(newaf, af.getTitle(), AlignFrame.DEFAULT_WIDTH,
1853 AlignFrame.DEFAULT_HEIGHT);
1856 af.alignPanels.clear();
1857 af.closeMenuItem_actionPerformed(true);
1862 * Gather expanded views (separate AlignFrame's) with the same sequence set
1863 * identifier back in to this frame as additional views, and close the
1864 * expanded views. Note the expanded frames may themselves have multiple
1865 * views. We take the lot.
1869 public void gatherViews(AlignFrame source)
1871 source.viewport.setGatherViewsHere(true);
1872 source.viewport.setExplodedGeometry(source.getBounds());
1873 JInternalFrame[] frames = desktop.getAllFrames();
1874 String viewId = source.viewport.getSequenceSetId();
1876 for (int t = 0; t < frames.length; t++)
1878 if (frames[t] instanceof AlignFrame && frames[t] != source)
1880 AlignFrame af = (AlignFrame) frames[t];
1881 boolean gatherThis = false;
1882 for (int a = 0; a < af.alignPanels.size(); a++)
1884 AlignmentPanel ap = af.alignPanels.get(a);
1885 if (viewId.equals(ap.av.getSequenceSetId()))
1888 ap.av.setGatherViewsHere(false);
1889 ap.av.setExplodedGeometry(af.getBounds());
1890 source.addAlignmentPanel(ap, false);
1896 af.alignPanels.clear();
1897 af.closeMenuItem_actionPerformed(true);
1904 jalview.gui.VamsasApplication v_client = null;
1907 public void vamsasImport_actionPerformed(ActionEvent e)
1909 if (v_client == null)
1911 // Load and try to start a session.
1912 JalviewFileChooser chooser = new JalviewFileChooser(
1913 jalview.bin.Cache.getProperty("LAST_DIRECTORY"));
1915 chooser.setFileView(new JalviewFileView());
1916 chooser.setDialogTitle(MessageManager
1917 .getString("label.open_saved_vamsas_session"));
1918 chooser.setToolTipText(MessageManager
1919 .getString("label.select_vamsas_session_opened_as_new_vamsas_session"));
1921 int value = chooser.showOpenDialog(this);
1923 if (value == JalviewFileChooser.APPROVE_OPTION)
1925 String fle = chooser.getSelectedFile().toString();
1926 if (!vamsasImport(chooser.getSelectedFile()))
1929 .showInternalMessageDialog(
1931 MessageManager.formatMessage(
1932 "label.couldnt_import_as_vamsas_session",
1933 new Object[] { fle }),
1935 .getString("label.vamsas_document_import_failed"),
1936 JOptionPane.ERROR_MESSAGE);
1942 jalview.bin.Cache.log
1943 .error("Implementation error - load session from a running session is not supported.");
1948 * import file into a new vamsas session (uses jalview.gui.VamsasApplication)
1951 * @return true if import was a success and a session was started.
1953 public boolean vamsasImport(URL url)
1955 // TODO: create progress bar
1956 if (v_client != null)
1959 jalview.bin.Cache.log
1960 .error("Implementation error - load session from a running session is not supported.");
1966 // copy the URL content to a temporary local file
1967 // TODO: be a bit cleverer here with nio (?!)
1968 File file = File.createTempFile("vdocfromurl", ".vdj");
1969 FileOutputStream fos = new FileOutputStream(file);
1970 BufferedInputStream bis = new BufferedInputStream(url.openStream());
1971 byte[] buffer = new byte[2048];
1973 while ((ln = bis.read(buffer)) > -1)
1975 fos.write(buffer, 0, ln);
1979 v_client = new jalview.gui.VamsasApplication(this, file,
1980 url.toExternalForm());
1981 } catch (Exception ex)
1983 jalview.bin.Cache.log.error(
1984 "Failed to create new vamsas session from contents of URL "
1988 setupVamsasConnectedGui();
1989 v_client.initial_update(); // TODO: thread ?
1990 return v_client.inSession();
1994 * import file into a new vamsas session (uses jalview.gui.VamsasApplication)
1997 * @return true if import was a success and a session was started.
1999 public boolean vamsasImport(File file)
2001 if (v_client != null)
2004 jalview.bin.Cache.log
2005 .error("Implementation error - load session from a running session is not supported.");
2009 setProgressBar(MessageManager.formatMessage(
2010 "status.importing_vamsas_session_from",
2011 new Object[] { file.getName() }), file.hashCode());
2014 v_client = new jalview.gui.VamsasApplication(this, file, null);
2015 } catch (Exception ex)
2017 setProgressBar(MessageManager.formatMessage(
2018 "status.importing_vamsas_session_from",
2019 new Object[] { file.getName() }), file.hashCode());
2020 jalview.bin.Cache.log.error(
2021 "New vamsas session from existing session file failed:", ex);
2024 setupVamsasConnectedGui();
2025 v_client.initial_update(); // TODO: thread ?
2026 setProgressBar(MessageManager.formatMessage(
2027 "status.importing_vamsas_session_from",
2028 new Object[] { file.getName() }), file.hashCode());
2029 return v_client.inSession();
2032 public boolean joinVamsasSession(String mysesid)
2034 if (v_client != null)
2038 .getString("error.try_join_vamsas_session_another"));
2040 if (mysesid == null)
2043 MessageManager.getString("error.invalid_vamsas_session_id"));
2045 v_client = new VamsasApplication(this, mysesid);
2046 setupVamsasConnectedGui();
2047 v_client.initial_update();
2048 return (v_client.inSession());
2052 public void vamsasStart_actionPerformed(ActionEvent e)
2054 if (v_client == null)
2057 // we just start a default session for moment.
2059 * JalviewFileChooser chooser = new JalviewFileChooser(jalview.bin.Cache.
2060 * getProperty("LAST_DIRECTORY"));
2062 * chooser.setFileView(new JalviewFileView());
2063 * chooser.setDialogTitle("Load Vamsas file");
2064 * chooser.setToolTipText("Import");
2066 * int value = chooser.showOpenDialog(this);
2068 * if (value == JalviewFileChooser.APPROVE_OPTION) { v_client = new
2069 * jalview.gui.VamsasApplication(this, chooser.getSelectedFile());
2071 v_client = new VamsasApplication(this);
2072 setupVamsasConnectedGui();
2073 v_client.initial_update(); // TODO: thread ?
2077 // store current data in session.
2078 v_client.push_update(); // TODO: thread
2082 protected void setupVamsasConnectedGui()
2084 vamsasStart.setText(MessageManager.getString("label.session_update"));
2085 vamsasSave.setVisible(true);
2086 vamsasStop.setVisible(true);
2087 vamsasImport.setVisible(false); // Document import to existing session is
2088 // not possible for vamsas-client-1.0.
2091 protected void setupVamsasDisconnectedGui()
2093 vamsasSave.setVisible(false);
2094 vamsasStop.setVisible(false);
2095 vamsasImport.setVisible(true);
2096 vamsasStart.setText(MessageManager
2097 .getString("label.new_vamsas_session"));
2101 public void vamsasStop_actionPerformed(ActionEvent e)
2103 if (v_client != null)
2105 v_client.end_session();
2107 setupVamsasDisconnectedGui();
2111 protected void buildVamsasStMenu()
2113 if (v_client == null)
2115 String[] sess = null;
2118 sess = VamsasApplication.getSessionList();
2119 } catch (Exception e)
2121 jalview.bin.Cache.log.warn(
2122 "Problem getting current sessions list.", e);
2127 jalview.bin.Cache.log.debug("Got current sessions list: "
2128 + sess.length + " entries.");
2129 VamsasStMenu.removeAll();
2130 for (int i = 0; i < sess.length; i++)
2132 JMenuItem sessit = new JMenuItem();
2133 sessit.setText(sess[i]);
2134 sessit.setToolTipText(MessageManager.formatMessage(
2135 "label.connect_to_session", new Object[] { sess[i] }));
2136 final Desktop dsktp = this;
2137 final String mysesid = sess[i];
2138 sessit.addActionListener(new ActionListener()
2142 public void actionPerformed(ActionEvent e)
2144 if (dsktp.v_client == null)
2146 Thread rthr = new Thread(new Runnable()
2152 dsktp.v_client = new VamsasApplication(dsktp, mysesid);
2153 dsktp.setupVamsasConnectedGui();
2154 dsktp.v_client.initial_update();
2162 VamsasStMenu.add(sessit);
2164 // don't show an empty menu.
2165 VamsasStMenu.setVisible(sess.length > 0);
2170 jalview.bin.Cache.log.debug("No current vamsas sessions.");
2171 VamsasStMenu.removeAll();
2172 VamsasStMenu.setVisible(false);
2177 // Not interested in the content. Just hide ourselves.
2178 VamsasStMenu.setVisible(false);
2183 public void vamsasSave_actionPerformed(ActionEvent e)
2185 if (v_client != null)
2187 JalviewFileChooser chooser = new JalviewFileChooser(
2188 jalview.bin.Cache.getProperty("LAST_DIRECTORY"), new String[]
2189 { "vdj" }, // TODO: VAMSAS DOCUMENT EXTENSION is VDJ
2190 new String[] { "Vamsas Document" }, "Vamsas Document");
2192 chooser.setFileView(new JalviewFileView());
2193 chooser.setDialogTitle(MessageManager
2194 .getString("label.save_vamsas_document_archive"));
2196 int value = chooser.showSaveDialog(this);
2198 if (value == JalviewFileChooser.APPROVE_OPTION)
2200 java.io.File choice = chooser.getSelectedFile();
2201 JPanel progpanel = addProgressPanel(MessageManager.formatMessage(
2202 "label.saving_vamsas_doc",
2203 new Object[] { choice.getName() }));
2204 jalview.bin.Cache.setProperty("LAST_DIRECTORY", choice.getParent());
2205 String warnmsg = null;
2206 String warnttl = null;
2209 v_client.vclient.storeDocument(choice);
2212 warnttl = "Serious Problem saving Vamsas Document";
2213 warnmsg = ex.toString();
2214 jalview.bin.Cache.log.error("Error Whilst saving document to "
2217 } catch (Exception ex)
2219 warnttl = "Problem saving Vamsas Document.";
2220 warnmsg = ex.toString();
2221 jalview.bin.Cache.log.warn("Exception Whilst saving document to "
2225 removeProgressPanel(progpanel);
2226 if (warnmsg != null)
2228 JOptionPane.showInternalMessageDialog(Desktop.desktop,
2230 warnmsg, warnttl, JOptionPane.ERROR_MESSAGE);
2236 JPanel vamUpdate = null;
2239 * hide vamsas user gui bits when a vamsas document event is being handled.
2242 * true to hide gui, false to reveal gui
2244 public void setVamsasUpdate(boolean b)
2246 jalview.bin.Cache.log.debug("Setting gui for Vamsas update "
2247 + (b ? "in progress" : "finished"));
2249 if (vamUpdate != null)
2251 this.removeProgressPanel(vamUpdate);
2255 vamUpdate = this.addProgressPanel(MessageManager
2256 .getString("label.updating_vamsas_session"));
2258 vamsasStart.setVisible(!b);
2259 vamsasStop.setVisible(!b);
2260 vamsasSave.setVisible(!b);
2263 public JInternalFrame[] getAllFrames()
2265 return desktop.getAllFrames();
2269 * Checks the given url to see if it gives a response indicating that the user
2270 * should be informed of a new questionnaire.
2274 public void checkForQuestionnaire(String url)
2276 UserQuestionnaireCheck jvq = new UserQuestionnaireCheck(url);
2277 // javax.swing.SwingUtilities.invokeLater(jvq);
2278 new Thread(jvq).start();
2282 * Proxy class for JDesktopPane which optionally displays the current memory
2283 * usage and highlights the desktop area with a red bar if free memory runs
2288 public class MyDesktopPane extends JDesktopPane implements Runnable
2291 private static final float ONE_MB = 1048576f;
2293 boolean showMemoryUsage = false;
2297 java.text.NumberFormat df;
2299 float maxMemory, allocatedMemory, freeMemory, totalFreeMemory,
2302 public MyDesktopPane(boolean showMemoryUsage)
2304 showMemoryUsage(showMemoryUsage);
2307 public void showMemoryUsage(boolean showMemory)
2309 this.showMemoryUsage = showMemory;
2312 Thread worker = new Thread(this);
2317 public boolean isShowMemoryUsage()
2319 return showMemoryUsage;
2325 df = java.text.NumberFormat.getNumberInstance();
2326 df.setMaximumFractionDigits(2);
2327 runtime = Runtime.getRuntime();
2329 while (showMemoryUsage)
2333 maxMemory = runtime.maxMemory() / ONE_MB;
2334 allocatedMemory = runtime.totalMemory() / ONE_MB;
2335 freeMemory = runtime.freeMemory() / ONE_MB;
2336 totalFreeMemory = freeMemory + (maxMemory - allocatedMemory);
2338 percentUsage = (totalFreeMemory / maxMemory) * 100;
2340 // if (percentUsage < 20)
2342 // border1 = BorderFactory.createMatteBorder(12, 12, 12, 12,
2344 // instance.set.setBorder(border1);
2347 // sleep after showing usage
2349 } catch (Exception ex)
2351 ex.printStackTrace();
2357 public void paintComponent(Graphics g)
2359 if (showMemoryUsage && g != null && df != null)
2361 if (percentUsage < 20)
2363 g.setColor(Color.red);
2365 FontMetrics fm = g.getFontMetrics();
2368 g.drawString(MessageManager.formatMessage(
2369 "label.memory_stats",
2370 new Object[] { df.format(totalFreeMemory),
2371 df.format(maxMemory), df.format(percentUsage) }), 10,
2372 getHeight() - fm.getHeight());
2379 * fixes stacking order after a modal dialog to ensure windows that should be
2380 * on top actually are
2382 public void relayerWindows()
2387 protected JMenuItem groovyShell;
2390 * Accessor method to quickly get all the AlignmentFrames loaded.
2392 * @return an array of AlignFrame, or null if none found
2394 public static AlignFrame[] getAlignFrames()
2396 if (Jalview.isHeadlessMode())
2398 // Desktop.desktop is null in headless mode
2399 return new AlignFrame[] { Jalview.currentAlignFrame };
2402 JInternalFrame[] frames = Desktop.desktop.getAllFrames();
2408 List<AlignFrame> avp = new ArrayList<AlignFrame>();
2410 for (int i = frames.length - 1; i > -1; i--)
2412 if (frames[i] instanceof AlignFrame)
2414 avp.add((AlignFrame) frames[i]);
2416 else if (frames[i] instanceof SplitFrame)
2419 * Also check for a split frame containing an AlignFrame
2421 GSplitFrame sf = (GSplitFrame) frames[i];
2422 if (sf.getTopFrame() instanceof AlignFrame)
2424 avp.add((AlignFrame) sf.getTopFrame());
2426 if (sf.getBottomFrame() instanceof AlignFrame)
2428 avp.add((AlignFrame) sf.getBottomFrame());
2432 if (avp.size() == 0)
2436 AlignFrame afs[] = avp.toArray(new AlignFrame[avp.size()]);
2441 * Returns an array of any AppJmol frames in the Desktop (or null if none).
2445 public GStructureViewer[] getJmols()
2447 JInternalFrame[] frames = Desktop.desktop.getAllFrames();
2453 List<GStructureViewer> avp = new ArrayList<GStructureViewer>();
2455 for (int i = frames.length - 1; i > -1; i--)
2457 if (frames[i] instanceof AppJmol)
2459 GStructureViewer af = (GStructureViewer) frames[i];
2463 if (avp.size() == 0)
2467 GStructureViewer afs[] = avp.toArray(new GStructureViewer[avp.size()]);
2472 * Add Groovy Support to Jalview
2474 public void groovyShell_actionPerformed()
2478 openGroovyConsole();
2479 } catch (Exception ex)
2481 jalview.bin.Cache.log.error("Groovy Shell Creation failed.", ex);
2482 JOptionPane.showInternalMessageDialog(Desktop.desktop,
2484 MessageManager.getString("label.couldnt_create_groovy_shell"),
2485 MessageManager.getString("label.groovy_support_failed"),
2486 JOptionPane.ERROR_MESSAGE);
2491 * Open the Groovy console
2493 void openGroovyConsole()
2495 if (groovyConsole == null)
2497 groovyConsole = new groovy.ui.Console();
2498 groovyConsole.setVariable("Jalview", this);
2499 groovyConsole.run();
2502 * We allow only one console at a time, so that AlignFrame menu option
2503 * 'Calculate | Run Groovy script' is unambiguous.
2504 * Disable 'Groovy Console', and enable 'Run script', when the console is
2505 * opened, and the reverse when it is closed
2507 Window window = (Window) groovyConsole.getFrame();
2508 window.addWindowListener(new WindowAdapter()
2511 public void windowClosed(WindowEvent e)
2514 * rebind CMD-Q from Groovy Console to Jalview Quit
2517 enableExecuteGroovy(false);
2523 * show Groovy console window (after close and reopen)
2525 ((Window) groovyConsole.getFrame()).setVisible(true);
2528 * if we got this far, enable 'Run Groovy' in AlignFrame menus
2529 * and disable opening a second console
2531 enableExecuteGroovy(true);
2535 * Bind Ctrl/Cmd-Q to Quit - for reset as Groovy Console takes over this
2536 * binding when opened
2538 protected void addQuitHandler()
2540 getRootPane().getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(
2541 KeyStroke.getKeyStroke(KeyEvent.VK_Q, Toolkit
2542 .getDefaultToolkit().getMenuShortcutKeyMask()),
2544 getRootPane().getActionMap().put("Quit", new AbstractAction()
2547 public void actionPerformed(ActionEvent e)
2555 * Enable or disable 'Run Groovy script' in AlignFrame calculate menus
2558 * true if Groovy console is open
2560 public void enableExecuteGroovy(boolean enabled)
2563 * disable opening a second Groovy console
2564 * (or re-enable when the console is closed)
2566 groovyShell.setEnabled(!enabled);
2568 AlignFrame[] alignFrames = getAlignFrames();
2569 if (alignFrames != null)
2571 for (AlignFrame af : alignFrames)
2573 af.setGroovyEnabled(enabled);
2579 * Progress bars managed by the IProgressIndicator method.
2581 private Hashtable<Long, JPanel> progressBars;
2583 private Hashtable<Long, IProgressIndicatorHandler> progressBarHandlers;
2588 * @see jalview.gui.IProgressIndicator#setProgressBar(java.lang.String, long)
2591 public void setProgressBar(String message, long id)
2593 if (progressBars == null)
2595 progressBars = new Hashtable<Long, JPanel>();
2596 progressBarHandlers = new Hashtable<Long, IProgressIndicatorHandler>();
2599 if (progressBars.get(new Long(id)) != null)
2601 JPanel panel = progressBars.remove(new Long(id));
2602 if (progressBarHandlers.contains(new Long(id)))
2604 progressBarHandlers.remove(new Long(id));
2606 removeProgressPanel(panel);
2610 progressBars.put(new Long(id), addProgressPanel(message));
2617 * @see jalview.gui.IProgressIndicator#registerHandler(long,
2618 * jalview.gui.IProgressIndicatorHandler)
2621 public void registerHandler(final long id,
2622 final IProgressIndicatorHandler handler)
2624 if (progressBarHandlers == null
2625 || !progressBars.containsKey(new Long(id)))
2629 .getString("error.call_setprogressbar_before_registering_handler"));
2631 progressBarHandlers.put(new Long(id), handler);
2632 final JPanel progressPanel = progressBars.get(new Long(id));
2633 if (handler.canCancel())
2635 JButton cancel = new JButton(
2636 MessageManager.getString("action.cancel"));
2637 final IProgressIndicator us = this;
2638 cancel.addActionListener(new ActionListener()
2642 public void actionPerformed(ActionEvent e)
2644 handler.cancelActivity(id);
2645 us.setProgressBar(MessageManager.formatMessage(
2646 "label.cancelled_params",
2647 new Object[] { ((JLabel) progressPanel.getComponent(0))
2651 progressPanel.add(cancel, BorderLayout.EAST);
2657 * @return true if any progress bars are still active
2660 public boolean operationInProgress()
2662 if (progressBars != null && progressBars.size() > 0)
2670 * This will return the first AlignFrame holding the given viewport instance.
2671 * It will break if there are more than one AlignFrames viewing a particular
2675 * @return alignFrame for viewport
2677 public static AlignFrame getAlignFrameFor(AlignViewportI viewport)
2679 if (desktop != null)
2681 AlignmentPanel[] aps = getAlignmentPanels(viewport.getSequenceSetId());
2682 for (int panel = 0; aps != null && panel < aps.length; panel++)
2684 if (aps[panel] != null && aps[panel].av == viewport)
2686 return aps[panel].alignFrame;
2693 public VamsasApplication getVamsasApplication()
2700 * flag set if jalview GUI is being operated programmatically
2702 private boolean inBatchMode = false;
2705 * check if jalview GUI is being operated programmatically
2707 * @return inBatchMode
2709 public boolean isInBatchMode()
2715 * set flag if jalview GUI is being operated programmatically
2717 * @param inBatchMode
2719 public void setInBatchMode(boolean inBatchMode)
2721 this.inBatchMode = inBatchMode;
2724 public void startServiceDiscovery()
2726 startServiceDiscovery(false);
2729 public void startServiceDiscovery(boolean blocking)
2731 boolean alive = true;
2732 Thread t0 = null, t1 = null, t2 = null;
2733 // JAL-940 - JALVIEW 1 services are now being EOLed as of JABA 2.1 release
2736 // todo: changesupport handlers need to be transferred
2737 if (discoverer == null)
2739 discoverer = new jalview.ws.jws1.Discoverer();
2740 // register PCS handler for desktop.
2741 discoverer.addPropertyChangeListener(changeSupport);
2743 // JAL-940 - disabled JWS1 service configuration - always start discoverer
2744 // until we phase out completely
2745 (t0 = new Thread(discoverer)).start();
2748 if (Cache.getDefault("SHOW_JWS2_SERVICES", true))
2750 if (jalview.ws.jws2.Jws2Discoverer.getDiscoverer().isRunning())
2752 jalview.ws.jws2.Jws2Discoverer.getDiscoverer().setAborted(true);
2754 t2 = jalview.ws.jws2.Jws2Discoverer.getDiscoverer().startDiscoverer(
2760 // TODO: do rest service discovery
2769 } catch (Exception e)
2772 alive = (t1 != null && t1.isAlive())
2773 || (t2 != null && t2.isAlive())
2774 || (t3 != null && t3.isAlive())
2775 || (t0 != null && t0.isAlive());
2781 * called to check if the service discovery process completed successfully.
2785 protected void JalviewServicesChanged(PropertyChangeEvent evt)
2787 if (evt.getNewValue() == null || evt.getNewValue() instanceof Vector)
2789 final String ermsg = jalview.ws.jws2.Jws2Discoverer.getDiscoverer()
2790 .getErrorMessages();
2793 if (Cache.getDefault("SHOW_WSDISCOVERY_ERRORS", true))
2795 if (serviceChangedDialog == null)
2797 // only run if we aren't already displaying one of these.
2798 addDialogThread(serviceChangedDialog = new Runnable()
2805 * JalviewDialog jd =new JalviewDialog() {
2807 * @Override protected void cancelPressed() { // TODO
2808 * Auto-generated method stub
2810 * }@Override protected void okPressed() { // TODO
2811 * Auto-generated method stub
2813 * }@Override protected void raiseClosed() { // TODO
2814 * Auto-generated method stub
2816 * } }; jd.initDialogFrame(new
2817 * JLabel("<html><table width=\"450\"><tr><td>" + ermsg +
2818 * "<br/>It may be that you have invalid JABA URLs in your web service preferences,"
2819 * + " or mis-configured HTTP proxy settings.<br/>" +
2820 * "Check the <em>Connections</em> and <em>Web services</em> tab of the"
2822 * " Tools->Preferences dialog box to change them.</td></tr></table></html>"
2823 * ), true, true, "Web Service Configuration Problem", 450,
2826 * jd.waitForInput();
2832 "<html><table width=\"450\"><tr><td>"
2834 + "</td></tr></table>"
2835 + "<p>It may be that you have invalid JABA URLs<br/>in your web service preferences,"
2836 + "<br>or as a command-line argument, or mis-configured HTTP proxy settings.</p>"
2837 + "<p>Check the <em>Connections</em> and <em>Web services</em> tab<br/>of the"
2838 + " Tools->Preferences dialog box to change them.</p></html>"),
2839 "Web Service Configuration Problem",
2840 JOptionPane.DEFAULT_OPTION,
2841 JOptionPane.ERROR_MESSAGE);
2842 serviceChangedDialog = null;
2851 .error("Errors reported by JABA discovery service. Check web services preferences.\n"
2858 private Runnable serviceChangedDialog = null;
2861 * start a thread to open a URL in the configured browser. Pops up a warning
2862 * dialog to the user if there is an exception when calling out to the browser
2867 public static void showUrl(final String url)
2869 showUrl(url, Desktop.instance);
2873 * Like showUrl but allows progress handler to be specified
2877 * (null) or object implementing IProgressIndicator
2879 public static void showUrl(final String url,
2880 final IProgressIndicator progress)
2882 new Thread(new Runnable()
2889 if (progress != null)
2891 progress.setProgressBar(MessageManager.formatMessage(
2892 "status.opening_params", new Object[] { url }), this
2895 jalview.util.BrowserLauncher.openURL(url);
2896 } catch (Exception ex)
2898 JOptionPane.showInternalMessageDialog(Desktop.desktop,
2900 .getString("label.web_browser_not_found_unix"),
2901 MessageManager.getString("label.web_browser_not_found"),
2902 JOptionPane.WARNING_MESSAGE);
2904 ex.printStackTrace();
2906 if (progress != null)
2908 progress.setProgressBar(null, this.hashCode());
2914 public static WsParamSetManager wsparamManager = null;
2916 public static ParamManager getUserParameterStore()
2918 if (wsparamManager == null)
2920 wsparamManager = new WsParamSetManager();
2922 return wsparamManager;
2926 * static hyperlink handler proxy method for use by Jalview's internal windows
2930 public static void hyperlinkUpdate(HyperlinkEvent e)
2932 if (e.getEventType() == EventType.ACTIVATED)
2937 url = e.getURL().toString();
2938 Desktop.showUrl(url);
2939 } catch (Exception x)
2943 if (Cache.log != null)
2945 Cache.log.error("Couldn't handle string " + url + " as a URL.");
2949 System.err.println("Couldn't handle string " + url
2953 // ignore any exceptions due to dud links.
2960 * single thread that handles display of dialogs to user.
2962 ExecutorService dialogExecutor = Executors.newSingleThreadExecutor();
2965 * flag indicating if dialogExecutor should try to acquire a permit
2967 private volatile boolean dialogPause = true;
2972 private java.util.concurrent.Semaphore block = new Semaphore(0);
2974 private static groovy.ui.Console groovyConsole;
2977 * add another dialog thread to the queue
2981 public void addDialogThread(final Runnable prompter)
2983 dialogExecutor.submit(new Runnable()
2993 } catch (InterruptedException x)
2998 if (instance == null)
3004 SwingUtilities.invokeAndWait(prompter);
3005 } catch (Exception q)
3007 Cache.log.warn("Unexpected Exception in dialog thread.", q);
3013 public void startDialogQueue()
3015 // set the flag so we don't pause waiting for another permit and semaphore
3016 // the current task to begin
3017 dialogPause = false;
3022 protected void snapShotWindow_actionPerformed(ActionEvent e)
3026 ImageMaker im = new jalview.util.ImageMaker(this, ImageMaker.TYPE.EPS,
3027 "View of Desktop", getWidth(), getHeight(), of = new File(
3028 "Jalview_snapshot" + System.currentTimeMillis()
3029 + ".eps"), "View of desktop", null, 0, false);
3032 paintAll(im.getGraphics());
3034 } catch (Exception q)
3036 Cache.log.error("Couldn't write snapshot to " + of.getAbsolutePath(),
3040 Cache.log.info("Successfully written snapshot to file "
3041 + of.getAbsolutePath());
3045 * Explode the views in the given SplitFrame into separate SplitFrame windows.
3046 * This respects (remembers) any previous 'exploded geometry' i.e. the size
3047 * and location last time the view was expanded (if any). However it does not
3048 * remember the split pane divider location - this is set to match the
3049 * 'exploding' frame.
3053 public void explodeViews(SplitFrame sf)
3055 AlignFrame oldTopFrame = (AlignFrame) sf.getTopFrame();
3056 AlignFrame oldBottomFrame = (AlignFrame) sf.getBottomFrame();
3057 List<? extends AlignmentViewPanel> topPanels = oldTopFrame
3059 List<? extends AlignmentViewPanel> bottomPanels = oldBottomFrame
3061 int viewCount = topPanels.size();
3068 * Processing in reverse order works, forwards order leaves the first panels
3069 * not visible. I don't know why!
3071 for (int i = viewCount - 1; i >= 0; i--)
3074 * Make new top and bottom frames. These take over the respective
3075 * AlignmentPanel objects, including their AlignmentViewports, so the
3076 * cdna/protein relationships between the viewports is carried over to the
3079 * explodedGeometry holds the (x, y) position of the previously exploded
3080 * SplitFrame, and the (width, height) of the AlignFrame component
3082 AlignmentPanel topPanel = (AlignmentPanel) topPanels.get(i);
3083 AlignFrame newTopFrame = new AlignFrame(topPanel);
3084 newTopFrame.setSize(oldTopFrame.getSize());
3085 newTopFrame.setVisible(true);
3086 Rectangle geometry = ((AlignViewport) topPanel.getAlignViewport())
3087 .getExplodedGeometry();
3088 if (geometry != null)
3090 newTopFrame.setSize(geometry.getSize());
3093 AlignmentPanel bottomPanel = (AlignmentPanel) bottomPanels.get(i);
3094 AlignFrame newBottomFrame = new AlignFrame(bottomPanel);
3095 newBottomFrame.setSize(oldBottomFrame.getSize());
3096 newBottomFrame.setVisible(true);
3097 geometry = ((AlignViewport) bottomPanel.getAlignViewport())
3098 .getExplodedGeometry();
3099 if (geometry != null)
3101 newBottomFrame.setSize(geometry.getSize());
3104 topPanel.av.setGatherViewsHere(false);
3105 bottomPanel.av.setGatherViewsHere(false);
3106 JInternalFrame splitFrame = new SplitFrame(newTopFrame,
3108 if (geometry != null)
3110 splitFrame.setLocation(geometry.getLocation());
3112 Desktop.addInternalFrame(splitFrame, sf.getTitle(), -1, -1);
3116 * Clear references to the panels (now relocated in the new SplitFrames)
3117 * before closing the old SplitFrame.
3120 bottomPanels.clear();
3125 * Gather expanded split frames, sharing the same pairs of sequence set ids,
3126 * back into the given SplitFrame as additional views. Note that the gathered
3127 * frames may themselves have multiple views.
3131 public void gatherViews(GSplitFrame source)
3134 * special handling of explodedGeometry for a view within a SplitFrame: - it
3135 * holds the (x, y) position of the enclosing SplitFrame, and the (width,
3136 * height) of the AlignFrame component
3138 AlignFrame myTopFrame = (AlignFrame) source.getTopFrame();
3139 AlignFrame myBottomFrame = (AlignFrame) source.getBottomFrame();
3140 myTopFrame.viewport.setExplodedGeometry(new Rectangle(source.getX(),
3141 source.getY(), myTopFrame.getWidth(), myTopFrame.getHeight()));
3142 myBottomFrame.viewport.setExplodedGeometry(new Rectangle(source.getX(),
3143 source.getY(), myBottomFrame.getWidth(), myBottomFrame
3145 myTopFrame.viewport.setGatherViewsHere(true);
3146 myBottomFrame.viewport.setGatherViewsHere(true);
3147 String topViewId = myTopFrame.viewport.getSequenceSetId();
3148 String bottomViewId = myBottomFrame.viewport.getSequenceSetId();
3150 JInternalFrame[] frames = desktop.getAllFrames();
3151 for (JInternalFrame frame : frames)
3153 if (frame instanceof SplitFrame && frame != source)
3155 SplitFrame sf = (SplitFrame) frame;
3156 AlignFrame topFrame = (AlignFrame) sf.getTopFrame();
3157 AlignFrame bottomFrame = (AlignFrame) sf.getBottomFrame();
3158 boolean gatherThis = false;
3159 for (int a = 0; a < topFrame.alignPanels.size(); a++)
3161 AlignmentPanel topPanel = topFrame.alignPanels.get(a);
3162 AlignmentPanel bottomPanel = bottomFrame.alignPanels.get(a);
3163 if (topViewId.equals(topPanel.av.getSequenceSetId())
3164 && bottomViewId.equals(bottomPanel.av.getSequenceSetId()))
3167 topPanel.av.setGatherViewsHere(false);
3168 bottomPanel.av.setGatherViewsHere(false);
3169 topPanel.av.setExplodedGeometry(new Rectangle(sf.getLocation(),
3170 topFrame.getSize()));
3171 bottomPanel.av.setExplodedGeometry(new Rectangle(sf
3172 .getLocation(), bottomFrame.getSize()));
3173 myTopFrame.addAlignmentPanel(topPanel, false);
3174 myBottomFrame.addAlignmentPanel(bottomPanel, false);
3180 topFrame.getAlignPanels().clear();
3181 bottomFrame.getAlignPanels().clear();
3188 * The dust settles...give focus to the tab we did this from.
3190 myTopFrame.setDisplayedView(myTopFrame.alignPanel);
3193 public static groovy.ui.Console getGroovyConsole()
3195 return groovyConsole;
3198 public static void transferFromDropTarget(List<String> files,
3199 List<DataSourceType> protocols, DropTargetDropEvent evt,
3204 DataFlavor uriListFlavor = new DataFlavor(
3205 "text/uri-list;class=java.lang.String");
3206 if (t.isDataFlavorSupported(DataFlavor.javaFileListFlavor))
3208 // Works on Windows and MacOSX
3209 Cache.log.debug("Drop handled as javaFileListFlavor");
3210 evt.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE);
3211 for (Object file : (List) t
3212 .getTransferData(DataFlavor.javaFileListFlavor))
3214 files.add(((File)file).toString());
3215 protocols.add(DataSourceType.FILE);
3220 // Unix like behaviour
3221 boolean added = false;
3223 if (t.isDataFlavorSupported(uriListFlavor))
3225 Cache.log.debug("Drop handled as uriListFlavor");
3226 // This is used by Unix drag system
3227 evt.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE);
3228 data = (String) t.getTransferData(uriListFlavor);
3232 // fallback to text: workaround - on OSX where there's a JVM bug
3233 Cache.log.debug("standard URIListFlavor failed. Trying text");
3234 // try text fallback
3235 data = (String) t.getTransferData(new DataFlavor(
3236 "text/plain;class=java.lang.String"));
3237 if (Cache.log.isDebugEnabled())
3239 Cache.log.debug("fallback returned " + data);
3242 while (protocols.size() < files.size())
3244 Cache.log.debug("Adding missing FILE protocol for "
3245 + files.get(protocols.size()));
3246 protocols.add(DataSourceType.FILE);
3248 for (java.util.StringTokenizer st = new java.util.StringTokenizer(
3249 data, "\r\n"); st.hasMoreTokens();)
3252 String s = st.nextToken();
3253 if (s.startsWith("#"))
3255 // the line is a comment (as per the RFC 2483)
3258 java.net.URI uri = new java.net.URI(s);
3259 if (uri.getScheme().toLowerCase().startsWith("http"))
3261 protocols.add(DataSourceType.URL);
3262 files.add(uri.toString());
3266 // otherwise preserve old behaviour: catch all for file objects
3267 java.io.File file = new java.io.File(uri);
3268 protocols.add(DataSourceType.FILE);
3269 files.add(file.toString());
3272 if (Cache.log.isDebugEnabled())
3274 if (data == null || !added)
3277 .debug("Couldn't resolve drop data. Here are the supported flavors:");
3278 for (DataFlavor fl : t.getTransferDataFlavors())
3280 Cache.log.debug("Supported transfer dataflavor: "
3282 evt.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE);
3283 Object df = t.getTransferData(fl);
3286 Cache.log.debug("Retrieves: " + df);
3290 Cache.log.debug("Retrieved nothing");