Merge branch 'features/JAL-2393customMatrices' into develop
[jalview.git] / src / jalview / gui / AlignFrame.java
index d4c87d8..8eb09ab 100644 (file)
@@ -34,7 +34,7 @@ import jalview.api.AlignmentViewPanel;
 import jalview.api.FeatureSettingsControllerI;
 import jalview.api.SplitContainerI;
 import jalview.api.ViewStyleI;
-import jalview.api.analysis.ScoreModelI;
+import jalview.api.analysis.SimilarityParamsI;
 import jalview.bin.Cache;
 import jalview.bin.Jalview;
 import jalview.commands.CommandI;
@@ -69,6 +69,7 @@ import jalview.io.FileFormat;
 import jalview.io.FileFormatI;
 import jalview.io.FileFormats;
 import jalview.io.FileLoader;
+import jalview.io.FileParse;
 import jalview.io.FormatAdapter;
 import jalview.io.HtmlSvgOutput;
 import jalview.io.IdentifyFile;
@@ -77,12 +78,12 @@ import jalview.io.JalviewFileChooser;
 import jalview.io.JalviewFileView;
 import jalview.io.JnetAnnotationMaker;
 import jalview.io.NewickFile;
+import jalview.io.ScoreMatrixFile;
 import jalview.io.TCoffeeScoreFile;
 import jalview.jbgui.GAlignFrame;
 import jalview.schemes.ColourSchemeI;
 import jalview.schemes.ColourSchemes;
 import jalview.schemes.ResidueColourScheme;
-import jalview.schemes.ResidueProperties;
 import jalview.schemes.TCoffeeColourScheme;
 import jalview.util.MessageManager;
 import jalview.viewmodel.AlignmentViewport;
@@ -364,7 +365,15 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
     setMenusFromViewport(viewport);
     buildSortByAnnotationScoresMenu();
-    buildTreeMenu();
+    calculateTree.addActionListener(new ActionListener()
+    {
+
+      @Override
+      public void actionPerformed(ActionEvent e)
+      {
+        openTreePcaDialog();
+      }
+    });
     buildColourMenu();
 
     if (Desktop.desktop != null)
@@ -3442,7 +3451,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   {
     SequenceI[] oldOrder = viewport.getAlignment().getSequencesArray();
     AlignmentSorter.sortByPID(viewport.getAlignment(), viewport
-            .getAlignment().getSequenceAt(0), null);
+            .getAlignment().getSequenceAt(0));
     addHistoryItem(new OrderCommand("Pairwise Sort", oldOrder,
             viewport.getAlignment()));
     alignPanel.paintAlignment(true);
@@ -3536,35 +3545,6 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     }
   }
 
-  /**
-   * DOCUMENT ME!
-   * 
-   * @param e
-   *          DOCUMENT ME!
-   */
-  @Override
-  public void PCAMenuItem_actionPerformed(ActionEvent e)
-  {
-    if (((viewport.getSelectionGroup() != null)
-            && (viewport.getSelectionGroup().getSize() < 4) && (viewport
-            .getSelectionGroup().getSize() > 0))
-            || (viewport.getAlignment().getHeight() < 4))
-    {
-      JvOptionPane
-              .showInternalMessageDialog(
-                      this,
-                      MessageManager
-                              .getString("label.principal_component_analysis_must_take_least_four_input_sequences"),
-                      MessageManager
-                              .getString("label.sequence_selection_insufficient"),
-                      JvOptionPane.WARNING_MESSAGE);
-
-      return;
-    }
-
-    new PCAPanel(alignPanel);
-  }
-
   @Override
   public void autoCalculate_actionPerformed(ActionEvent e)
   {
@@ -3589,67 +3569,21 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   }
 
   /**
-   * DOCUMENT ME!
-   * 
-   * @param e
-   *          DOCUMENT ME!
-   */
-  @Override
-  public void averageDistanceTreeMenuItem_actionPerformed(ActionEvent e)
-  {
-    newTreePanel("AV", "PID", "Average distance tree using PID");
-  }
-
-  /**
-   * DOCUMENT ME!
-   * 
-   * @param e
-   *          DOCUMENT ME!
-   */
-  @Override
-  public void neighbourTreeMenuItem_actionPerformed(ActionEvent e)
-  {
-    newTreePanel("NJ", "PID", "Neighbour joining tree using PID");
-  }
-
-  /**
-   * DOCUMENT ME!
-   * 
-   * @param e
-   *          DOCUMENT ME!
-   */
-  @Override
-  protected void njTreeBlosumMenuItem_actionPerformed(ActionEvent e)
-  {
-    newTreePanel("NJ", "BL", "Neighbour joining tree using BLOSUM62");
-  }
-
-  /**
-   * DOCUMENT ME!
-   * 
-   * @param e
-   *          DOCUMENT ME!
-   */
-  @Override
-  protected void avTreeBlosumMenuItem_actionPerformed(ActionEvent e)
-  {
-    newTreePanel("AV", "BL", "Average distance tree using BLOSUM62");
-  }
-
-  /**
-   * DOCUMENT ME!
+   * Constructs a tree panel and adds it to the desktop
    * 
    * @param type
-   *          DOCUMENT ME!
-   * @param pwType
-   *          DOCUMENT ME!
-   * @param title
-   *          DOCUMENT ME!
+   *          tree type (NJ or AV)
+   * @param modelName
+   *          name of score model used to compute the tree
+   * @param options
+   *          parameters for the distance or similarity calculation
    */
