click node to select sequences
authoramwaterhouse <Andrew Waterhouse>
Mon, 18 Sep 2006 13:25:27 +0000 (13:25 +0000)
committeramwaterhouse <Andrew Waterhouse>
Mon, 18 Sep 2006 13:25:27 +0000 (13:25 +0000)
src/jalview/appletgui/TreeCanvas.java
src/jalview/gui/TreeCanvas.java

index a9be9bc..928d21f 100755 (executable)
@@ -30,7 +30,7 @@ import jalview.schemes.*;
 import jalview.util.*;\r
 \r
 public class TreeCanvas\r
-    extends Panel implements MouseListener\r
+    extends Panel implements MouseListener, MouseMotionListener\r
 {\r
   NJTree tree;\r
   ScrollPane scrollPane;\r
@@ -50,25 +50,25 @@ public class TreeCanvas
   String longestName;\r
   int labelLength = -1;\r
 \r
-  //RubberbandRectangle rubberband;\r
-\r
-  Vector listeners;\r
-\r
   Hashtable nameHash = new Hashtable();\r
   Hashtable nodeHash = new Hashtable();\r
 \r
+  SequenceNode highlightNode;\r
+\r
+\r
   public TreeCanvas(AlignViewport av, ScrollPane scroller)\r
   {\r
     this.av = av;\r
     font = av.getFont();\r
     scrollPane = scroller;\r
     addMouseListener(this);\r
+    addMouseMotionListener(this);\r
     setLayout(null);\r
 \r
     PaintRefresher.Register(this, av.alignment);\r
   }\r
 \r
-  public void TreeSelectionChanged(Sequence sequence)\r
+  public void treeSelectionChanged(SequenceI sequence)\r
   {\r
     SequenceGroup selected = av.getSelectionGroup();\r
     if (selected == null)\r
@@ -79,9 +79,6 @@ public class TreeCanvas
 \r
     selected.setEndRes(av.alignment.getWidth()-1);\r
     selected.addOrRemove(sequence, true);\r
-\r
-    PaintRefresher.Refresh(this, av.alignment);\r
-    repaint();\r
   }\r
 \r
   public void setTree(NJTree tree)\r
@@ -214,7 +211,10 @@ public class TreeCanvas
 \r
       // Draw horizontal line\r
       g.drawLine(xstart, ypos, xend, ypos);\r
-      g.fillRect(xend - 2, ypos - 2, 4, 4);\r
+      if (node == highlightNode)\r
+        g.fillRect(xend - 3, ypos - 3, 6, 6);\r
+      else\r
+        g.fillRect(xend - 2, ypos - 2, 4, 4);\r
 \r
       int ystart = (int) ( ( (SequenceNode) node.left()).ycount * chunk) + offy;\r
       int yend = (int) ( ( (SequenceNode) node.right()).ycount * chunk) + offy;\r
@@ -348,22 +348,39 @@ public class TreeCanvas
     }\r
   }\r
 \r
-  public void paint(Graphics g)\r
+  public void update(Graphics g)\r
+  {\r
+    paint(g);\r
+  }\r
+\r
+  Image offscreen;\r
+  public void paint(Graphics g1)\r
   {\r
 \r
     if(tree==null)\r
       return;\r
 \r
-    g.setFont(font);\r
-\r
-\r
-    FontMetrics fm = g.getFontMetrics(font);\r
-\r
     if (nameHash.size() == 0)\r
     {\r
       repaint();\r
     }\r
 \r
+    FontMetrics fm = g1.getFontMetrics(font);\r
+\r
+    int width = scrollPane.getSize().width;\r
+    int height = scrollPane.getSize().height;\r
+    if(!fitToWindow)\r
+      height = fm.getHeight() * nameHash.size();\r
+\r
+\r
+    if(offscreen==null || offscreen.getWidth(this)!=width\r
+    || offscreen.getHeight(this)!=height)\r
+      offscreen = createImage(width, height);\r
+\r
+    Graphics g = offscreen.getGraphics();\r
+\r
+    g.setFont(font);\r
+\r
     if (fitToWindow ||\r
         (!fitToWindow &&\r
          scrollPane.getSize().height > fm.getHeight() * nameHash.size() + offy))\r
@@ -377,6 +394,7 @@ public class TreeCanvas
       draw(g, scrollPane.getSize().width, fm.getHeight() * nameHash.size());\r
     }\r
 \r
+    g1.drawImage(offscreen, 0, 0, this);\r
     scrollPane.validate();\r
   }\r
 \r
@@ -431,8 +449,57 @@ public class TreeCanvas
   public void mouseExited(MouseEvent e)\r
   {}\r
 \r
