2 * Jalview - A Sequence Alignment Editor and Viewer
3 * Copyright (C) 2007 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Softwarechang
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
26 import java.awt.datatransfer.*;
27 import java.awt.dnd.*;
28 import java.awt.event.*;
29 import java.awt.print.*;
31 import javax.swing.event.MenuEvent;
33 import jalview.analysis.*;
34 import jalview.commands.*;
35 import jalview.datamodel.*;
37 import jalview.jbgui.*;
38 import jalview.schemes.*;
47 public class AlignFrame
48 extends GAlignFrame implements DropTargetListener
51 public static final int DEFAULT_WIDTH = 700;
54 public static final int DEFAULT_HEIGHT = 500;
55 public AlignmentPanel alignPanel;
57 AlignViewport viewport;
59 Vector alignPanels = new Vector();
63 * Last format used to load or save alignments in this window
65 String currentFileFormat = null;
67 * Current filename for this alignment
69 String fileName = null;
73 * Creates a new AlignFrame object.
75 * @param al DOCUMENT ME!
77 public AlignFrame(AlignmentI al, int width, int height)
79 this(al, null, width, height);
84 * new alignment window with hidden columns
85 * @param al AlignmentI
86 * @param hiddenColumns ColumnSelection or null
88 public AlignFrame(AlignmentI al, ColumnSelection hiddenColumns,
89 int width, int height)
91 this.setSize(width, height);
92 viewport = new AlignViewport(al, hiddenColumns);
94 alignPanel = new AlignmentPanel(this, viewport);
96 if(al.getDataset()==null)
101 addAlignmentPanel(alignPanel, true);
106 * Make a new AlignFrame from exisiting alignmentPanels
107 * @param ap AlignmentPanel
108 * @param av AlignViewport
110 public AlignFrame(AlignmentPanel ap)
114 addAlignmentPanel(ap, false);
120 if (viewport.conservation == null)
122 BLOSUM62Colour.setEnabled(false);
123 conservationMenuItem.setEnabled(false);
124 modifyConservation.setEnabled(false);
125 // PIDColour.setEnabled(false);
126 // abovePIDThreshold.setEnabled(false);
127 // modifyPID.setEnabled(false);
130 String sortby = jalview.bin.Cache.getDefault("SORT_ALIGNMENT", "No sort");
132 if (sortby.equals("Id"))
134 sortIDMenuItem_actionPerformed(null);
136 else if (sortby.equals("Pairwise Identity"))
138 sortPairwiseMenuItem_actionPerformed(null);
141 if (Desktop.desktop != null)
143 this.setDropTarget(new java.awt.dnd.DropTarget(this, this));
144 addServiceListeners();
145 setGUINucleotide(viewport.alignment.isNucleotide());
148 setMenusFromViewport(viewport);
149 buildSortByAnnotationScoresMenu();
150 if (viewport.wrapAlignment)
152 wrapMenuItem_actionPerformed(null);
155 if (jalview.bin.Cache.getDefault("SHOW_OVERVIEW",false))
157 this.overviewMenuItem_actionPerformed(null);
164 public void setFileName(String file, String format)
167 currentFileFormat = format;
168 reload.setEnabled(true);
171 void addKeyListener()
173 addKeyListener(new KeyAdapter()
175 public void keyPressed(KeyEvent evt)
177 if (viewport.cursorMode &&
178 ( (evt.getKeyCode() >= KeyEvent.VK_0 &&
179 evt.getKeyCode() <= KeyEvent.VK_9)
181 (evt.getKeyCode() >= KeyEvent.VK_NUMPAD0 &&
182 evt.getKeyCode() <= KeyEvent.VK_NUMPAD9)
184 && Character.isDigit(evt.getKeyChar()))
185 alignPanel.seqPanel.numberPressed(evt.getKeyChar());
187 switch (evt.getKeyCode())
190 case 27: // escape key
191 deselectAllSequenceMenuItem_actionPerformed(null);
195 case KeyEvent.VK_DOWN:
196 if (evt.isAltDown() || !viewport.cursorMode)
197 moveSelectedSequences(false);
198 if (viewport.cursorMode)
199 alignPanel.seqPanel.moveCursor(0, 1);
203 if (evt.isAltDown() || !viewport.cursorMode)
204 moveSelectedSequences(true);
205 if (viewport.cursorMode)
206 alignPanel.seqPanel.moveCursor(0, -1);
210 case KeyEvent.VK_LEFT:
211 if (evt.isAltDown() || !viewport.cursorMode)
212 slideSequences(false,
213 alignPanel.seqPanel.getKeyboardNo1());
215 alignPanel.seqPanel.moveCursor( -1, 0);
220 case KeyEvent.VK_RIGHT:
221 if (evt.isAltDown() || !viewport.cursorMode)
223 alignPanel.seqPanel.getKeyboardNo1());
225 alignPanel.seqPanel.moveCursor(1, 0);
228 case KeyEvent.VK_SPACE:
229 if (viewport.cursorMode)
231 alignPanel.seqPanel.insertGapAtCursor(evt.isControlDown()
237 case KeyEvent.VK_DELETE:
238 case KeyEvent.VK_BACK_SPACE:
239 if (!viewport.cursorMode)
241 cut_actionPerformed(null);
245 alignPanel.seqPanel.deleteGapAtCursor(evt.isControlDown()
253 if (viewport.cursorMode)
255 alignPanel.seqPanel.setCursorRow();
259 if (viewport.cursorMode && !evt.isControlDown())
261 alignPanel.seqPanel.setCursorColumn();
265 if (viewport.cursorMode)
267 alignPanel.seqPanel.setCursorPosition();
271 case KeyEvent.VK_ENTER:
272 case KeyEvent.VK_COMMA:
273 if (viewport.cursorMode)
275 alignPanel.seqPanel.setCursorRowAndColumn();
280 if (viewport.cursorMode)
282 alignPanel.seqPanel.setSelectionAreaAtCursor(true);
286 if (viewport.cursorMode)
288 alignPanel.seqPanel.setSelectionAreaAtCursor(false);
293 viewport.cursorMode = !viewport.cursorMode;
294 statusBar.setText("Keyboard editing mode is " +
295 (viewport.cursorMode ? "on" : "off"));
296 if (viewport.cursorMode)
298 alignPanel.seqPanel.seqCanvas.cursorX = viewport.startRes;
299 alignPanel.seqPanel.seqCanvas.cursorY = viewport.startSeq;
301 alignPanel.seqPanel.seqCanvas.repaint();
307 ClassLoader cl = jalview.gui.Desktop.class.getClassLoader();
308 java.net.URL url = javax.help.HelpSet.findHelpSet(cl, "help/help");
309 javax.help.HelpSet hs = new javax.help.HelpSet(cl, url);
311 javax.help.HelpBroker hb = hs.createHelpBroker();
312 hb.setCurrentID("home");
313 hb.setDisplayed(true);
317 ex.printStackTrace();
323 boolean toggleSeqs = !evt.isControlDown();
324 boolean toggleCols = !evt.isShiftDown();
326 boolean hide = false;
328 SequenceGroup sg = viewport.getSelectionGroup();
331 if (sg != null && sg.getSize() != viewport.alignment.getHeight())
333 hideSelSequences_actionPerformed(null);
336 else if (! (toggleCols &&
337 viewport.colSel.getSelected().size() > 0))
339 showAllSeqs_actionPerformed(null);
345 if (viewport.colSel.getSelected().size() > 0)
347 hideSelColumns_actionPerformed(null);
350 viewport.selectionGroup = sg;
355 showAllColumns_actionPerformed(null);
360 case KeyEvent.VK_PAGE_UP:
361 if (viewport.wrapAlignment)
363 alignPanel.scrollUp(true);
367 alignPanel.setScrollValues(viewport.startRes,
369 - viewport.endSeq + viewport.startSeq);
372 case KeyEvent.VK_PAGE_DOWN:
373 if (viewport.wrapAlignment)
375 alignPanel.scrollUp(false);
379 alignPanel.setScrollValues(viewport.startRes,
381 + viewport.endSeq - viewport.startSeq);
387 public void keyReleased(KeyEvent evt)
389 switch(evt.getKeyCode())
391 case KeyEvent.VK_LEFT:
392 if (evt.isAltDown() || !viewport.cursorMode)
393 viewport.firePropertyChange("alignment", null,
394 viewport.getAlignment().getSequences());
397 case KeyEvent.VK_RIGHT:
398 if (evt.isAltDown() || !viewport.cursorMode)
399 viewport.firePropertyChange("alignment", null,
400 viewport.getAlignment().getSequences());
408 public void addAlignmentPanel(final AlignmentPanel ap,
411 ap.alignFrame = this;
413 alignPanels.addElement(ap);
415 PaintRefresher.Register(ap, ap.av.getSequenceSetId());
417 int aSize = alignPanels.size();
419 tabbedPane.setVisible(aSize>1 || ap.av.viewName!=null);
421 if (aSize == 1 && ap.av.viewName==null)
423 this.getContentPane().add(ap, BorderLayout.CENTER);
429 setInitialTabVisible();
432 expandViews.setEnabled(true);
433 gatherViews.setEnabled(true);
434 tabbedPane.addTab(ap.av.viewName, ap);
436 ap.setVisible(false);
443 ap.av.alignment.padGaps();
445 ap.av.updateConservation(ap);
446 ap.av.updateConsensus(ap);
450 public void setInitialTabVisible()
452 expandViews.setEnabled(true);
453 gatherViews.setEnabled(true);
454 tabbedPane.setVisible(true);
455 AlignmentPanel first = (AlignmentPanel) alignPanels.firstElement();
456 tabbedPane.addTab(first.av.viewName,first);
457 this.getContentPane().add(tabbedPane, BorderLayout.CENTER);
461 public AlignViewport getViewport()
466 /* Set up intrinsic listeners for dynamically generated GUI bits. */
467 private void addServiceListeners()
469 final java.beans.PropertyChangeListener thisListener;
470 // Do this once to get current state
471 BuildWebServiceMenu();
472 Desktop.discoverer.addPropertyChangeListener(
473 thisListener = new java.beans.PropertyChangeListener()
475 public void propertyChange(PropertyChangeEvent evt)
477 // System.out.println("Discoverer property change.");
478 if (evt.getPropertyName().equals("services"))
480 // System.out.println("Rebuilding web service menu");
481 BuildWebServiceMenu();
486 addInternalFrameListener(new javax.swing.event.
487 InternalFrameAdapter()
489 public void internalFrameClosed(
490 javax.swing.event.InternalFrameEvent evt)
492 // System.out.println("deregistering discoverer listener");
493 Desktop.discoverer.removePropertyChangeListener(thisListener);
494 closeMenuItem_actionPerformed(true);
500 public void setGUINucleotide(boolean nucleotide)
502 showTranslation.setVisible( nucleotide );
503 conservationMenuItem.setEnabled( !nucleotide );
504 modifyConservation.setEnabled( !nucleotide );
506 //Remember AlignFrame always starts as protein
509 calculateMenu.remove(calculateMenu.getItemCount()-2);
511 setShowProductsEnabled();
517 * Need to call this method when tabs are selected for multiple views,
518 * or when loading from Jalview2XML.java
519 * @param av AlignViewport
521 void setMenusFromViewport(AlignViewport av)
523 padGapsMenuitem.setSelected(av.padGaps);
524 colourTextMenuItem.setSelected(av.showColourText);
525 abovePIDThreshold.setSelected(av.getAbovePIDThreshold());
526 conservationMenuItem.setSelected(av.getConservationSelected());
527 seqLimits.setSelected(av.getShowJVSuffix());
528 idRightAlign.setSelected(av.rightAlignIds);
529 renderGapsMenuItem.setSelected(av.renderGaps);
530 wrapMenuItem.setSelected(av.wrapAlignment);
531 scaleAbove.setVisible(av.wrapAlignment);
532 scaleLeft.setVisible(av.wrapAlignment);
533 scaleRight.setVisible(av.wrapAlignment);
534 annotationPanelMenuItem.setState(av.showAnnotation);
535 viewBoxesMenuItem.setSelected(av.showBoxes);
536 viewTextMenuItem.setSelected(av.showText);
538 setColourSelected(ColourSchemeProperty.
539 getColourName(av.getGlobalColourScheme()));
541 showSeqFeatures.setSelected(av.showSequenceFeatures);
542 hiddenMarkers.setState(av.showHiddenMarkers);
543 applyToAllGroups.setState(av.colourAppliesToAllGroups);
549 Hashtable progressBars;
550 public void setProgressBar(String message, long id)
552 if(progressBars == null)
554 progressBars = new Hashtable();
557 JPanel progressPanel;
558 GridLayout layout = (GridLayout) statusPanel.getLayout();
559 if(progressBars.get( new Long(id) )!=null)
561 progressPanel = (JPanel)progressBars.get( new Long(id) );
562 statusPanel.remove(progressPanel);
563 progressBars.remove( progressPanel );
564 progressPanel = null;
567 statusBar.setText(message);
570 layout.setRows(layout.getRows() - 1);
574 progressPanel = new JPanel(new BorderLayout(10, 5));
576 JProgressBar progressBar = new JProgressBar();
577 progressBar.setIndeterminate(true);
579 progressPanel.add(new JLabel(message), BorderLayout.WEST);
580 progressPanel.add(progressBar, BorderLayout.CENTER);
582 layout.setRows(layout.getRows() + 1);
583 statusPanel.add(progressPanel);
585 progressBars.put(new Long(id), progressPanel);
592 * @return true if any progress bars are still active
594 public boolean operationInProgress()
596 if (progressBars!=null && progressBars.size()>0)
603 Added so Castor Mapping file can obtain Jalview Version
605 public String getVersion()
607 return jalview.bin.Cache.getProperty("VERSION");
610 public FeatureRenderer getFeatureRenderer()
612 return alignPanel.seqPanel.seqCanvas.getFeatureRenderer();
616 public void fetchSequence_actionPerformed(ActionEvent e)
618 new SequenceFetcher(this);
621 public void addFromFile_actionPerformed(ActionEvent e)
623 Desktop.instance.inputLocalFileMenuItem_actionPerformed(viewport);
626 public void reload_actionPerformed(ActionEvent e)
630 if(currentFileFormat.equals("Jalview"))
632 JInternalFrame [] frames = Desktop.desktop.getAllFrames();
633 for(int i=0; i<frames.length; i++)
635 if (frames[i] instanceof AlignFrame
637 && ( (AlignFrame) frames[i]).fileName.equals(fileName))
641 frames[i].setSelected(true);
642 Desktop.instance.closeAssociatedWindows();
644 catch (java.beans.PropertyVetoException ex)
649 Desktop.instance.closeAssociatedWindows();
651 FileLoader loader = new FileLoader();
652 String protocol = fileName.startsWith("http:")? "URL":"File";
653 loader.LoadFile(viewport, fileName, protocol, currentFileFormat);
657 Rectangle bounds = this.getBounds();
659 FileLoader loader = new FileLoader();
660 String protocol = fileName.startsWith("http:") ? "URL" : "File";
661 AlignFrame newframe =
662 loader.LoadFileWaitTillLoaded(fileName, protocol, currentFileFormat);
664 newframe.setBounds(bounds);
666 this.closeMenuItem_actionPerformed(true);
672 public void addFromText_actionPerformed(ActionEvent e)
674 Desktop.instance.inputTextboxMenuItem_actionPerformed(viewport);
677 public void addFromURL_actionPerformed(ActionEvent e)
679 Desktop.instance.inputURLMenuItem_actionPerformed(viewport);
683 public void save_actionPerformed(ActionEvent e)
686 || currentFileFormat==null
687 || fileName.startsWith("http")
690 saveAs_actionPerformed(null);
694 saveAlignment(fileName, currentFileFormat);
701 * @param e DOCUMENT ME!
703 public void saveAs_actionPerformed(ActionEvent e)
705 JalviewFileChooser chooser = new JalviewFileChooser(jalview.bin.Cache.
706 getProperty( "LAST_DIRECTORY"),
707 jalview.io.AppletFormatAdapter.WRITABLE_EXTENSIONS,
708 jalview.io.AppletFormatAdapter.WRITABLE_FNAMES,
713 chooser.setFileView(new JalviewFileView());
714 chooser.setDialogTitle("Save Alignment to file");
715 chooser.setToolTipText("Save");
717 int value = chooser.showSaveDialog(this);
719 if (value == JalviewFileChooser.APPROVE_OPTION)
721 currentFileFormat = chooser.getSelectedFormat();
722 if (currentFileFormat == null)
724 JOptionPane.showInternalMessageDialog(Desktop.desktop,
725 "You must select a file format before saving!",
726 "File format not specified",
727 JOptionPane.WARNING_MESSAGE);
728 value = chooser.showSaveDialog(this);
732 fileName = chooser.getSelectedFile().getPath();
734 jalview.bin.Cache.setProperty("DEFAULT_FILE_FORMAT",
737 jalview.bin.Cache.setProperty("LAST_DIRECTORY", fileName);
738 if (currentFileFormat.indexOf(" ")>-1)
740 currentFileFormat = currentFileFormat.substring(0, currentFileFormat.indexOf(" "));
742 saveAlignment(fileName, currentFileFormat);
746 public boolean saveAlignment(String file, String format)
748 boolean success = true;
750 if (format.equalsIgnoreCase("Jalview"))
752 String shortName = title;
754 if (shortName.indexOf(java.io.File.separatorChar) > -1)
756 shortName = shortName.substring(shortName.lastIndexOf(
757 java.io.File.separatorChar) + 1);
760 success = new Jalview2XML().SaveAlignment(this, file, shortName);
762 statusBar.setText("Successfully saved to file: "
764 +format +" format.");
770 String[] omitHidden = null;
772 if (viewport.hasHiddenColumns)
774 int reply = JOptionPane.showInternalConfirmDialog(Desktop.desktop,
775 "The Alignment contains hidden columns."
776 + "\nDo you want to save only the visible alignment?",
777 "Save / Omit Hidden Columns",
778 JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE);
780 if (reply == JOptionPane.YES_OPTION)
782 omitHidden = viewport.getViewAsString(false);
785 FormatAdapter f = new FormatAdapter();
787 String output = f.formatSequences(
789 (Alignment) viewport.alignment, // class cast exceptions will occur in the distant future
790 omitHidden, f.getCacheSuffixDefault(format), viewport.colSel);
800 java.io.PrintWriter out = new java.io.PrintWriter(
801 new java.io.FileWriter(file));
806 statusBar.setText("Successfully saved to file: "
808 + format + " format.");
813 ex.printStackTrace();
820 JOptionPane.showInternalMessageDialog(
821 this, "Couldn't save file: " + fileName,
823 JOptionPane.WARNING_MESSAGE);
832 * @param e DOCUMENT ME!
834 protected void outputText_actionPerformed(ActionEvent e)
836 String [] omitHidden = null;
838 if(viewport.hasHiddenColumns)
840 int reply = JOptionPane.showInternalConfirmDialog(Desktop.desktop,
841 "The Alignment contains hidden columns."
842 +"\nDo you want to output only the visible alignment?",
843 "Save / Omit Hidden Columns",
844 JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE);
846 if(reply==JOptionPane.YES_OPTION)
848 omitHidden = viewport.getViewAsString(false);
852 CutAndPasteTransfer cap = new CutAndPasteTransfer();
853 cap.setForInput(null);
854 Desktop.addInternalFrame(cap,
855 "Alignment output - " + e.getActionCommand(), 600,
859 cap.setText(new FormatAdapter().formatSequences(
860 e.getActionCommand(),
862 omitHidden, viewport.colSel));
868 * @param e DOCUMENT ME!
870 protected void htmlMenuItem_actionPerformed(ActionEvent e)
872 new HTMLOutput(alignPanel,
873 alignPanel.seqPanel.seqCanvas.getSequenceRenderer(),
874 alignPanel.seqPanel.seqCanvas.getFeatureRenderer());
877 public void createImageMap(File file, String image)
879 alignPanel.makePNGImageMap(file, image);
885 * @param e DOCUMENT ME!
887 public void createPNG(File f)
889 alignPanel.makePNG(f);
895 * @param e DOCUMENT ME!
897 public void createEPS(File f)
899 alignPanel.makeEPS(f);
903 public void pageSetup_actionPerformed(ActionEvent e)
905 PrinterJob printJob = PrinterJob.getPrinterJob();
906 PrintThread.pf = printJob.pageDialog(printJob.defaultPage());
912 * @param e DOCUMENT ME!
914 public void printMenuItem_actionPerformed(ActionEvent e)
916 //Putting in a thread avoids Swing painting problems
917 PrintThread thread = new PrintThread(alignPanel);
921 public void exportFeatures_actionPerformed(ActionEvent e)
923 new AnnotationExporter().exportFeatures(alignPanel);
927 public void exportAnnotations_actionPerformed(ActionEvent e)
929 new AnnotationExporter().exportAnnotations(
931 viewport.showAnnotation ? viewport.alignment.getAlignmentAnnotation() : null,
932 viewport.alignment.getGroups(),
933 ((Alignment)viewport.alignment).alignmentProperties
938 public void associatedData_actionPerformed(ActionEvent e)
940 // Pick the tree file
941 JalviewFileChooser chooser = new JalviewFileChooser(jalview.bin.Cache.
944 chooser.setFileView(new JalviewFileView());
945 chooser.setDialogTitle("Load Jalview Annotations or Features File");
946 chooser.setToolTipText("Load Jalview Annotations / Features file");
948 int value = chooser.showOpenDialog(null);
950 if (value == JalviewFileChooser.APPROVE_OPTION)
952 String choice = chooser.getSelectedFile().getPath();
953 jalview.bin.Cache.setProperty("LAST_DIRECTORY", choice);
954 loadJalviewDataFile(choice);
963 * @param e DOCUMENT ME!
965 public void closeMenuItem_actionPerformed(boolean closeAllTabs)
967 if(alignPanels!=null && alignPanels.size()<2)
974 if(alignPanels!=null)
978 for (int i = 0; i < alignPanels.size(); i++)
980 AlignmentPanel ap = (AlignmentPanel) alignPanels.elementAt(i);
981 jalview.structure.StructureSelectionManager.getStructureSelectionManager()
982 .removeStructureViewerListener(ap.seqPanel, null);
983 PaintRefresher.RemoveComponent(ap.seqPanel.seqCanvas);
984 PaintRefresher.RemoveComponent(ap.idPanel.idCanvas);
985 PaintRefresher.RemoveComponent(ap);
986 ap.av.alignment = null;
991 int index = tabbedPane.getSelectedIndex();
993 alignPanels.removeElement(alignPanel);
994 PaintRefresher.RemoveComponent(alignPanel.seqPanel.seqCanvas);
995 PaintRefresher.RemoveComponent(alignPanel.idPanel.idCanvas);
996 PaintRefresher.RemoveComponent(alignPanel);
997 viewport.alignment = null;
1001 tabbedPane.removeTabAt(index);
1002 tabbedPane.validate();
1004 if(index==tabbedPane.getTabCount())
1009 this.tabSelectionChanged(index);
1015 this.setClosed(true);
1018 catch (Exception ex)
1020 ex.printStackTrace();
1028 void updateEditMenuBar()
1031 if (viewport.historyList.size() > 0)
1033 undoMenuItem.setEnabled(true);
1034 CommandI command = (CommandI) viewport.historyList.peek();
1035 undoMenuItem.setText("Undo " + command.getDescription());
1039 undoMenuItem.setEnabled(false);
1040 undoMenuItem.setText("Undo");
1043 if (viewport.redoList.size() > 0)
1045 redoMenuItem.setEnabled(true);
1047 CommandI command = (CommandI) viewport.redoList.peek();
1048 redoMenuItem.setText("Redo " + command.getDescription());
1052 redoMenuItem.setEnabled(false);
1053 redoMenuItem.setText("Redo");
1058 public void addHistoryItem(CommandI command)
1060 if(command.getSize()>0)
1062 viewport.historyList.push(command);
1063 viewport.redoList.clear();
1064 updateEditMenuBar();
1065 viewport.hasHiddenColumns = viewport.colSel.getHiddenColumns() != null;
1071 * @return alignment objects for all views
1073 AlignmentI[] getViewAlignments()
1075 if (alignPanels!=null)
1077 Enumeration e = alignPanels.elements();
1078 AlignmentI[] als = new AlignmentI[alignPanels.size()];
1079 for (int i=0; e.hasMoreElements(); i++)
1081 als[i] = ((AlignmentPanel) e.nextElement()).av.getAlignment();
1087 return new AlignmentI[] { viewport.alignment };
1094 * @param e DOCUMENT ME!
1096 protected void undoMenuItem_actionPerformed(ActionEvent e)
1098 if (viewport.historyList.empty())
1100 CommandI command = (CommandI)viewport.historyList.pop();
1101 viewport.redoList.push(command);
1102 command.undoCommand(getViewAlignments());
1104 AlignViewport originalSource = getOriginatingSource(command);
1105 updateEditMenuBar();
1107 if(originalSource!=null)
1109 originalSource.hasHiddenColumns = viewport.colSel.getHiddenColumns() != null;
1110 originalSource.firePropertyChange("alignment",
1112 originalSource.alignment.getSequences());
1119 * @param e DOCUMENT ME!
1121 protected void redoMenuItem_actionPerformed(ActionEvent e)
1123 if(viewport.redoList.size()<1)
1128 CommandI command = (CommandI) viewport.redoList.pop();
1129 viewport.historyList.push(command);
1130 command.doCommand(getViewAlignments());
1132 AlignViewport originalSource = getOriginatingSource(command);
1133 updateEditMenuBar();
1135 if(originalSource!=null)
1137 originalSource.hasHiddenColumns = viewport.colSel.getHiddenColumns() != null;
1138 originalSource.firePropertyChange("alignment",
1140 originalSource.alignment.getSequences());
1144 AlignViewport getOriginatingSource(CommandI command)
1146 AlignViewport originalSource = null;
1147 //For sequence removal and addition, we need to fire
1148 //the property change event FROM the viewport where the
1149 //original alignment was altered
1151 if (command instanceof EditCommand)
1153 EditCommand editCommand = (EditCommand) command;
1154 al = editCommand.getAlignment();
1155 Vector comps = (Vector) PaintRefresher.components
1156 .get(viewport.getSequenceSetId());
1158 for (int i = 0; i < comps.size(); i++)
1160 if (comps.elementAt(i) instanceof AlignmentPanel)
1162 if (al == ( (AlignmentPanel) comps.elementAt(i)).av.alignment)
1164 originalSource = ( (AlignmentPanel) comps.elementAt(i)).av;
1171 if (originalSource == null)
1173 //The original view is closed, we must validate
1174 //the current view against the closed view first
1177 PaintRefresher.validateSequences(al, viewport.alignment);
1180 originalSource = viewport;
1183 return originalSource;
1189 * @param up DOCUMENT ME!
1191 public void moveSelectedSequences(boolean up)
1193 SequenceGroup sg = viewport.getSelectionGroup();
1202 for (int i = 1; i < viewport.alignment.getHeight(); i++)
1204 SequenceI seq = viewport.alignment.getSequenceAt(i);
1206 if (!sg.getSequences(null).contains(seq))
1211 SequenceI temp = viewport.alignment.getSequenceAt(i - 1);
1213 if (sg.getSequences(null).contains(temp))
1218 viewport.alignment.getSequences().setElementAt(temp, i);
1219 viewport.alignment.getSequences().setElementAt(seq, i - 1);
1224 for (int i = viewport.alignment.getHeight() - 2; i > -1; i--)
1226 SequenceI seq = viewport.alignment.getSequenceAt(i);
1228 if (!sg.getSequences(null).contains(seq))
1233 SequenceI temp = viewport.alignment.getSequenceAt(i + 1);
1235 if (sg.getSequences(null).contains(temp))
1240 viewport.alignment.getSequences().setElementAt(temp, i);
1241 viewport.alignment.getSequences().setElementAt(seq, i + 1);
1245 alignPanel.paintAlignment(true);
1251 synchronized void slideSequences(boolean right, int size)
1253 Vector sg = new Vector();
1254 if(viewport.cursorMode)
1256 sg.addElement(viewport.alignment.getSequenceAt(
1257 alignPanel.seqPanel.seqCanvas.cursorY));
1259 else if(viewport.getSelectionGroup()!=null
1260 && viewport.getSelectionGroup().getSize()!=viewport.alignment.getHeight())
1262 sg = viewport.getSelectionGroup().getSequences(
1263 viewport.hiddenRepSequences);
1271 Vector invertGroup = new Vector();
1273 for (int i = 0; i < viewport.alignment.getHeight(); i++)
1275 if(!sg.contains(viewport.alignment.getSequenceAt(i)))
1276 invertGroup.add(viewport.alignment.getSequenceAt(i));
1279 SequenceI[] seqs1 = new SequenceI[sg.size()];
1280 for (int i = 0; i < sg.size(); i++)
1281 seqs1[i] = (SequenceI) sg.elementAt(i);
1283 SequenceI[] seqs2 = new SequenceI[invertGroup.size()];
1284 for (int i = 0; i < invertGroup.size(); i++)
1285 seqs2[i] = (SequenceI) invertGroup.elementAt(i);
1287 SlideSequencesCommand ssc;
1289 ssc = new SlideSequencesCommand("Slide Sequences",
1291 viewport.getGapCharacter()
1294 ssc = new SlideSequencesCommand("Slide Sequences",
1296 viewport.getGapCharacter()
1299 int groupAdjustment = 0;
1300 if (ssc.getGapsInsertedBegin() && right)
1302 if (viewport.cursorMode)
1303 alignPanel.seqPanel.moveCursor(size, 0);
1305 groupAdjustment = size;
1307 else if (!ssc.getGapsInsertedBegin() && !right)
1309 if (viewport.cursorMode)
1310 alignPanel.seqPanel.moveCursor( -size, 0);
1312 groupAdjustment = -size;
1315 if (groupAdjustment != 0)
1317 viewport.getSelectionGroup().setStartRes(
1318 viewport.getSelectionGroup().getStartRes() + groupAdjustment);
1319 viewport.getSelectionGroup().setEndRes(
1320 viewport.getSelectionGroup().getEndRes() + groupAdjustment);
1324 boolean appendHistoryItem = false;
1325 if(viewport.historyList!=null
1326 && viewport.historyList.size()>0
1327 && viewport.historyList.peek() instanceof SlideSequencesCommand)
1329 appendHistoryItem = ssc.appendSlideCommand(
1330 (SlideSequencesCommand)viewport.historyList.peek())
1334 if(!appendHistoryItem)
1335 addHistoryItem(ssc);
1344 * @param e DOCUMENT ME!
1346 protected void copy_actionPerformed(ActionEvent e)
1349 if (viewport.getSelectionGroup() == null)
1353 // TODO: preserve the ordering of displayed alignment annotation in any internal paste (particularly sequence associated annotation)
1354 SequenceI [] seqs = viewport.getSelectionAsNewSequence();
1355 String[] omitHidden = null;
1357 if (viewport.hasHiddenColumns)
1359 omitHidden = viewport.getViewAsString(true);
1362 String output = new FormatAdapter().formatSequences(
1367 StringSelection ss = new StringSelection(output);
1371 jalview.gui.Desktop.internalCopy = true;
1372 //Its really worth setting the clipboard contents
1373 //to empty before setting the large StringSelection!!
1374 Toolkit.getDefaultToolkit().getSystemClipboard()
1375 .setContents(new StringSelection(""), null);
1377 Toolkit.getDefaultToolkit().getSystemClipboard()
1378 .setContents(ss, Desktop.instance);
1380 catch (OutOfMemoryError er)
1382 er.printStackTrace();
1383 javax.swing.SwingUtilities.invokeLater(new Runnable()
1387 javax.swing.JOptionPane.showInternalMessageDialog(Desktop.desktop,
1388 "Out of memory copying region!!"
1390 "\nSee help files for increasing Java Virtual Machine memory."
1392 javax.swing.JOptionPane.WARNING_MESSAGE);
1399 Vector hiddenColumns = null;
1400 if(viewport.hasHiddenColumns)
1402 hiddenColumns =new Vector();
1403 int hiddenOffset = viewport.getSelectionGroup().getStartRes();
1404 for (int i = 0; i < viewport.getColumnSelection().getHiddenColumns().size();
1407 int[] region = (int[])
1408 viewport.getColumnSelection().getHiddenColumns().elementAt(i);
1410 hiddenColumns.addElement(new int[]
1411 {region[0] - hiddenOffset,
1412 region[1]-hiddenOffset});
1416 Desktop.jalviewClipboard = new Object[]
1419 viewport.alignment.getDataset(),
1421 statusBar.setText("Copied "+seqs.length+" sequences to clipboard.");
1427 * @param e DOCUMENT ME!
1429 protected void pasteNew_actionPerformed(ActionEvent e)
1437 * @param e DOCUMENT ME!
1439 protected void pasteThis_actionPerformed(ActionEvent e)
1447 * @param newAlignment DOCUMENT ME!
1449 void paste(boolean newAlignment)
1451 boolean externalPaste=true;
1454 Clipboard c = Toolkit.getDefaultToolkit().getSystemClipboard();
1455 Transferable contents = c.getContents(this);
1457 if (contents == null)
1465 str = (String) contents.getTransferData(DataFlavor.stringFlavor);
1466 if (str.length() < 1)
1471 format = new IdentifyFile().Identify(str, "Paste");
1474 catch (OutOfMemoryError er)
1476 er.printStackTrace();
1477 javax.swing.SwingUtilities.invokeLater(new Runnable()
1481 javax.swing.JOptionPane.showInternalMessageDialog(Desktop.desktop,
1482 "Out of memory pasting sequences!!"
1484 "\nSee help files for increasing Java Virtual Machine memory."
1486 javax.swing.JOptionPane.WARNING_MESSAGE);
1493 SequenceI[] sequences;
1494 boolean annotationAdded = false;
1495 AlignmentI alignment = null;
1497 if(Desktop.jalviewClipboard!=null)
1499 // The clipboard was filled from within Jalview, we must use the sequences
1500 // And dataset from the copied alignment
1501 SequenceI[] newseq = (SequenceI[])Desktop.jalviewClipboard[0];
1502 // be doubly sure that we create *new* sequence objects.
1503 sequences = new SequenceI[newseq.length];
1504 for (int i=0;i<newseq.length;i++) {
1505 sequences[i] = new Sequence(newseq[i]);
1507 alignment = new Alignment(sequences);
1508 externalPaste = false;
1512 // parse the clipboard as an alignment.
1513 alignment = new FormatAdapter().readFile(str, "Paste", format);
1514 sequences = alignment.getSequencesArray();
1522 if (Desktop.jalviewClipboard != null)
1524 // dataset is inherited
1525 alignment.setDataset( (Alignment) Desktop.jalviewClipboard[1]);
1529 // new dataset is constructed
1530 alignment.setDataset(null);
1532 alwidth = alignment.getWidth()+1;
1536 AlignmentI pastedal = alignment; // preserve pasted alignment object
1537 // Add pasted sequences and dataset into existing alignment.
1538 alignment = viewport.getAlignment();
1539 alwidth = alignment.getWidth()+1;
1540 // decide if we need to import sequences from an existing dataset
1541 boolean importDs = Desktop.jalviewClipboard != null
1542 && Desktop.jalviewClipboard[1] != alignment.getDataset();
1543 // importDs==true instructs us to copy over new dataset sequences from
1544 // an existing alignment
1545 Vector newDs = (importDs) ? new Vector() : null; // used to create
1546 // minimum dataset set
1548 for (int i = 0; i < sequences.length; i++)
1552 newDs.addElement(null);
1554 SequenceI ds = sequences[i].getDatasetSequence(); // null for a simple
1556 if (importDs && ds != null)
1558 if (!newDs.contains(ds))
1560 newDs.setElementAt(ds, i);
1561 ds = new Sequence(ds);
1562 // update with new dataset sequence
1563 sequences[i].setDatasetSequence(ds);
1567 ds = sequences[newDs.indexOf(ds)].getDatasetSequence();
1572 // copy and derive new dataset sequence
1573 sequences[i] = sequences[i].deriveSequence();
1574 alignment.getDataset().addSequence(sequences[i].getDatasetSequence());
1575 // TODO: avoid creation of duplicate dataset sequences with a
1576 // 'contains' method using SequenceI.equals()/SequenceI.contains()
1578 alignment.addSequence(sequences[i]); // merges dataset
1582 newDs.clear(); // tidy up
1584 if (pastedal.getAlignmentAnnotation()!=null) {
1585 // Add any annotation attached to alignment.
1586 AlignmentAnnotation[] alann = pastedal.getAlignmentAnnotation();
1587 for (int i=0; i<alann.length; i++)
1589 annotationAdded=true;
1590 if (alann[i].sequenceRef==null && !alann[i].autoCalculated) {
1591 AlignmentAnnotation newann = new AlignmentAnnotation(alann[i]);
1592 newann.padAnnotation(alwidth);
1593 alignment.addAnnotation(newann);
1598 if (!newAlignment) {
1602 addHistoryItem(new EditCommand(
1607 alignment.getWidth(),
1611 // Add any annotations attached to sequences
1612 for (int i = 0; i < sequences.length; i++)
1614 if (sequences[i].getAnnotation() != null)
1616 for (int a = 0; a < sequences[i].getAnnotation().length; a++)
1618 annotationAdded=true;
1619 sequences[i].getAnnotation()[a].adjustForAlignment();
1620 sequences[i].getAnnotation()[a].padAnnotation(alwidth);
1621 alignment.addAnnotation(sequences[i].getAnnotation()[a]); // annotation was duplicated earlier
1622 alignment.setAnnotationIndex(sequences[i].getAnnotation()[a], a);
1626 if (!newAlignment) {
1628 // propagate alignment changed.
1629 viewport.setEndSeq(alignment.getHeight());
1630 if (annotationAdded)
1632 // Duplicate sequence annotation in all views.
1633 AlignmentI[] alview = this.getViewAlignments();
1634 for (int i = 0; i < sequences.length; i++)
1636 AlignmentAnnotation sann[] = sequences[i].getAnnotation();
1639 for (int avnum=0;avnum<alview.length; avnum++)
1641 if (alview[avnum]!=alignment)
1643 // duplicate in a view other than the one with input focus
1644 int avwidth = alview[avnum].getWidth()+1;
1645 // this relies on sann being preserved after we
1646 // modify the sequence's annotation array for each duplication
1647 for (int a=0; a<sann.length; a++)
1649 AlignmentAnnotation newann = new AlignmentAnnotation(sann[a]);
1650 sequences[i].addAlignmentAnnotation(newann);
1651 newann.padAnnotation(avwidth);
1652 alview[avnum].addAnnotation(newann); // annotation was duplicated earlier
1653 alview[avnum].setAnnotationIndex(newann, a);
1658 buildSortByAnnotationScoresMenu();
1660 viewport.firePropertyChange("alignment", null, alignment.getSequences());
1663 AlignFrame af = new AlignFrame(alignment, DEFAULT_WIDTH, DEFAULT_HEIGHT);
1664 String newtitle = new String("Copied sequences");
1666 if(Desktop.jalviewClipboard!=null && Desktop.jalviewClipboard[2]!=null)
1668 Vector hc = (Vector)Desktop.jalviewClipboard[2];
1669 for(int i=0; i<hc.size(); i++)
1671 int [] region = (int[]) hc.elementAt(i);
1672 af.viewport.hideColumns(region[0], region[1]);
1677 //>>>This is a fix for the moment, until a better solution is found!!<<<
1678 af.alignPanel.seqPanel.seqCanvas.getFeatureRenderer().transferSettings(
1679 alignPanel.seqPanel.seqCanvas.getFeatureRenderer());
1681 // TODO: maintain provenance of an alignment, rather than just make the title a concatenation of operations.
1682 if (!externalPaste) {
1683 if (title.startsWith("Copied sequences"))
1689 newtitle = newtitle.concat("- from " + title);
1692 newtitle = new String("Pasted sequences");
1695 Desktop.addInternalFrame(af, newtitle, DEFAULT_WIDTH,
1702 catch (Exception ex)
1704 ex.printStackTrace();
1705 System.out.println("Exception whilst pasting: "+ex);
1706 // could be anything being pasted in here
1715 * @param e DOCUMENT ME!
1717 protected void cut_actionPerformed(ActionEvent e)
1719 copy_actionPerformed(null);
1720 delete_actionPerformed(null);
1726 * @param e DOCUMENT ME!
1728 protected void delete_actionPerformed(ActionEvent evt)
1731 SequenceGroup sg = viewport.getSelectionGroup();
1737 Vector seqs = new Vector();
1739 for (int i = 0; i < sg.getSize(); i++)
1741 seq = sg.getSequenceAt(i);
1742 seqs.addElement(seq);
1746 // If the cut affects all sequences, remove highlighted columns
1747 if (sg.getSize() == viewport.alignment.getHeight())
1749 viewport.getColumnSelection().removeElements(sg.getStartRes(),
1750 sg.getEndRes() + 1);
1754 SequenceI [] cut = new SequenceI[seqs.size()];
1755 for(int i=0; i<seqs.size(); i++)
1757 cut[i] = (SequenceI)seqs.elementAt(i);
1764 addHistoryItem(new EditCommand("Cut Sequences",
1768 sg.getEndRes()-sg.getStartRes()+1,
1769 viewport.alignment));
1772 viewport.setSelectionGroup(null);
1773 viewport.alignment.deleteGroup(sg);
1775 viewport.firePropertyChange("alignment", null,
1776 viewport.getAlignment().getSequences());
1778 if (viewport.getAlignment().getHeight() < 1)
1782 this.setClosed(true);
1784 catch (Exception ex)
1793 * @param e DOCUMENT ME!
1795 protected void deleteGroups_actionPerformed(ActionEvent e)
1797 viewport.alignment.deleteAllGroups();
1798 viewport.sequenceColours = null;
1799 viewport.setSelectionGroup(null);
1800 PaintRefresher.Refresh(this, viewport.getSequenceSetId());
1801 alignPanel.paintAlignment(true);
1807 * @param e DOCUMENT ME!
1809 public void selectAllSequenceMenuItem_actionPerformed(ActionEvent e)
1811 SequenceGroup sg = new SequenceGroup();
1813 for (int i = 0; i < viewport.getAlignment().getSequences().size();
1816 sg.addSequence(viewport.getAlignment().getSequenceAt(i), false);
1819 sg.setEndRes(viewport.alignment.getWidth() - 1);
1820 viewport.setSelectionGroup(sg);
1821 alignPanel.paintAlignment(true);
1822 PaintRefresher.Refresh(alignPanel, viewport.getSequenceSetId());
1828 * @param e DOCUMENT ME!
1830 public void deselectAllSequenceMenuItem_actionPerformed(ActionEvent e)
1832 if(viewport.cursorMode)
1834 alignPanel.seqPanel.keyboardNo1 = null;
1835 alignPanel.seqPanel.keyboardNo2 = null;
1837 viewport.setSelectionGroup(null);
1838 viewport.getColumnSelection().clear();
1839 viewport.setSelectionGroup(null);
1840 alignPanel.seqPanel.seqCanvas.highlightSearchResults(null);
1841 alignPanel.idPanel.idCanvas.searchResults = null;
1842 alignPanel.paintAlignment(true);
1843 PaintRefresher.Refresh(alignPanel, viewport.getSequenceSetId());
1849 * @param e DOCUMENT ME!
1851 public void invertSequenceMenuItem_actionPerformed(ActionEvent e)
1853 SequenceGroup sg = viewport.getSelectionGroup();
1857 selectAllSequenceMenuItem_actionPerformed(null);
1862 for (int i = 0; i < viewport.getAlignment().getSequences().size();
1865 sg.addOrRemove(viewport.getAlignment().getSequenceAt(i), false);
1868 alignPanel.paintAlignment(true);
1870 PaintRefresher.Refresh(alignPanel, viewport.getSequenceSetId());
1873 public void invertColSel_actionPerformed(ActionEvent e)
1875 viewport.invertColumnSelection();
1876 alignPanel.paintAlignment(true);
1883 * @param e DOCUMENT ME!
1885 public void remove2LeftMenuItem_actionPerformed(ActionEvent e)
1887 trimAlignment(true);
1893 * @param e DOCUMENT ME!
1895 public void remove2RightMenuItem_actionPerformed(ActionEvent e)
1897 trimAlignment(false);
1900 void trimAlignment(boolean trimLeft)
1902 ColumnSelection colSel = viewport.getColumnSelection();
1905 if (colSel.size() > 0)
1909 column = colSel.getMin();
1913 column = colSel.getMax();
1917 if(viewport.getSelectionGroup()!=null)
1919 seqs = viewport.getSelectionGroup().getSequencesAsArray(viewport.
1920 hiddenRepSequences);
1924 seqs = viewport.alignment.getSequencesArray();
1928 TrimRegionCommand trimRegion;
1931 trimRegion = new TrimRegionCommand("Remove Left",
1932 TrimRegionCommand.TRIM_LEFT,
1937 viewport.selectionGroup);
1938 viewport.setStartRes(0);
1942 trimRegion = new TrimRegionCommand("Remove Right",
1943 TrimRegionCommand.TRIM_RIGHT,
1948 viewport.selectionGroup);
1951 statusBar.setText("Removed "+trimRegion.getSize()+" columns.");
1954 addHistoryItem(trimRegion);
1956 Vector groups = viewport.alignment.getGroups();
1958 for (int i = 0; i < groups.size(); i++)
1960 SequenceGroup sg = (SequenceGroup) groups.get(i);
1962 if ( (trimLeft && !sg.adjustForRemoveLeft(column))
1963 || (!trimLeft && !sg.adjustForRemoveRight(column)))
1965 viewport.alignment.deleteGroup(sg);
1969 viewport.firePropertyChange("alignment", null,
1970 viewport.getAlignment().getSequences());
1977 * @param e DOCUMENT ME!
1979 public void removeGappedColumnMenuItem_actionPerformed(ActionEvent e)
1981 int start = 0, end = viewport.alignment.getWidth()-1;
1984 if (viewport.getSelectionGroup() != null)
1986 seqs = viewport.getSelectionGroup().getSequencesAsArray(viewport.
1987 hiddenRepSequences);
1988 start = viewport.getSelectionGroup().getStartRes();
1989 end = viewport.getSelectionGroup().getEndRes();
1993 seqs = viewport.alignment.getSequencesArray();
1997 RemoveGapColCommand removeGapCols =
1998 new RemoveGapColCommand("Remove Gapped Columns",
2001 viewport.alignment);
2003 addHistoryItem(removeGapCols);
2005 statusBar.setText("Removed "+removeGapCols.getSize()+" empty columns.");
2007 //This is to maintain viewport position on first residue
2009 SequenceI seq = viewport.alignment.getSequenceAt(0);
2010 int startRes = seq.findPosition(viewport.startRes);
2011 // ShiftList shifts;
2012 // viewport.getAlignment().removeGaps(shifts=new ShiftList());
2013 // edit.alColumnChanges=shifts.getInverse();
2014 // if (viewport.hasHiddenColumns)
2015 // viewport.getColumnSelection().compensateForEdits(shifts);
2016 viewport.setStartRes(seq.findIndex(startRes)-1);
2017 viewport.firePropertyChange("alignment", null,
2018 viewport.getAlignment().getSequences());
2025 * @param e DOCUMENT ME!
2027 public void removeAllGapsMenuItem_actionPerformed(ActionEvent e)
2029 int start = 0, end = viewport.alignment.getWidth()-1;
2032 if (viewport.getSelectionGroup() != null)
2034 seqs = viewport.getSelectionGroup().getSequencesAsArray(viewport.
2035 hiddenRepSequences);
2036 start = viewport.getSelectionGroup().getStartRes();
2037 end = viewport.getSelectionGroup().getEndRes();
2041 seqs = viewport.alignment.getSequencesArray();
2044 //This is to maintain viewport position on first residue
2046 SequenceI seq = viewport.alignment.getSequenceAt(0);
2047 int startRes = seq.findPosition(viewport.startRes);
2049 addHistoryItem(new RemoveGapsCommand("Remove Gaps",
2052 viewport.alignment));
2054 viewport.setStartRes(seq.findIndex(startRes)-1);
2056 viewport.firePropertyChange("alignment", null,
2057 viewport.getAlignment().getSequences());
2064 * @param e DOCUMENT ME!
2066 public void padGapsMenuitem_actionPerformed(ActionEvent e)
2068 viewport.padGaps = padGapsMenuitem.isSelected();
2070 viewport.firePropertyChange("alignment",
2072 viewport.getAlignment().getSequences());
2078 * @param e DOCUMENT ME!
2080 public void findMenuItem_actionPerformed(ActionEvent e)
2085 public void newView_actionPerformed(ActionEvent e)
2087 AlignmentPanel newap =
2088 new Jalview2XML().copyAlignPanel(alignPanel, true);
2090 newap.av.gatherViewsHere = false;
2092 if (viewport.viewName == null)
2094 viewport.viewName = "Original";
2097 newap.av.historyList = viewport.historyList;
2098 newap.av.redoList = viewport.redoList;
2100 int index = Desktop.getViewCount(viewport.getSequenceSetId());
2101 String newViewName = "View " +index;
2103 Vector comps = (Vector) PaintRefresher.components.get(viewport.
2104 getSequenceSetId());
2105 Vector existingNames = new Vector();
2106 for(int i=0; i<comps.size(); i++)
2108 if(comps.elementAt(i) instanceof AlignmentPanel)
2110 AlignmentPanel ap = (AlignmentPanel)comps.elementAt(i);
2111 if(!existingNames.contains(ap.av.viewName))
2113 existingNames.addElement(ap.av.viewName);
2118 while(existingNames.contains(newViewName))
2120 newViewName = "View "+ (++index);
2123 newap.av.viewName = newViewName;
2125 addAlignmentPanel(newap, false);
2127 if(alignPanels.size()==2)
2129 viewport.gatherViewsHere = true;
2131 tabbedPane.setSelectedIndex(tabbedPane.getTabCount() - 1);
2134 public void expandViews_actionPerformed(ActionEvent e)
2136 Desktop.instance.explodeViews(this);
2139 public void gatherViews_actionPerformed(ActionEvent e)
2141 Desktop.instance.gatherViews(this);
2149 * @param e DOCUMENT ME!
2151 public void font_actionPerformed(ActionEvent e)
2153 new FontChooser(alignPanel);
2160 * @param e DOCUMENT ME!
2162 protected void seqLimit_actionPerformed(ActionEvent e)
2164 viewport.setShowJVSuffix(seqLimits.isSelected());
2166 alignPanel.idPanel.idCanvas.setPreferredSize(alignPanel.calculateIdWidth());
2167 alignPanel.paintAlignment(true);
2170 public void idRightAlign_actionPerformed(ActionEvent e)
2172 viewport.rightAlignIds = idRightAlign.isSelected();
2173 alignPanel.paintAlignment(true);
2181 * @param e DOCUMENT ME!
2183 protected void colourTextMenuItem_actionPerformed(ActionEvent e)
2185 viewport.setColourText(colourTextMenuItem.isSelected());
2186 alignPanel.paintAlignment(true);
2192 * @param e DOCUMENT ME!
2194 public void wrapMenuItem_actionPerformed(ActionEvent e)
2196 scaleAbove.setVisible(wrapMenuItem.isSelected());
2197 scaleLeft.setVisible(wrapMenuItem.isSelected());
2198 scaleRight.setVisible(wrapMenuItem.isSelected());
2199 viewport.setWrapAlignment(wrapMenuItem.isSelected());
2200 alignPanel.setWrapAlignment(wrapMenuItem.isSelected());
2203 public void showAllSeqs_actionPerformed(ActionEvent e)
2205 viewport.showAllHiddenSeqs();
2208 public void showAllColumns_actionPerformed(ActionEvent e)
2210 viewport.showAllHiddenColumns();
2214 public void hideSelSequences_actionPerformed(ActionEvent e)
2216 viewport.hideAllSelectedSeqs();
2217 alignPanel.paintAlignment(true);
2220 public void hideSelColumns_actionPerformed(ActionEvent e)
2222 viewport.hideSelectedColumns();
2223 alignPanel.paintAlignment(true);
2226 public void hiddenMarkers_actionPerformed(ActionEvent e)
2228 viewport.setShowHiddenMarkers(hiddenMarkers.isSelected());
2235 * @param e DOCUMENT ME!
2237 protected void scaleAbove_actionPerformed(ActionEvent e)
2239 viewport.setScaleAboveWrapped(scaleAbove.isSelected());
2240 alignPanel.paintAlignment(true);
2246 * @param e DOCUMENT ME!
2248 protected void scaleLeft_actionPerformed(ActionEvent e)
2250 viewport.setScaleLeftWrapped(scaleLeft.isSelected());
2251 alignPanel.paintAlignment(true);
2257 * @param e DOCUMENT ME!
2259 protected void scaleRight_actionPerformed(ActionEvent e)
2261 viewport.setScaleRightWrapped(scaleRight.isSelected());
2262 alignPanel.paintAlignment(true);
2268 * @param e DOCUMENT ME!
2270 public void viewBoxesMenuItem_actionPerformed(ActionEvent e)
2272 viewport.setShowBoxes(viewBoxesMenuItem.isSelected());
2273 alignPanel.paintAlignment(true);
2279 * @param e DOCUMENT ME!
2281 public void viewTextMenuItem_actionPerformed(ActionEvent e)
2283 viewport.setShowText(viewTextMenuItem.isSelected());
2284 alignPanel.paintAlignment(true);
2290 * @param e DOCUMENT ME!
2292 protected void renderGapsMenuItem_actionPerformed(ActionEvent e)
2294 viewport.setRenderGaps(renderGapsMenuItem.isSelected());
2295 alignPanel.paintAlignment(true);
2299 public FeatureSettings featureSettings;
2300 public void featureSettings_actionPerformed(ActionEvent e)
2302 if(featureSettings !=null )
2304 featureSettings.close();
2305 featureSettings = null;
2307 featureSettings = new FeatureSettings(this);
2313 * @param evt DOCUMENT ME!
2315 public void showSeqFeatures_actionPerformed(ActionEvent evt)
2317 viewport.setShowSequenceFeatures(showSeqFeatures.isSelected());
2318 alignPanel.paintAlignment(true);
2319 if (alignPanel.getOverviewPanel() != null)
2321 alignPanel.getOverviewPanel().updateOverviewImage();
2328 * @param e DOCUMENT ME!
2330 public void annotationPanelMenuItem_actionPerformed(ActionEvent e)
2332 viewport.setShowAnnotation(annotationPanelMenuItem.isSelected());
2333 alignPanel.setAnnotationVisible(annotationPanelMenuItem.isSelected());
2336 public void alignmentProperties()
2338 JEditorPane editPane = new JEditorPane("text/html","");
2339 editPane.setEditable(false);
2340 StringBuffer contents = new StringBuffer("<html>");
2343 int min=Integer.MAX_VALUE, max=0;
2344 for(int i=0; i<viewport.alignment.getHeight(); i++)
2346 int size = viewport.alignment.getSequenceAt(i).getEnd()
2347 -viewport.alignment.getSequenceAt(i).getStart();
2354 avg = avg/(float)viewport.alignment.getHeight();
2356 contents.append("<br>Sequences: "+ viewport.alignment.getHeight());
2357 contents.append("<br>Minimum Sequence Length: "+min);
2358 contents.append("<br>Maximum Sequence Length: "+max);
2359 contents.append("<br>Average Length: "+(int)avg);
2361 if (((Alignment)viewport.alignment).getProperties() != null)
2363 Hashtable props = ((Alignment)viewport.alignment).getProperties();
2364 Enumeration en = props.keys();
2365 contents.append("<br><br><table border=\"1\">");
2366 while(en.hasMoreElements())
2368 String key = en.nextElement().toString();
2369 StringBuffer val = new StringBuffer();
2370 String vals = props.get(key).toString();
2373 npos = vals.indexOf("\n",pos);
2376 val.append(vals.substring(pos));
2378 val.append(vals.substring(pos, npos));
2383 contents.append("<tr><td>"+key+"</td><td>"+val+"</td></tr>");
2385 contents.append("</table>");
2387 editPane.setText(contents.toString()+"</html>");
2388 JInternalFrame frame = new JInternalFrame();
2389 frame.getContentPane().add(new JScrollPane(editPane));
2391 Desktop.instance.addInternalFrame(frame,"Alignment Properties: "+getTitle(),500,400);
2398 * @param e DOCUMENT ME!
2400 public void overviewMenuItem_actionPerformed(ActionEvent e)
2402 if (alignPanel.overviewPanel != null)
2407 JInternalFrame frame = new JInternalFrame();
2408 OverviewPanel overview = new OverviewPanel(alignPanel);
2409 frame.setContentPane(overview);
2410 Desktop.addInternalFrame(frame, "Overview " + this.getTitle(),
2411 frame.getWidth(), frame.getHeight());
2413 frame.setLayer(JLayeredPane.PALETTE_LAYER);
2414 frame.addInternalFrameListener(new javax.swing.event.InternalFrameAdapter()
2416 public void internalFrameClosed(
2417 javax.swing.event.InternalFrameEvent evt)
2419 alignPanel.setOverviewPanel(null);
2424 alignPanel.setOverviewPanel(overview);
2427 public void textColour_actionPerformed(ActionEvent e)
2429 new TextColourChooser().chooseColour(alignPanel, null);
2435 * @param e DOCUMENT ME!
2437 protected void noColourmenuItem_actionPerformed(ActionEvent e)
2445 * @param e DOCUMENT ME!
2447 public void clustalColour_actionPerformed(ActionEvent e)
2449 changeColour(new ClustalxColourScheme(
2450 viewport.alignment.getSequences(), viewport.alignment.getWidth()));
2456 * @param e DOCUMENT ME!
2458 public void zappoColour_actionPerformed(ActionEvent e)
2460 changeColour(new ZappoColourScheme());
2466 * @param e DOCUMENT ME!
2468 public void taylorColour_actionPerformed(ActionEvent e)
2470 changeColour(new TaylorColourScheme());
2476 * @param e DOCUMENT ME!
2478 public void hydrophobicityColour_actionPerformed(ActionEvent e)
2480 changeColour(new HydrophobicColourScheme());
2486 * @param e DOCUMENT ME!
2488 public void helixColour_actionPerformed(ActionEvent e)
2490 changeColour(new HelixColourScheme());
2496 * @param e DOCUMENT ME!
2498 public void strandColour_actionPerformed(ActionEvent e)
2500 changeColour(new StrandColourScheme());
2506 * @param e DOCUMENT ME!
2508 public void turnColour_actionPerformed(ActionEvent e)
2510 changeColour(new TurnColourScheme());
2516 * @param e DOCUMENT ME!
2518 public void buriedColour_actionPerformed(ActionEvent e)
2520 changeColour(new BuriedColourScheme());
2526 * @param e DOCUMENT ME!
2528 public void nucleotideColour_actionPerformed(ActionEvent e)
2530 changeColour(new NucleotideColourScheme());
2533 public void annotationColour_actionPerformed(ActionEvent e)
2535 new AnnotationColourChooser(viewport, alignPanel);
2542 * @param e DOCUMENT ME!
2544 protected void applyToAllGroups_actionPerformed(ActionEvent e)
2546 viewport.setColourAppliesToAllGroups(applyToAllGroups.isSelected());
2552 * @param cs DOCUMENT ME!
2554 public void changeColour(ColourSchemeI cs)
2560 if (viewport.getAbovePIDThreshold())
2562 threshold = SliderPanel.setPIDSliderSource(alignPanel, cs,
2565 cs.setThreshold(threshold,
2566 viewport.getIgnoreGapsConsensus());
2568 viewport.setGlobalColourScheme(cs);
2572 cs.setThreshold(0, viewport.getIgnoreGapsConsensus());
2575 if (viewport.getConservationSelected())
2578 Alignment al = (Alignment) viewport.alignment;
2579 Conservation c = new Conservation("All",
2580 ResidueProperties.propHash, 3,
2581 al.getSequences(), 0,
2585 c.verdict(false, viewport.ConsPercGaps);
2587 cs.setConservation(c);
2589 cs.setConservationInc(SliderPanel.setConservationSlider(alignPanel, cs,
2594 cs.setConservation(null);
2597 cs.setConsensus(viewport.hconsensus);
2600 viewport.setGlobalColourScheme(cs);
2602 if (viewport.getColourAppliesToAllGroups())
2604 Vector groups = viewport.alignment.getGroups();
2606 for (int i = 0; i < groups.size(); i++)
2608 SequenceGroup sg = (SequenceGroup) groups.elementAt(i);
2616 if (cs instanceof ClustalxColourScheme)
2618 sg.cs = new ClustalxColourScheme(
2619 sg.getSequences(viewport.hiddenRepSequences), sg.getWidth());
2621 else if (cs instanceof UserColourScheme)
2623 sg.cs = new UserColourScheme( ( (UserColourScheme) cs).getColours());
2629 sg.cs = (ColourSchemeI) cs.getClass().newInstance();
2631 catch (Exception ex)
2636 if (viewport.getAbovePIDThreshold()
2637 || cs instanceof PIDColourScheme
2638 || cs instanceof Blosum62ColourScheme)
2640 sg.cs.setThreshold(threshold,
2641 viewport.getIgnoreGapsConsensus());
2643 sg.cs.setConsensus(AAFrequency.calculate(
2644 sg.getSequences(viewport.hiddenRepSequences), sg.getStartRes(),
2649 sg.cs.setThreshold(0, viewport.getIgnoreGapsConsensus());
2653 if (viewport.getConservationSelected())
2655 Conservation c = new Conservation("Group",
2656 ResidueProperties.propHash, 3,
2657 sg.getSequences(viewport.
2658 hiddenRepSequences),
2662 c.verdict(false, viewport.ConsPercGaps);
2663 sg.cs.setConservation(c);
2667 sg.cs.setConservation(null);
2672 if (alignPanel.getOverviewPanel() != null)
2674 alignPanel.getOverviewPanel().updateOverviewImage();
2680 alignPanel.paintAlignment(true);
2686 * @param e DOCUMENT ME!
2688 protected void modifyPID_actionPerformed(ActionEvent e)
2690 if (viewport.getAbovePIDThreshold() && viewport.globalColourScheme!=null)
2692 SliderPanel.setPIDSliderSource(alignPanel,
2693 viewport.getGlobalColourScheme(),
2695 SliderPanel.showPIDSlider();
2702 * @param e DOCUMENT ME!
2704 protected void modifyConservation_actionPerformed(ActionEvent e)
2706 if (viewport.getConservationSelected() && viewport.globalColourScheme!=null)
2708 SliderPanel.setConservationSlider(alignPanel,
2709 viewport.globalColourScheme,
2711 SliderPanel.showConservationSlider();
2718 * @param e DOCUMENT ME!
2720 protected void conservationMenuItem_actionPerformed(ActionEvent e)
2722 viewport.setConservationSelected(conservationMenuItem.isSelected());
2724 viewport.setAbovePIDThreshold(false);
2725 abovePIDThreshold.setSelected(false);
2727 changeColour(viewport.getGlobalColourScheme());
2729 modifyConservation_actionPerformed(null);
2735 * @param e DOCUMENT ME!
2737 public void abovePIDThreshold_actionPerformed(ActionEvent e)
2739 viewport.setAbovePIDThreshold(abovePIDThreshold.isSelected());
2741 conservationMenuItem.setSelected(false);
2742 viewport.setConservationSelected(false);
2744 changeColour(viewport.getGlobalColourScheme());
2746 modifyPID_actionPerformed(null);
2752 * @param e DOCUMENT ME!
2754 public void userDefinedColour_actionPerformed(ActionEvent e)
2756 if (e.getActionCommand().equals("User Defined..."))
2758 new UserDefinedColours(alignPanel, null);
2762 UserColourScheme udc = (UserColourScheme) UserDefinedColours.
2763 getUserColourSchemes().get(e.getActionCommand());
2769 public void updateUserColourMenu()
2772 Component[] menuItems = colourMenu.getMenuComponents();
2773 int i, iSize = menuItems.length;
2774 for (i = 0; i < iSize; i++)
2776 if (menuItems[i].getName() != null &&
2777 menuItems[i].getName().equals("USER_DEFINED"))
2779 colourMenu.remove(menuItems[i]);
2783 if (jalview.gui.UserDefinedColours.getUserColourSchemes() != null)
2785 java.util.Enumeration userColours = jalview.gui.UserDefinedColours.
2786 getUserColourSchemes().keys();
2788 while (userColours.hasMoreElements())
2790 final JRadioButtonMenuItem radioItem = new JRadioButtonMenuItem(
2792 nextElement().toString());
2793 radioItem.setName("USER_DEFINED");
2794 radioItem.addMouseListener(new MouseAdapter()
2796 public void mousePressed(MouseEvent evt)
2798 if(evt.isControlDown() || SwingUtilities.isRightMouseButton(evt))
2800 radioItem.removeActionListener(radioItem.getActionListeners()[0]);
2802 int option = JOptionPane.showInternalConfirmDialog(jalview.gui.
2804 "Remove from default list?",
2805 "Remove user defined colour",
2806 JOptionPane.YES_NO_OPTION);
2807 if(option == JOptionPane.YES_OPTION)
2809 jalview.gui.UserDefinedColours.removeColourFromDefaults(
2810 radioItem.getText());
2811 colourMenu.remove(radioItem);
2815 radioItem.addActionListener(new ActionListener()
2817 public void actionPerformed(ActionEvent evt)
2819 userDefinedColour_actionPerformed(evt);
2826 radioItem.addActionListener(new ActionListener()
2828 public void actionPerformed(ActionEvent evt)
2830 userDefinedColour_actionPerformed(evt);
2834 colourMenu.insert(radioItem, 15);
2835 colours.add(radioItem);
2843 * @param e DOCUMENT ME!
2845 public void PIDColour_actionPerformed(ActionEvent e)
2847 changeColour(new PIDColourScheme());
2853 * @param e DOCUMENT ME!
2855 public void BLOSUM62Colour_actionPerformed(ActionEvent e)
2857 changeColour(new Blosum62ColourScheme());
2863 * @param e DOCUMENT ME!
2865 public void sortPairwiseMenuItem_actionPerformed(ActionEvent e)
2867 SequenceI [] oldOrder = viewport.getAlignment().getSequencesArray();
2868 AlignmentSorter.sortByPID(viewport.getAlignment(),
2869 viewport.getAlignment().getSequenceAt(0));
2870 addHistoryItem(new OrderCommand("Pairwise Sort", oldOrder,
2871 viewport.alignment));
2872 alignPanel.paintAlignment(true);
2878 * @param e DOCUMENT ME!
2880 public void sortIDMenuItem_actionPerformed(ActionEvent e)
2882 SequenceI [] oldOrder = viewport.getAlignment().getSequencesArray();
2883 AlignmentSorter.sortByID(viewport.getAlignment());
2884 addHistoryItem(new OrderCommand("ID Sort", oldOrder, viewport.alignment));
2885 alignPanel.paintAlignment(true);
2891 * @param e DOCUMENT ME!
2893 public void sortGroupMenuItem_actionPerformed(ActionEvent e)
2895 SequenceI [] oldOrder = viewport.getAlignment().getSequencesArray();
2896 AlignmentSorter.sortByGroup(viewport.getAlignment());
2897 addHistoryItem(new OrderCommand("Group Sort", oldOrder, viewport.alignment));
2899 alignPanel.paintAlignment(true);
2904 * @param e DOCUMENT ME!
2906 public void removeRedundancyMenuItem_actionPerformed(ActionEvent e)
2908 new RedundancyPanel(alignPanel, this);
2915 * @param e DOCUMENT ME!
2917 public void pairwiseAlignmentMenuItem_actionPerformed(ActionEvent e)
2919 if ( (viewport.getSelectionGroup() == null) ||
2920 (viewport.getSelectionGroup().getSize() < 2))
2922 JOptionPane.showInternalMessageDialog(this,
2923 "You must select at least 2 sequences.",
2924 "Invalid Selection",
2925 JOptionPane.WARNING_MESSAGE);
2929 JInternalFrame frame = new JInternalFrame();
2930 frame.setContentPane(new PairwiseAlignPanel(viewport));
2931 Desktop.addInternalFrame(frame, "Pairwise Alignment", 600, 500);
2938 * @param e DOCUMENT ME!
2940 public void PCAMenuItem_actionPerformed(ActionEvent e)
2942 if ( ( (viewport.getSelectionGroup() != null) &&
2943 (viewport.getSelectionGroup().getSize() < 4) &&
2944 (viewport.getSelectionGroup().getSize() > 0)) ||
2945 (viewport.getAlignment().getHeight() < 4))
2947 JOptionPane.showInternalMessageDialog(this,
2948 "Principal component analysis must take\n" +
2949 "at least 4 input sequences.",
2950 "Sequence selection insufficient",
2951 JOptionPane.WARNING_MESSAGE);
2956 new PCAPanel(alignPanel);
2960 public void autoCalculate_actionPerformed(ActionEvent e)
2962 viewport.autoCalculateConsensus = autoCalculate.isSelected();
2963 if(viewport.autoCalculateConsensus)
2965 viewport.firePropertyChange("alignment",
2967 viewport.getAlignment().getSequences());
2975 * @param e DOCUMENT ME!
2977 public void averageDistanceTreeMenuItem_actionPerformed(ActionEvent e)
2979 NewTreePanel("AV", "PID", "Average distance tree using PID");
2985 * @param e DOCUMENT ME!
2987 public void neighbourTreeMenuItem_actionPerformed(ActionEvent e)
2989 NewTreePanel("NJ", "PID", "Neighbour joining tree using PID");
2995 * @param e DOCUMENT ME!
2997 protected void njTreeBlosumMenuItem_actionPerformed(ActionEvent e)
2999 NewTreePanel("NJ", "BL", "Neighbour joining tree using BLOSUM62");
3005 * @param e DOCUMENT ME!
3007 protected void avTreeBlosumMenuItem_actionPerformed(ActionEvent e)
3009 NewTreePanel("AV", "BL", "Average distance tree using BLOSUM62");
3015 * @param type DOCUMENT ME!
3016 * @param pwType DOCUMENT ME!
3017 * @param title DOCUMENT ME!
3019 void NewTreePanel(String type, String pwType, String title)
3023 if (viewport.getSelectionGroup() != null)
3025 if (viewport.getSelectionGroup().getSize() < 3)
3027 JOptionPane.showMessageDialog(Desktop.desktop,
3028 "You need to have more than two sequences selected to build a tree!",
3029 "Not enough sequences",
3030 JOptionPane.WARNING_MESSAGE);
3035 SequenceGroup sg = viewport.getSelectionGroup();
3037 /* Decide if the selection is a column region */
3038 while (s < sg.getSize())
3040 if ( ( (SequenceI) sg.getSequences(null).elementAt(s++)).getLength() <
3043 JOptionPane.showMessageDialog(Desktop.desktop,
3044 "The selected region to create a tree may\nonly contain residues or gaps.\n" +
3045 "Try using the Pad function in the edit menu,\n" +
3046 "or one of the multiple sequence alignment web services.",
3047 "Sequences in selection are not aligned",
3048 JOptionPane.WARNING_MESSAGE);
3054 title = title + " on region";
3055 tp = new TreePanel(alignPanel, type, pwType);
3059 //are the sequences aligned?
3060 if (!viewport.alignment.isAligned())
3062 JOptionPane.showMessageDialog(Desktop.desktop,
3063 "The sequences must be aligned before creating a tree.\n" +
3064 "Try using the Pad function in the edit menu,\n" +
3065 "or one of the multiple sequence alignment web services.",
3066 "Sequences not aligned",
3067 JOptionPane.WARNING_MESSAGE);
3072 if(viewport.alignment.getHeight()<2)
3077 tp = new TreePanel(alignPanel, type, pwType);
3082 if(viewport.viewName!=null)
3084 title+= viewport.viewName+" of ";
3087 title += this.title;
3089 Desktop.addInternalFrame(tp, title, 600, 500);
3095 * @param title DOCUMENT ME!
3096 * @param order DOCUMENT ME!
3098 public void addSortByOrderMenuItem(String title, final AlignmentOrder order)
3100 final JMenuItem item = new JMenuItem("by " + title);
3102 item.addActionListener(new java.awt.event.ActionListener()
3104 public void actionPerformed(ActionEvent e)
3106 SequenceI [] oldOrder = viewport.getAlignment().getSequencesArray();
3108 // TODO: JBPNote - have to map order entries to curent SequenceI pointers
3109 AlignmentSorter.sortBy(viewport.getAlignment(), order);
3111 addHistoryItem(new OrderCommand(order.getName(), oldOrder,
3112 viewport.alignment));
3114 alignPanel.paintAlignment(true);
3119 * Add a new sort by annotation score menu item
3120 * @param sort the menu to add the option to
3121 * @param scoreLabel the label used to retrieve scores for each sequence on the alignment
3123 public void addSortByAnnotScoreMenuItem(JMenu sort, final String scoreLabel)
3125 final JMenuItem item = new JMenuItem(scoreLabel);
3127 item.addActionListener(new java.awt.event.ActionListener()
3129 public void actionPerformed(ActionEvent e)
3131 SequenceI [] oldOrder = viewport.getAlignment().getSequencesArray();
3132 AlignmentSorter.sortByAnnotationScore(scoreLabel, viewport.getAlignment());
3133 addHistoryItem(new OrderCommand("Sort by "+scoreLabel, oldOrder, viewport.alignment));
3134 alignPanel.paintAlignment(true);
3139 * last hash for alignment's annotation array - used to minimise cost of rebuild.
3141 protected int _annotationScoreVectorHash;
3143 * search the alignment and rebuild the sort by annotation score submenu
3144 * the last alignment annotation vector hash is stored to minimize
3145 * cost of rebuilding in subsequence calls.
3148 public void buildSortByAnnotationScoresMenu()
3150 if(viewport.alignment.getAlignmentAnnotation()==null)
3155 if (viewport.alignment.getAlignmentAnnotation().hashCode()!=_annotationScoreVectorHash)
3157 sortByAnnotScore.removeAll();
3158 // almost certainly a quicker way to do this - but we keep it simple
3159 Hashtable scoreSorts=new Hashtable();
3160 AlignmentAnnotation aann[];
3161 Enumeration sq = viewport.alignment.getSequences().elements();
3162 while (sq.hasMoreElements())
3164 aann = ((SequenceI) sq.nextElement()).getAnnotation();
3165 for (int i=0;aann!=null && i<aann.length; i++)
3167 if (aann[i].hasScore() && aann[i].sequenceRef!=null)
3169 scoreSorts.put(aann[i].label, aann[i].label);
3173 Enumeration labels = scoreSorts.keys();
3174 while (labels.hasMoreElements())
3176 addSortByAnnotScoreMenuItem(sortByAnnotScore, (String) labels.nextElement());
3178 sortByAnnotScore.setVisible(scoreSorts.size()>0);
3181 _annotationScoreVectorHash =
3182 viewport.alignment.getAlignmentAnnotation().hashCode();
3187 * Maintain the Order by->Displayed Tree menu.
3188 * Creates a new menu item for a TreePanel with an appropriate
3189 * <code>jalview.analysis.AlignmentSorter</code> call. Listeners are added
3190 * to remove the menu item when the treePanel is closed, and adjust
3191 * the tree leaf to sequence mapping when the alignment is modified.
3192 * @param treePanel Displayed tree window.
3193 * @param title SortBy menu item title.
3195 public void buildTreeMenu()
3197 sortByTreeMenu.removeAll();
3199 Vector comps = (Vector) PaintRefresher.components.get(viewport.
3200 getSequenceSetId());
3201 Vector treePanels = new Vector();
3202 int i, iSize = comps.size();
3203 for(i=0; i<iSize; i++)
3205 if(comps.elementAt(i) instanceof TreePanel)
3207 treePanels.add(comps.elementAt(i));
3211 iSize = treePanels.size();
3215 sortByTreeMenu.setVisible(false);
3219 sortByTreeMenu.setVisible(true);
3221 for(i=0; i<treePanels.size(); i++)
3223 TreePanel tp = (TreePanel)treePanels.elementAt(i);
3224 final JMenuItem item = new JMenuItem(tp.getTitle());
3225 final NJTree tree = ((TreePanel)treePanels.elementAt(i)).getTree();
3226 item.addActionListener(new java.awt.event.ActionListener()
3228 public void actionPerformed(ActionEvent e)
3230 SequenceI[] oldOrder = viewport.getAlignment().getSequencesArray();
3231 AlignmentSorter.sortByTree(viewport.getAlignment(), tree);
3233 addHistoryItem(new OrderCommand("Tree Sort",
3235 viewport.alignment));
3237 alignPanel.paintAlignment(true);
3241 sortByTreeMenu.add(item);
3246 * Work out whether the whole set of sequences
3247 * or just the selected set will be submitted for multiple alignment.
3250 private jalview.datamodel.AlignmentView gatherSequencesForAlignment()
3252 // Now, check we have enough sequences
3253 AlignmentView msa = null;
3255 if ( (viewport.getSelectionGroup() != null) &&
3256 (viewport.getSelectionGroup().getSize() > 1))
3258 // JBPNote UGLY! To prettify, make SequenceGroup and Alignment conform to some common interface!
3259 /*SequenceGroup seqs = viewport.getSelectionGroup();
3261 msa = new SequenceI[sz = seqs.getSize(false)];
3263 for (int i = 0; i < sz; i++)
3265 msa[i] = (SequenceI) seqs.getSequenceAt(i);
3267 msa = viewport.getAlignmentView(true);
3271 /*Vector seqs = viewport.getAlignment().getSequences();
3273 if (seqs.size() > 1)
3275 msa = new SequenceI[seqs.size()];
3277 for (int i = 0; i < seqs.size(); i++)
3279 msa[i] = (SequenceI) seqs.elementAt(i);
3282 msa = viewport.getAlignmentView(false);
3288 * Decides what is submitted to a secondary structure prediction service,
3289 * the currently selected sequence, or the currently selected alignment
3290 * (where the first sequence in the set is the one that the prediction
3293 AlignmentView gatherSeqOrMsaForSecStrPrediction()
3295 AlignmentView seqs = null;
3297 if ( (viewport.getSelectionGroup() != null) &&
3298 (viewport.getSelectionGroup().getSize() > 0))
3300 seqs = viewport.getAlignmentView(true);
3304 seqs = viewport.getAlignmentView(false);
3306 // limit sequences - JBPNote in future - could spawn multiple prediction jobs
3307 // TODO: viewport.alignment.isAligned is a global state - the local selection may well be aligned - we preserve 2.0.8 behaviour for moment.
3308 if (!viewport.alignment.isAligned())
3310 seqs.setSequences(new SeqCigar[]
3311 {seqs.getSequences()[0]});
3318 * @param e DOCUMENT ME!
3320 protected void LoadtreeMenuItem_actionPerformed(ActionEvent e)
3322 // Pick the tree file
3323 JalviewFileChooser chooser = new JalviewFileChooser(jalview.bin.Cache.
3326 chooser.setFileView(new JalviewFileView());
3327 chooser.setDialogTitle("Select a newick-like tree file");
3328 chooser.setToolTipText("Load a tree file");
3330 int value = chooser.showOpenDialog(null);
3332 if (value == JalviewFileChooser.APPROVE_OPTION)
3334 String choice = chooser.getSelectedFile().getPath();
3335 jalview.bin.Cache.setProperty("LAST_DIRECTORY", choice);
3336 jalview.io.NewickFile fin = null;
3339 fin = new jalview.io.NewickFile(choice,
3341 viewport.setCurrentTree(ShowNewickTree(fin, choice).getTree());
3343 catch (Exception ex)
3345 JOptionPane.showMessageDialog(Desktop.desktop,
3347 "Problem reading tree file",
3348 JOptionPane.WARNING_MESSAGE);
3349 ex.printStackTrace();
3351 if (fin!=null && fin.hasWarningMessage())
3353 JOptionPane.showMessageDialog(Desktop.desktop,
3354 fin.getWarningMessage(),
3355 "Possible problem with tree file",
3356 JOptionPane.WARNING_MESSAGE);
3362 public TreePanel ShowNewickTree(NewickFile nf, String title)
3364 return ShowNewickTree(nf,title,600,500,4,5);
3367 public TreePanel ShowNewickTree(NewickFile nf, String title,
3368 AlignmentView input)
3370 return ShowNewickTree(nf,title, input, 600,500,4,5);
3373 public TreePanel ShowNewickTree(NewickFile nf, String title, int w, int h,
3376 return ShowNewickTree(nf, title, null, w, h, x, y);
3379 * Add a treeviewer for the tree extracted from a newick file object to the current alignment view
3381 * @param nf the tree
3382 * @param title tree viewer title
3383 * @param input Associated alignment input data (or null)
3388 * @return TreePanel handle
3390 public TreePanel ShowNewickTree(NewickFile nf, String title,
3391 AlignmentView input, int w, int h, int x,
3394 TreePanel tp = null;
3400 if (nf.getTree() != null)
3402 tp = new TreePanel(alignPanel,
3411 tp.setLocation(x,y);
3415 Desktop.addInternalFrame(tp, title, w, h);
3418 catch (Exception ex)
3420 ex.printStackTrace();
3428 * Generates menu items and listener event actions for web service clients
3431 public void BuildWebServiceMenu()
3433 // TODO: add support for context dependent disabling of services based on alignment and current selection
3434 // TODO: refactor to allow list of AbstractName/Handler bindings to be stored or retrieved from elsewhere
3435 // TODO: add additional serviceHandle parameter to specify abstract handler class independently of AbstractName
3436 // TODO: add in rediscovery GUI function to restart discoverer
3437 // TODO: group services by location as well as function and/or introduce object broker mechanism.
3438 if ( (Discoverer.services != null)
3439 && (Discoverer.services.size() > 0))
3441 Vector msaws = (Vector) Discoverer.services.get("MsaWS");
3442 Vector secstrpr = (Vector) Discoverer.services.get("SecStrPred");
3443 Vector wsmenu = new Vector();
3444 final AlignFrame af = this;
3447 // Add any Multiple Sequence Alignment Services
3448 final JMenu msawsmenu = new JMenu("Alignment");
3449 for (int i = 0, j = msaws.size(); i < j; i++)
3451 final ext.vamsas.ServiceHandle sh = (ext.vamsas.ServiceHandle) msaws.
3453 final JMenuItem method = new JMenuItem(sh.getName());
3454 method.addActionListener(new ActionListener()
3456 public void actionPerformed(ActionEvent e)
3458 AlignmentView msa = gatherSequencesForAlignment();
3459 new jalview.ws.MsaWSClient(sh, title, msa,
3461 viewport.getAlignment().getDataset(),
3467 msawsmenu.add(method);
3468 // Deal with services that we know accept partial alignments.
3469 if (sh.getName().indexOf("lustal") > -1)
3471 // We know that ClustalWS can accept partial alignments for refinement.
3472 final JMenuItem methodR = new JMenuItem(sh.getName()+" Realign");
3473 methodR.addActionListener(new ActionListener()
3475 public void actionPerformed(ActionEvent e)
3477 AlignmentView msa = gatherSequencesForAlignment();
3478 new jalview.ws.MsaWSClient(sh, title, msa,
3480 viewport.getAlignment().getDataset(),
3486 msawsmenu.add(methodR);
3490 wsmenu.add(msawsmenu);
3492 if (secstrpr != null)
3494 // Add any secondary structure prediction services
3495 final JMenu secstrmenu = new JMenu("Secondary Structure Prediction");
3496 for (int i = 0, j = secstrpr.size(); i < j; i++)
3498 final ext.vamsas.ServiceHandle sh = (ext.vamsas.ServiceHandle)
3500 final JMenuItem method = new JMenuItem(sh.getName());
3501 method.addActionListener(new ActionListener()
3503 public void actionPerformed(ActionEvent e)
3505 AlignmentView msa = gatherSeqOrMsaForSecStrPrediction();
3506 if (msa.getSequences().length == 1)
3508 // Single Sequence prediction
3509 new jalview.ws.JPredClient(sh, title, false, msa, af, true);
3513 if (msa.getSequences().length > 1)
3515 // Sequence profile based prediction
3516 new jalview.ws.JPredClient(sh,
3517 title, true, msa, af, true);
3522 secstrmenu.add(method);
3524 wsmenu.add(secstrmenu);
3526 resetWebServiceMenu();
3527 for (int i = 0, j = wsmenu.size(); i < j; i++)
3529 webService.add( (JMenu) wsmenu.get(i));
3534 resetWebServiceMenu();
3535 this.webService.add(this.webServiceNoServices);
3541 * empty the web service menu and add any ad-hoc functions
3542 * not dynamically discovered.
3545 private void resetWebServiceMenu()
3547 webService.removeAll();
3548 // Temporary hack - DBRef Fetcher always top level ws entry.
3549 JMenuItem rfetch = new JMenuItem("Fetch DB References");
3550 rfetch.setToolTipText("Retrieve and parse uniprot records for the alignment or the currently selected sequences");
3551 webService.add(rfetch);
3552 rfetch.addActionListener(new ActionListener() {
3554 public void actionPerformed(ActionEvent e)
3556 new jalview.ws.DBRefFetcher(
3557 alignPanel.av.getSequenceSelection(),
3558 alignPanel.alignFrame).fetchDBRefs(false);
3564 /* public void vamsasStore_actionPerformed(ActionEvent e)
3566 JalviewFileChooser chooser = new JalviewFileChooser(jalview.bin.Cache.
3567 getProperty("LAST_DIRECTORY"));
3569 chooser.setFileView(new JalviewFileView());
3570 chooser.setDialogTitle("Export to Vamsas file");
3571 chooser.setToolTipText("Export");
3573 int value = chooser.showSaveDialog(this);
3575 if (value == JalviewFileChooser.APPROVE_OPTION)
3577 jalview.io.VamsasDatastore vs = new jalview.io.VamsasDatastore(viewport);
3578 //vs.store(chooser.getSelectedFile().getAbsolutePath() );
3579 vs.storeJalview( chooser.getSelectedFile().getAbsolutePath(), this);
3583 * prototype of an automatically enabled/disabled analysis function
3586 protected void setShowProductsEnabled()
3588 SequenceI [] selection = viewport.getSequenceSelection();
3589 if (canShowProducts(selection, viewport.getSelectionGroup()!=null, viewport.getAlignment().getDataset()))
3591 showProducts.setEnabled(true);
3594 showProducts.setEnabled(false);
3598 * search selection for sequence xRef products and build the
3599 * show products menu.
3602 * @return true if showProducts menu should be enabled.
3604 public boolean canShowProducts(SequenceI[] selection, boolean isRegionSelection, Alignment dataset)
3606 boolean showp=false;
3608 showProducts.removeAll();
3609 final boolean dna = viewport.getAlignment().isNucleotide();
3610 final Alignment ds = dataset;
3611 String[] ptypes = CrossRef.findSequenceXrefTypes(dna, selection, dataset);
3612 //Object[] prods = CrossRef.buildXProductsList(viewport.getAlignment().isNucleotide(), selection, dataset, true);
3613 final SequenceI[] sel = selection;
3614 for (int t=0; ptypes!=null && t<ptypes.length; t++)
3617 final boolean isRegSel = isRegionSelection;
3618 final AlignFrame af = this;
3619 final String source = ptypes[t];
3620 JMenuItem xtype = new JMenuItem(ptypes[t]);
3621 xtype.addActionListener(new ActionListener() {
3623 public void actionPerformed(ActionEvent e)
3625 // TODO: new thread for this call with vis-delay
3626 af.showProductsFor(sel, ds, isRegSel, dna, source);
3630 showProducts.add(xtype);
3632 showProducts.setVisible(showp);
3633 showProducts.setEnabled(showp);
3634 } catch (Exception e)
3636 jalview.bin.Cache.log.warn("canTranslate threw an exception - please report to help@jalview.org",e);
3641 protected void showProductsFor(SequenceI[] sel, Alignment ds, boolean isRegSel, boolean dna, String source)
3643 final boolean fisRegSel = isRegSel;
3644 final boolean fdna = dna;
3645 final String fsrc = source;
3646 final AlignFrame ths = this;
3647 final SequenceI[] fsel = sel;
3648 Runnable foo = new Runnable() {
3652 final long sttime = System.currentTimeMillis();
3653 ths.setProgressBar("Searching for sequences from "+fsrc, sttime);
3655 Alignment ds = ths.getViewport().alignment.getDataset(); // update our local dataset reference
3656 Alignment prods = CrossRef.findXrefSequences(fsel, fdna, fsrc, ds);
3659 SequenceI[] sprods = new SequenceI[prods.getHeight()];
3660 for (int s=0; s<sprods.length;s++)
3662 sprods[s] = (prods.getSequenceAt(s)).deriveSequence();
3663 if (ds.getSequences()==null || !ds.getSequences().contains(sprods[s].getDatasetSequence()))
3664 ds.addSequence(sprods[s].getDatasetSequence());
3665 sprods[s].updatePDBIds();
3667 Alignment al = new Alignment(sprods);
3668 AlignedCodonFrame[] cf = prods.getCodonFrames();
3669 for (int s=0; cf!=null && s<cf.length; s++)
3671 al.addCodonFrame(cf[s]);
3675 AlignFrame naf = new AlignFrame(al, DEFAULT_WIDTH, DEFAULT_HEIGHT);
3676 String newtitle =""+((fdna) ? "Proteins " : "Nucleotides ") + " for "+((fisRegSel) ? "selected region of " : "")
3678 Desktop.addInternalFrame(naf, newtitle, DEFAULT_WIDTH,
3681 System.err.println("No Sequences generated for xRef type "+fsrc);
3686 jalview.bin.Cache.log.error("Exception when finding crossreferences",e);
3690 jalview.bin.Cache.log.error("Error when finding crossreferences",e);
3692 ths.setProgressBar("Finished searching for sequences from "+fsrc, sttime);
3696 Thread frunner = new Thread(foo);
3701 public boolean canShowTranslationProducts(SequenceI[] selection, AlignmentI alignment)
3705 return (jalview.analysis.Dna.canTranslate(selection, viewport.getViewAsVisibleContigs(true)));
3706 } catch (Exception e)
3708 jalview.bin.Cache.log.warn("canTranslate threw an exception - please report to help@jalview.org",e);
3713 public void showProducts_actionPerformed(ActionEvent e)
3715 ///////////////////////////////
3716 // Collect Data to be translated/transferred
3718 SequenceI [] selection = viewport.getSequenceSelection();
3719 AlignmentI al = null;
3721 al = jalview.analysis.Dna.CdnaTranslate(selection, viewport.getViewAsVisibleContigs(true),
3722 viewport.getGapCharacter(), viewport.getAlignment().getDataset());
3723 } catch (Exception ex) {
3725 jalview.bin.Cache.log.debug("Exception during translation.",ex);
3729 JOptionPane.showMessageDialog(Desktop.desktop,
3730 "Please select at least three bases in at least one sequence in order to perform a cDNA translation.",
3731 "Translation Failed",
3732 JOptionPane.WARNING_MESSAGE);
3734 AlignFrame af = new AlignFrame(al, DEFAULT_WIDTH, DEFAULT_HEIGHT);
3735 Desktop.addInternalFrame(af, "Translation of "+this.getTitle(),
3741 public void showTranslation_actionPerformed(ActionEvent e)
3743 ///////////////////////////////
3744 // Collect Data to be translated/transferred
3746 SequenceI [] selection = viewport.getSequenceSelection();
3747 String [] seqstring = viewport.getViewAsString(true);
3748 AlignmentI al = null;
3750 al = jalview.analysis.Dna.CdnaTranslate(selection, seqstring, viewport.getViewAsVisibleContigs(true),
3751 viewport.getGapCharacter(), viewport.alignment.getAlignmentAnnotation(),
3752 viewport.alignment.getWidth(), viewport.getAlignment().getDataset());
3753 } catch (Exception ex) {
3755 jalview.bin.Cache.log.debug("Exception during translation.",ex);
3759 JOptionPane.showMessageDialog(Desktop.desktop,
3760 "Please select at least three bases in at least one sequence in order to perform a cDNA translation.",
3761 "Translation Failed",
3762 JOptionPane.WARNING_MESSAGE);
3764 AlignFrame af = new AlignFrame(al, DEFAULT_WIDTH, DEFAULT_HEIGHT);
3765 Desktop.addInternalFrame(af, "Translation of "+this.getTitle(),
3772 * Try to load a features file onto the alignment.
3773 * @param file contents or path to retrieve file
3774 * @param type access mode of file (see jalview.io.AlignFile)
3775 * @return true if features file was parsed corectly.
3777 public boolean parseFeaturesFile(String file, String type)
3779 boolean featuresFile = false;
3782 featuresFile = new FeaturesFile(file,
3783 type).parse(viewport.alignment.getDataset(),
3784 alignPanel.seqPanel.seqCanvas.
3785 getFeatureRenderer().featureColours,
3790 ex.printStackTrace();
3795 viewport.showSequenceFeatures = true;
3796 showSeqFeatures.setSelected(true);
3797 alignPanel.paintAlignment(true);
3800 return featuresFile;
3803 public void dragEnter(DropTargetDragEvent evt)
3806 public void dragExit(DropTargetEvent evt)
3809 public void dragOver(DropTargetDragEvent evt)
3812 public void dropActionChanged(DropTargetDragEvent evt)
3815 public void drop(DropTargetDropEvent evt)
3817 Transferable t = evt.getTransferable();
3818 java.util.List files = null;
3822 DataFlavor uriListFlavor = new DataFlavor(
3823 "text/uri-list;class=java.lang.String");
3824 if (t.isDataFlavorSupported(DataFlavor.javaFileListFlavor))
3826 //Works on Windows and MacOSX
3827 evt.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE);
3828 files = (java.util.List) t.getTransferData(DataFlavor.
3829 javaFileListFlavor);
3831 else if (t.isDataFlavorSupported(uriListFlavor))
3833 // This is used by Unix drag system
3834 evt.acceptDrop(DnDConstants.ACTION_COPY_OR_MOVE);
3835 String data = (String) t.getTransferData(uriListFlavor);
3836 files = new java.util.ArrayList(1);
3837 for (java.util.StringTokenizer st = new java.util.StringTokenizer(
3840 st.hasMoreTokens(); )
3842 String s = st.nextToken();
3843 if (s.startsWith("#"))
3845 // the line is a comment (as per the RFC 2483)
3849 java.net.URI uri = new java.net.URI(s);
3850 java.io.File file = new java.io.File(uri);
3857 e.printStackTrace();
3864 for (int i = 0; i < files.size(); i++)
3866 loadJalviewDataFile(files.get(i).toString());
3869 catch (Exception ex)
3871 ex.printStackTrace();
3877 * Attempt to load a "dropped" file: First by testing
3878 * whether it's and Annotation file, then a JNet file, and finally a features file. If all are
3879 * false then the user may have dropped an alignment file onto this
3881 * @param file either a filename or a URL string.
3883 public void loadJalviewDataFile(String file)
3887 String protocol = "File";
3889 if (file.indexOf("http:") > -1 || file.indexOf("file:") > -1)
3894 boolean isAnnotation = new AnnotationFile().readAnnotationFile(viewport.
3895 alignment, file, protocol);
3899 // try to see if its a JNet 'concise' style annotation file *before* we try to parse it as a features file
3900 String format = new IdentifyFile().Identify(file, protocol);
3901 if(format.equalsIgnoreCase("JnetFile"))
3903 jalview.io.JPredFile predictions = new jalview.io.JPredFile(
3905 new JnetAnnotationMaker().add_annotation(predictions,
3906 viewport.getAlignment(),
3912 // try to parse it as a features file
3913 boolean isGroupsFile = parseFeaturesFile(file,protocol);
3914 // if it wasn't a features file then we just treat it as a general alignment file to load into the current view.
3917 new FileLoader().LoadFile(viewport, file, protocol, format);
3919 alignPanel.paintAlignment(true);
3926 alignPanel.adjustAnnotationHeight();
3927 buildSortByAnnotationScoresMenu();
3928 alignPanel.paintAlignment(true);
3931 catch (Exception ex)
3933 ex.printStackTrace();
3937 public void tabSelectionChanged(int index)
3941 alignPanel = (AlignmentPanel) alignPanels.elementAt(index);
3942 viewport = alignPanel.av;
3943 setMenusFromViewport(viewport);
3947 public void tabbedPane_mousePressed(MouseEvent e)
3949 if(SwingUtilities.isRightMouseButton(e))
3951 String reply = JOptionPane.showInternalInputDialog(this,
3954 JOptionPane.QUESTION_MESSAGE);
3958 viewport.viewName = reply;
3959 tabbedPane.setTitleAt( tabbedPane.getSelectedIndex() ,reply);
3965 public AlignViewport getCurrentView()
3972 * Open the dialog for regex description parsing.
3974 protected void extractScores_actionPerformed(ActionEvent e)
3976 ParseProperties pp = new jalview.analysis.ParseProperties(viewport.alignment);
3977 if (pp.getScoresFromDescription("col", "score column ", "\\W+([-+]?\\d*\\.?\\d*e?-?\\d*)\\W+([-+]?\\d*\\.?\\d*e?-?\\d*)")>0)
3979 buildSortByAnnotationScoresMenu();
3988 public PrintThread(AlignmentPanel ap)
3992 static PageFormat pf;
3995 PrinterJob printJob = PrinterJob.getPrinterJob();
3999 printJob.setPrintable(ap, pf);
4003 printJob.setPrintable(ap);
4006 if (printJob.printDialog())
4012 catch (Exception PrintException)
4014 PrintException.printStackTrace();