-  void newTreePanel(String type, String pwType, String title)
+  void newTreePanel(String type, String modelName, SimilarityParamsI options)
   {
+    String frameTitle = "";
     TreePanel tp;
 
+    boolean onSelection = false;
     if (viewport.getSelectionGroup() != null
             && viewport.getSelectionGroup().getSize() > 0)
     {
@@ -3685,45 +3619,29 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           return;
         }
       }
-
-      title = title + " on region";
-      tp = new TreePanel(alignPanel, type, pwType);
+      onSelection = true;
     }
     else
     {
-      // are the visible sequences aligned?
-      if (!viewport.getAlignment().isAligned(false))
-      {
-        JvOptionPane
-                .showMessageDialog(
-                        Desktop.desktop,
-                        MessageManager
-                                .getString("label.sequences_must_be_aligned_before_creating_tree"),
-                        MessageManager
-                                .getString("label.sequences_not_aligned"),
-                        JvOptionPane.WARNING_MESSAGE);
-
-        return;
-      }
-
       if (viewport.getAlignment().getHeight() < 2)
       {
         return;
       }
-
-      tp = new TreePanel(alignPanel, type, pwType);
     }
 
-    title += " from ";
+    tp = new TreePanel(alignPanel, type, modelName, options);
+    frameTitle = tp.getPanelTitle() + (onSelection ? " on region" : "");
+
+    frameTitle += " from ";
 
     if (viewport.viewName != null)
     {
-      title += viewport.viewName + " of ";
+      frameTitle += viewport.viewName + " of ";
     }
 
-    title += this.title;
+    frameTitle += this.title;
 
-    Desktop.addInternalFrame(tp, title, 600, 500);
+    Desktop.addInternalFrame(tp, frameTitle, 600, 500);
   }
 
   /**
@@ -3845,48 +3763,10 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
    * call. Listeners are added to remove the menu item when the treePanel is
    * closed, and adjust the tree leaf to sequence mapping when the alignment is
    * modified.
-   * 
-   * @param treePanel
-   *          Displayed tree window.
-   * @param title
-   *          SortBy menu item title.
    */
   @Override