-  public void mouseClicked(MouseEvent e)\r
+  public void mouseClicked(MouseEvent evt)\r
+  {\r
+    if (highlightNode != null)\r
+    {\r
+      if (evt.getClickCount() > 1)\r
+      {\r
+        tree.swapNodes(highlightNode);\r
+        tree.reCount(tree.getTopNode());\r
+        tree.findHeight(tree.getTopNode());\r
+      }\r
+      else\r
+      {\r
+        Vector leaves = new Vector();\r
+        tree.findLeaves(highlightNode, leaves);\r
+\r
+        for (int i = 0; i < leaves.size(); i++)\r
+        {\r
+          SequenceI seq =\r
+              (SequenceI) ( (SequenceNode) leaves.elementAt(i)).element();\r
+          treeSelectionChanged(seq);\r
+        }\r
+      }\r
+\r
+      PaintRefresher.Refresh(this, av.alignment);\r
+      repaint();\r
+    }\r
+  }\r
+\r
+  public void mouseDragged(MouseEvent ect)\r
+  {}\r
+\r
+\r
+  public void mouseMoved(MouseEvent evt)\r
   {\r
+    av.setCurrentTree(tree);\r
+\r
+    Object ob = findElement(evt.getX(), evt.getY());\r
+\r
+    if (ob instanceof SequenceNode)\r
+    {\r
+      highlightNode = (SequenceNode) ob;\r
+      repaint();\r
+    }\r
+    else\r
+    {\r
+      if (highlightNode != null)\r
+      {\r
+        highlightNode = null;\r
+        repaint();\r
+      }\r
+    }\r
   }\r
 \r
   public void mousePressed(MouseEvent e)\r
@@ -446,19 +513,12 @@ public class TreeCanvas
 \r
     if (ob instanceof SequenceI)\r
     {\r
-      TreeSelectionChanged( (Sequence) ob);\r
+      treeSelectionChanged( (Sequence) ob);\r
+      PaintRefresher.Refresh(this, av.alignment);\r
       repaint();\r
       return;\r
-\r
     }\r
-    else if (ob instanceof SequenceNode)\r
-    {\r
-      SequenceNode tmpnode = (SequenceNode) ob;\r
-      tree.swapNodes(tmpnode);\r
-      tree.reCount(tree.getTopNode());\r
-      tree.findHeight(tree.getTopNode());\r
-    }\r
-    else\r
+    else if ( !(ob instanceof SequenceNode))\r
     {\r
       // Find threshold\r
 \r
@@ -474,7 +534,19 @@ public class TreeCanvas
         av.setSelectionGroup(null);\r
         av.alignment.deleteAllGroups();\r
 \r
-        for (int i = 0; i < tree.getGroups().size(); i++)\r
+        colourGroups();\r
+\r
+      }\r
+    }\r
+\r
+    PaintRefresher.Refresh(this, av.alignment);\r
+    repaint();\r
+\r
+  }\r
+\r
+  void colourGroups()\r
+  {\r
+    for (int i = 0; i < tree.getGroups().size(); i++)\r
         {\r
 \r
           Color col = new Color( (int) (Math.random() * 255),\r
@@ -538,11 +610,6 @@ public class TreeCanvas
           av.alignment.addGroup(sg);\r
 \r
         }\r
-      }\r
-    }\r
-\r
-    PaintRefresher.Refresh(this, av.alignment);\r
-    repaint();\r
 \r
   }\r
 \r
index 154fe46..70aeb60 100755 (executable)
@@ -42,7 +42,7 @@ import javax.swing.*;
  * @version $Revision$\r
  */\r
 public class TreeCanvas extends JPanel implements MouseListener, Runnable,\r
-    Printable\r
+    Printable, MouseMotionListener\r
 {\r
     /** DOCUMENT ME!! */\r
     public static final String PLACEHOLDER = " * ";\r
@@ -61,10 +61,9 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
     String longestName;\r
     int labelLength = -1;\r
 \r
-    //RubberbandRectangle rubberband;\r
-    Vector listeners;\r
     Hashtable nameHash = new Hashtable();\r
     Hashtable nodeHash = new Hashtable();\r
+    SequenceNode highlightNode;\r
 \r
     /**\r
      * Creates a new TreeCanvas object.\r
@@ -80,6 +79,7 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
         font = av.getFont();\r
         scrollPane = scroller;\r
         addMouseListener(this);\r
+        addMouseMotionListener(this);\r
         PaintRefresher.Register(this, av.alignment);\r
     }\r
 \r
@@ -89,7 +89,7 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
      *\r
      * @param sequence DOCUMENT ME!\r
      */\r
-    public void TreeSelectionChanged(Sequence sequence)\r
+    public void treeSelectionChanged(SequenceI sequence)\r
     {\r
         SequenceGroup selected = av.getSelectionGroup();\r
 \r
@@ -101,9 +101,6 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
 \r
         selected.setEndRes(av.alignment.getWidth()-1);\r
         selected.addOrRemove(sequence, true);\r
-\r
-        PaintRefresher.Refresh(this, av.alignment);\r
-        repaint();\r
     }\r
 \r
     /**\r
@@ -258,7 +255,10 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
 \r
             // Draw horizontal line\r
             g.drawLine(xstart, ypos, xend, ypos);\r
-            g.fillRect(xend - 2, ypos - 2, 4, 4);\r
+            if (node == highlightNode)\r
+              g.fillRect(xend - 3, ypos - 3, 6, 6);\r
+            else\r
+              g.fillRect(xend - 2, ypos - 2, 4, 4);\r
 \r
             int ystart = (int) (((SequenceNode) node.left()).ycount * chunk) +\r
                 offy;\r
@@ -657,10 +657,60 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
      *\r
      * @param e DOCUMENT ME!\r
      */\r
-    public void mouseClicked(MouseEvent e)\r
+    public void mouseClicked(MouseEvent evt)\r
     {\r
+      if(highlightNode!=null)\r
+      {\r
+        if(evt.getClickCount()>1)\r
+        {\r
+          tree.swapNodes(highlightNode);\r
+          tree.reCount(tree.getTopNode());\r
+          tree.findHeight(tree.getTopNode());\r
+        }\r
+        else\r
+        {\r
+          Vector leaves = new Vector();\r
+          tree.findLeaves(highlightNode, leaves);\r
+\r
+          for (int i = 0; i < leaves.size(); i++)\r
+          {\r
+            SequenceI seq =\r
+                (SequenceI) ( (SequenceNode) leaves.elementAt(i)).element();\r
+            treeSelectionChanged(seq);\r
+          }\r
+        }\r
+\r
+        PaintRefresher.Refresh(this, av.alignment);\r
+        repaint();\r
+      }\r
     }\r
 \r
+\r
+\r
+    public void mouseMoved(MouseEvent evt)\r
+    {\r
+      av.setCurrentTree(tree);\r
+\r
+      Object ob = findElement(evt.getX(), evt.getY());\r
+\r
+      if (ob instanceof SequenceNode)\r
+      {\r
+        highlightNode = (SequenceNode) ob;\r
+        repaint();\r
+      }\r
+      else\r
+      {\r
+        if (highlightNode != null)\r
+        {\r
+          highlightNode = null;\r
+          repaint();\r
+        }\r
+      }\r
+  }\r
+\r
+    public void mouseDragged(MouseEvent ect)\r
+    {}\r
+\r
     /**\r
      * DOCUMENT ME!\r
      *\r
@@ -677,19 +727,12 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
 \r
         if (ob instanceof SequenceI)\r
         {\r
-            TreeSelectionChanged((Sequence) ob);\r
-            repaint();\r
-\r
-            return;\r
-        }\r
-        else if (ob instanceof SequenceNode)\r
-        {\r
-            SequenceNode tmpnode = (SequenceNode) ob;\r
-            tree.swapNodes(tmpnode);\r
-            tree.reCount(tree.getTopNode());\r
-            tree.findHeight(tree.getTopNode());\r
+          treeSelectionChanged( (Sequence) ob);\r
+          PaintRefresher.Refresh(this, av.alignment);\r
+          repaint();\r
+          return;\r
         }\r
-        else\r
+        else if( !(ob instanceof SequenceNode) )\r
         {\r
             // Find threshold\r
             if (tree.getMaxHeight() != 0)\r
@@ -704,76 +747,84 @@ public class TreeCanvas extends JPanel implements MouseListener, Runnable,
                 av.setSelectionGroup(null);\r
                 av.alignment.deleteAllGroups();\r
 \r
-                for (int i = 0; i < tree.getGroups().size(); i++)\r
-                {\r
-                    Color col = new Color((int) (Math.random() * 255),\r
-                            (int) (Math.random() * 255),\r
-                            (int) (Math.random() * 255));\r
-                    setColor((SequenceNode) tree.getGroups().elementAt(i),\r
-                        col.brighter());\r
+                colourGroups();\r
+              }\r
 \r
-                    Vector l = tree.findLeaves((SequenceNode) tree.getGroups()\r
-                                                                  .elementAt(i),\r
-                            new Vector());\r
+              PaintRefresher.Refresh(this, av.alignment);\r
+              repaint();\r
+        }\r
 \r
-                    Vector sequences = new Vector();\r
 \r
-                    for (int j = 0; j < l.size(); j++)\r
-                    {\r
-                        SequenceI s1 = (SequenceI) ((SequenceNode) l.elementAt(j)).element();\r
+    }\r
 \r
-                        if (!sequences.contains(s1))\r
-                        {\r
-                            sequences.addElement(s1);\r
-                        }\r
-                    }\r
+    void colourGroups()\r
+    {\r
+      for (int i = 0; i < tree.getGroups().size(); i++)\r
+      {\r
+        Color col = new Color( (int) (Math.random() * 255),\r
+                              (int) (Math.random() * 255),\r
+                              (int) (Math.random() * 255));\r
+        setColor( (SequenceNode) tree.getGroups().elementAt(i),\r
+                 col.brighter());\r
 \r
-                    ColourSchemeI cs = null;\r
+        Vector l = tree.findLeaves( (SequenceNode) tree.getGroups()\r
+                                   .elementAt(i),\r
+                                   new Vector());\r
 \r
-                    if (av.getGlobalColourScheme() != null)\r
-                    {\r
-                      if (av.getGlobalColourScheme() instanceof UserColourScheme)\r
-                      {\r
-                        cs = new UserColourScheme(\r
-                            ( (UserColourScheme) av.getGlobalColourScheme()).getColours());\r
-\r
-                      }\r
-                      else\r
-                        cs = ColourSchemeProperty.getColour(sequences,\r
-                                                            av.alignment.getWidth(),\r
-                                                            ColourSchemeProperty.getColourName(\r
-                                                                av.getGlobalColourScheme()));\r
-\r
-                        cs.setThreshold(av.getGlobalColourScheme().getThreshold(),\r
-                                                             av.getIgnoreGapsConsensus());\r
-                    }\r
+        Vector sequences = new Vector();\r
 \r
+        for (int j = 0; j < l.size(); j++)\r
+        {\r
+          SequenceI s1 = (SequenceI) ( (SequenceNode) l.elementAt(j)).element();\r
 \r
-                    SequenceGroup sg = new SequenceGroup(sequences,\r
-                            "TreeGroup", cs, true, true, false, 0,\r
-                            av.alignment.getWidth()-1);\r
+          if (!sequences.contains(s1))\r
+          {\r
+            sequences.addElement(s1);\r
+          }\r
+        }\r
 \r
+        ColourSchemeI cs = null;\r
 \r
-                    if (  av.getGlobalColourScheme()!=null\r
-                       && av.getGlobalColourScheme().conservationApplied())\r
-                    {\r
-                        Conservation c = new Conservation("Group",\r
-                                ResidueProperties.propHash, 3,\r
-                                sg.getSequences(false),\r
-                                sg.getStartRes(), sg.getEndRes());\r
-\r
-                        c.calculate();\r
-                        c.verdict(false, av.ConsPercGaps);\r
-                        sg.cs.setConservation(c);\r
-                    }\r
+        if (av.getGlobalColourScheme() != null)\r
+        {\r
+          if (av.getGlobalColourScheme() instanceof UserColourScheme)\r
+          {\r
+            cs = new UserColourScheme(\r
+                ( (UserColourScheme) av.getGlobalColourScheme()).getColours());\r
 \r
-                    av.alignment.addGroup(sg);\r
-                }\r
-            }\r
+          }\r
+          else\r
+            cs = ColourSchemeProperty.getColour(sequences,\r
+                                                av.alignment.getWidth(),\r
+                                                ColourSchemeProperty.\r
+                                                getColourName(\r
+                                                    av.getGlobalColourScheme()));\r
+\r
+          cs.setThreshold(av.getGlobalColourScheme().getThreshold(),\r
+                          av.getIgnoreGapsConsensus());\r
         }\r
 \r
-        PaintRefresher.Refresh(this, av.alignment);\r
-        repaint();\r
+        SequenceGroup sg = new SequenceGroup(sequences,\r
+                                             "TreeGroup", cs, true, true, false,\r
+                                             0,\r
+                                             av.alignment.getWidth() - 1);\r
+\r
+        if (av.getGlobalColourScheme() != null\r
+            && av.getGlobalColourScheme().conservationApplied())\r
+        {\r
+          Conservation c = new Conservation("Group",\r
+                                            ResidueProperties.propHash, 3,\r
+                                            sg.getSequences(false),\r
+                                            sg.getStartRes(), sg.getEndRes());\r
+\r
+          c.calculate();\r
+          c.verdict(false, av.ConsPercGaps);\r
+          sg.cs.setConservation(c);\r
+        }\r
+\r
+        av.alignment.addGroup(sg);\r
+      }\r
+\r
     }\r
 \r
     /**\r