-  public void buildTreeMenu()
+  public void buildTreeSortMenu()
   {
-    calculateTree.removeAll();
-    // build the calculate menu
-
-    for (final String type : new String[] { "NJ", "AV" })
-    {
-      String treecalcnm = MessageManager.getString("label.tree_calc_"
-              + type.toLowerCase());
-      for (final String pwtype : ResidueProperties.scoreMatrices.keySet())
-      {
-        JMenuItem tm = new JMenuItem();
-        ScoreModelI sm = ResidueProperties.scoreMatrices.get(pwtype);
-        if (sm.isDNA() == viewport.getAlignment().isNucleotide()
-                || sm.isProtein() == !viewport.getAlignment()
-                        .isNucleotide())
-        {
-          String smn = MessageManager.getStringOrReturn(
-                  "label.score_model_", sm.getName());
-          final String title = MessageManager.formatMessage(
-                  "label.treecalc_title", treecalcnm, smn);
-          tm.setText(title);//
-          tm.addActionListener(new java.awt.event.ActionListener()
-          {
-            @Override
-            public void actionPerformed(ActionEvent e)
-            {
-              newTreePanel(type, pwtype, title);
-            }
-          });
-          calculateTree.add(tm);
-        }
-
-      }
-    }
     sortByTreeMenu.removeAll();
 
     List<Component> comps = PaintRefresher.components.get(viewport
@@ -4037,13 +3917,13 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
     if (value == JalviewFileChooser.APPROVE_OPTION)
     {
-      String choice = chooser.getSelectedFile().getPath();
-      jalview.bin.Cache.setProperty("LAST_DIRECTORY", choice);
-      jalview.io.NewickFile fin = null;
+      String filePath = chooser.getSelectedFile().getPath();
+      Cache.setProperty("LAST_DIRECTORY", filePath);
+      NewickFile fin = null;
       try
       {
-        fin = new NewickFile(choice, DataSourceType.FILE);
-        viewport.setCurrentTree(ShowNewickTree(fin, choice).getTree());
+        fin = new NewickFile(filePath, DataSourceType.FILE);
+        viewport.setCurrentTree(showNewickTree(fin, filePath).getTree());
       } catch (Exception ex)
       {
         JvOptionPane
@@ -4065,25 +3945,19 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     }
   }
 
-  public TreePanel ShowNewickTree(NewickFile nf, String title)
-  {
-    return ShowNewickTree(nf, title, 600, 500, 4, 5);
-  }
-
-  public TreePanel ShowNewickTree(NewickFile nf, String title,
-          AlignmentView input)
+  public TreePanel showNewickTree(NewickFile nf, String treeTitle)
   {
-    return ShowNewickTree(nf, title, input, 600, 500, 4, 5);
+    return showNewickTree(nf, treeTitle, 600, 500, 4, 5);
   }
 
-  public TreePanel ShowNewickTree(NewickFile nf, String title, int w,
+  public TreePanel showNewickTree(NewickFile nf, String treeTitle, int w,
           int h, int x, int y)
   {
-    return ShowNewickTree(nf, title, null, w, h, x, y);
+    return showNewickTree(nf, treeTitle, null, w, h, x, y);
   }
 
   /**
-   * Add a treeviewer for the tree extracted from a newick file object to the
+   * Add a treeviewer for the tree extracted from a Newick file object to the
    * current alignment view
    * 
    * @param nf
@@ -4102,7 +3976,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
    *          position
    * @return TreePanel handle
    */
-  public TreePanel ShowNewickTree(NewickFile nf, String title,
+  public TreePanel showNewickTree(NewickFile nf, String treeTitle,
           AlignmentView input, int w, int h, int x, int y)
   {
     TreePanel tp = null;
@@ -4113,7 +3987,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
 
       if (nf.getTree() != null)
       {
-        tp = new TreePanel(alignPanel, "FromFile", title, nf, input);
+        tp = new TreePanel(alignPanel, nf, treeTitle, input);
 
         tp.setSize(w, h);
 
@@ -4122,7 +3996,7 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           tp.setLocation(x, y);
         }
 
-        Desktop.addInternalFrame(tp, title, w, h);
+        Desktop.addInternalFrame(tp, treeTitle, w, h);
       }
     } catch (Exception ex)
     {
@@ -4695,10 +4569,13 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
   }
 
   /**
-   * Attempt to load a "dropped" file or URL string: First by testing whether
-   * it's an Annotation file, then a JNet file, and finally a features file. If
-   * all are false then the user may have dropped an alignment file onto this
-   * AlignFrame.
+   * Attempt to load a "dropped" file or URL string, by testing in turn for
+   * <ul>
+   * <li>an Annotation file</li>
+   * <li>a JNet file</li>
+   * <li>a features file</li>
+   * <li>else try to interpret as an alignment file</li>
+   * </ul>
    * 
    * @param file
    *          either a filename or a URL string.
@@ -4772,7 +4649,18 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
           {
             format = new IdentifyFile().identify(file, sourceType);
           }
-          if (FileFormat.Jnet.equals(format))
+          if (FileFormat.ScoreMatrix == format)
+          {
+            ScoreMatrixFile sm = new ScoreMatrixFile(new FileParse(file,
+                    sourceType));
+            sm.parse();
+            // todo: i18n this message
+            statusBar
+                    .setText(MessageManager.formatMessage(
+                            "label.successfully_loaded_matrix",
+                            sm.getMatrixName()));
+          }
+          else if (FileFormat.Jnet.equals(format))
           {
             JPredFile predictions = new JPredFile(file, sourceType);
             new JnetAnnotationMaker();
@@ -5707,6 +5595,18 @@ public class AlignFrame extends GAlignFrame implements DropTargetListener,
     ColourSchemeI colourScheme = viewport.getGlobalColourScheme();
     ColourMenuHelper.setColourSelected(colourMenu, colourScheme);
   }
+
+  /**
+   * Open a dialog (if not already open) that allows the user to select and
+   * calculate PCA or Tree analysis
+   */
+  protected void openTreePcaDialog()
+  {
+    if (alignPanel.getCalculationDialog() == null)
+    {
+      new CalculationChooser(AlignFrame.this);
+    }
+  }
 }
 
 class PrintThread extends Thread