minor formatting of tooltip
[jalview.git] / src / jalview / gui / IdPanel.java
1 /*\r
2  * Jalview - A Sequence Alignment Editor and Viewer\r
3  * Copyright (C) 2007 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle\r
4  *\r
5  * This program is free software; you can redistribute it and/or\r
6  * modify it under the terms of the GNU General Public License\r
7  * as published by the Free Software Foundation; either version 2\r
8  * of the License, or (at your option) any later version.\r
9  *\r
10  * This program is distributed in the hope that it will be useful,\r
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of\r
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
13  * GNU General Public License for more details.\r
14  *\r
15  * You should have received a copy of the GNU General Public License\r
16  * along with this program; if not, write to the Free Software\r
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA\r
18  */\r
19 package jalview.gui;\r
20 \r
21 import java.awt.*;\r
22 import java.awt.event.*;\r
23 import javax.swing.*;\r
24 \r
25 import jalview.datamodel.*;\r
26 \r
27 /**\r
28  * DOCUMENT ME!\r
29  *\r
30  * @author $author$\r
31  * @version $Revision$\r
32  */\r
33 public class IdPanel\r
34     extends JPanel implements MouseListener,\r
35     MouseMotionListener, MouseWheelListener\r
36 {\r
37   protected IdCanvas idCanvas;\r
38   protected AlignViewport av;\r
39   protected AlignmentPanel alignPanel;\r
40   ScrollThread scrollThread = null;\r
41   int offy;\r
42   int width;\r
43   int lastid = -1;\r
44   boolean mouseDragging = false;\r
45 \r
46   /**\r
47    * Creates a new IdPanel object.\r
48    *\r
49    * @param av DOCUMENT ME!\r
50    * @param parent DOCUMENT ME!\r
51    */\r
52   public IdPanel(AlignViewport av, AlignmentPanel parent)\r
53   {\r
54     this.av = av;\r
55     alignPanel = parent;\r
56     idCanvas = new IdCanvas(av);\r
57     setLayout(new BorderLayout());\r
58     add(idCanvas, BorderLayout.CENTER);\r
59     addMouseListener(this);\r
60     addMouseMotionListener(this);\r
61     addMouseWheelListener(this);\r
62     ToolTipManager.sharedInstance().registerComponent(this);\r
63   }\r
64 \r
65   /**\r
66    * DOCUMENT ME!\r
67    *\r
68    * @param e DOCUMENT ME!\r
69    */\r
70   public void mouseMoved(MouseEvent e)\r
71   {\r
72     int seq = Math.max(0, alignPanel.seqPanel.findSeq(e));\r
73     String tmp;\r
74     if (seq > -1 && seq < av.alignment.getHeight())\r
75     {\r
76       SequenceI sequence = av.alignment.getSequenceAt(seq);\r
77       StringBuffer tip = new StringBuffer();\r
78       tip.append("<i>");\r
79 \r
80       int maxWidth = 0;\r
81       if (sequence.getDescription() != null)\r
82       {\r
83         tmp = sequence.getDescription();\r
84         tip.append("<br>"+tmp);\r
85         maxWidth = Math.max(maxWidth, tmp.length());\r
86       }\r
87 \r
88       DBRefEntry[] dbrefs = sequence.getDatasetSequence().getDBRef();\r
89       if (dbrefs != null)\r
90       {\r
91         for (int i = 0; i < dbrefs.length; i++)\r
92         {\r
93           tip.append("<br>");\r
94           tmp = dbrefs[i].getSource() + " " + dbrefs[i].getAccessionId();\r
95           tip.append(tmp);\r
96           maxWidth = Math.max(maxWidth, tmp.length());\r
97         }\r
98       }\r
99 \r
100 \r
101       //ADD NON POSITIONAL SEQUENCE INFO\r
102       SequenceFeature[] features = sequence.getDatasetSequence().\r
103           getSequenceFeatures();\r
104       if (features != null)\r
105       {\r
106         for (int i = 0; i < features.length; i++)\r
107         {\r
108           if (features[i].begin == 0 && features[i].end == 0)\r
109           {\r
110             tmp = features[i].featureGroup\r
111                        + " " + features[i].getType() + " " +\r
112                        features[i].description;\r
113             tip.append("<br>" + tmp);\r
114             maxWidth = Math.max(maxWidth, tmp.length());\r
115           }\r
116         }\r
117       }\r
118 \r
119       if(maxWidth > 60)\r
120       {\r
121          tip.insert(0, "<table width=350 border=0><tr><td><i>");\r
122          tip.append("</i></td></tr></table>");\r
123       }\r
124 \r
125       tip.append("</html>");\r
126 \r
127       setToolTipText("<html>"+sequence.getDisplayId(true)+tip.toString());\r
128     }\r
129   }\r
130 \r
131   /**\r
132    * DOCUMENT ME!\r
133    *\r
134    * @param e DOCUMENT ME!\r
135    */\r
136   public void mouseDragged(MouseEvent e)\r
137   {\r
138     mouseDragging = true;\r
139 \r
140     int seq = Math.max(0, alignPanel.seqPanel.findSeq(e));\r
141 \r
142     if (seq < lastid)\r
143     {\r
144       selectSeqs(lastid - 1, seq);\r
145     }\r
146     else if (seq > lastid)\r
147     {\r
148       selectSeqs(lastid + 1, seq);\r
149     }\r
150 \r
151     lastid = seq;\r
152     alignPanel.paintAlignment(true);\r
153   }\r
154 \r
155   public void mouseWheelMoved(MouseWheelEvent e)\r
156   {\r
157     e.consume();\r
158       if (e.getWheelRotation() > 0)\r
159       {\r
160         alignPanel.scrollUp(false);\r
161       }\r
162       else\r
163       {\r
164         alignPanel.scrollUp(true);\r
165       }\r
166   }\r
167 \r
168   /**\r
169    * DOCUMENT ME!\r
170    *\r
171    * @param e DOCUMENT ME!\r
172    */\r
173   public void mouseClicked(MouseEvent e)\r
174   {\r
175     if (e.getClickCount() < 2)\r
176     {\r
177       return;\r
178     }\r
179 \r
180     java.util.Vector links = Preferences.sequenceURLLinks;\r
181     if (links == null || links.size() < 1)\r
182     {\r
183       return;\r
184     }\r
185 \r
186     int seq = alignPanel.seqPanel.findSeq(e);\r
187 \r
188     //DEFAULT LINK IS FIRST IN THE LINK LIST\r
189 \r
190     String id = av.getAlignment().getSequenceAt(seq).getName();\r
191     if (id.indexOf("|") > -1)\r
192     {\r
193       id = id.substring(id.lastIndexOf("|") + 1);\r
194     }\r
195 \r
196     String url = links.elementAt(0).toString();\r
197     url = url.substring(url.indexOf("|") + 1);\r
198 \r
199     int index = url.indexOf("$SEQUENCE_ID$");\r
200     url = url.substring(0, index) + id + url.substring(index + 13);\r
201 \r
202     try\r
203     {\r
204       jalview.util.BrowserLauncher.openURL(url);\r
205     }\r
206     catch (Exception ex)\r
207     {\r
208       JOptionPane.showInternalMessageDialog(Desktop.desktop,\r
209                                             "Unixers: Couldn't find default web browser."\r
210                                             +\r
211           "\nAdd the full path to your browser in Preferences.",\r
212                                             "Web browser not found",\r
213                                             JOptionPane.WARNING_MESSAGE);\r
214       ex.printStackTrace();\r
215     }\r
216   }\r
217 \r
218   /**\r
219    * DOCUMENT ME!\r
220    *\r
221    * @param e DOCUMENT ME!\r
222    */\r
223   public void mouseEntered(MouseEvent e)\r
224   {\r
225     if (scrollThread != null)\r
226     {\r
227       scrollThread.running = false;\r
228     }\r
229   }\r
230 \r
231   /**\r
232    * DOCUMENT ME!\r
233    *\r
234    * @param e DOCUMENT ME!\r
235    */\r
236   public void mouseExited(MouseEvent e)\r
237   {\r
238     if (av.getWrapAlignment())\r
239     {\r
240       return;\r
241     }\r
242 \r
243     if (mouseDragging && (e.getY() < 0) && (av.getStartSeq() > 0))\r
244     {\r
245       scrollThread = new ScrollThread(true);\r
246     }\r
247 \r
248     if (mouseDragging && (e.getY() >= getHeight()) &&\r
249         (av.alignment.getHeight() > av.getEndSeq()))\r
250     {\r
251       scrollThread = new ScrollThread(false);\r
252     }\r
253   }\r
254 \r
255   /**\r
256    * DOCUMENT ME!\r
257    *\r
258    * @param e DOCUMENT ME!\r
259    */\r
260   public void mousePressed(MouseEvent e)\r
261   {\r
262     if (e.getClickCount() == 2)\r
263     {\r
264       return;\r
265     }\r
266 \r
267     int seq = alignPanel.seqPanel.findSeq(e);\r
268 \r
269     if (javax.swing.SwingUtilities.isRightMouseButton(e))\r
270     {\r
271       jalview.gui.PopupMenu pop = new jalview.gui.PopupMenu(alignPanel,\r
272           (Sequence) av.getAlignment().getSequenceAt(seq),\r
273           Preferences.sequenceURLLinks);\r
274       pop.show(this, e.getX(), e.getY());\r
275 \r
276       return;\r
277     }\r
278 \r
279     if ( (av.getSelectionGroup() == null) ||\r
280         ( (!e.isControlDown() && !e.isShiftDown()) && av.getSelectionGroup() != null))\r
281     {\r
282       av.setSelectionGroup(new SequenceGroup());\r
283       av.getSelectionGroup().setStartRes(0);\r
284       av.getSelectionGroup().setEndRes(av.alignment.getWidth() - 1);\r
285     }\r
286 \r
287     if (e.isShiftDown() && (lastid != -1))\r
288     {\r
289       selectSeqs(lastid, seq);\r
290     }\r
291     else\r
292     {\r
293       selectSeq(seq);\r
294     }\r
295 \r
296     alignPanel.paintAlignment(true);\r
297   }\r
298 \r
299   /**\r
300    * DOCUMENT ME!\r
301    *\r
302    * @param seq DOCUMENT ME!\r
303    */\r
304   void selectSeq(int seq)\r
305   {\r
306     lastid = seq;\r
307 \r
308     SequenceI pickedSeq = av.getAlignment().getSequenceAt(seq);\r
309     av.getSelectionGroup().addOrRemove(pickedSeq, true);\r
310   }\r
311 \r
312   /**\r
313    * DOCUMENT ME!\r
314    *\r
315    * @param start DOCUMENT ME!\r
316    * @param end DOCUMENT ME!\r
317    */\r
318   void selectSeqs(int start, int end)\r
319   {\r
320     if (av.getSelectionGroup() == null)\r
321     {\r
322       return;\r
323     }\r
324 \r
325     if (end >= av.getAlignment().getHeight())\r
326     {\r
327       end = av.getAlignment().getHeight() - 1;\r
328     }\r
329 \r
330     lastid = start;\r
331 \r
332     if (end < start)\r
333     {\r
334       int tmp = start;\r
335       start = end;\r
336       end = tmp;\r
337       lastid = end;\r
338     }\r
339 \r
340     for (int i = start; i <= end; i++)\r
341     {\r
342       av.getSelectionGroup().addSequence(av.getAlignment().getSequenceAt(i),\r
343                                          true);\r
344     }\r
345   }\r
346 \r
347   /**\r
348    * DOCUMENT ME!\r
349    *\r
350    * @param e DOCUMENT ME!\r
351    */\r
352   public void mouseReleased(MouseEvent e)\r
353   {\r
354     if (scrollThread != null)\r
355     {\r
356       scrollThread.running = false;\r
357     }\r
358 \r
359     mouseDragging = false;\r
360     PaintRefresher.Refresh(this, av.getSequenceSetId());\r
361   }\r
362 \r
363   /**\r
364    * DOCUMENT ME!\r
365    *\r
366    * @param found DOCUMENT ME!\r
367    */\r
368   public void highlightSearchResults(java.util.Vector found)\r
369   {\r
370     idCanvas.setHighlighted(found);\r
371 \r
372     if (found == null)\r
373     {\r
374       return;\r
375     }\r
376 \r
377     int index = av.alignment.findIndex( (SequenceI) found.get(0));\r
378 \r
379     // do we need to scroll the panel?\r
380     if ( (av.getStartSeq() > index) || (av.getEndSeq() < index))\r
381     {\r
382       alignPanel.setScrollValues(av.getStartRes(), index);\r
383     }\r
384   }\r
385 \r
386   // this class allows scrolling off the bottom of the visible alignment\r
387   class ScrollThread\r
388       extends Thread\r
389   {\r
390     boolean running = false;\r
391     boolean up = true;\r
392 \r
393     public ScrollThread(boolean up)\r
394     {\r
395       this.up = up;\r
396       start();\r
397     }\r
398 \r
399     public void stopScrolling()\r
400     {\r
401       running = false;\r
402     }\r
403 \r
404     public void run()\r
405     {\r
406       running = true;\r
407 \r
408       while (running)\r
409       {\r
410         if (alignPanel.scrollUp(up))\r
411         {\r
412           // scroll was ok, so add new sequence to selection\r
413           int seq = av.getStartSeq();\r
414 \r
415           if (!up)\r
416           {\r
417             seq = av.getEndSeq();\r
418           }\r
419 \r
420           if (seq < lastid)\r
421           {\r
422             selectSeqs(lastid - 1, seq);\r
423           }\r
424           else if (seq > lastid)\r
425           {\r
426             selectSeqs(lastid + 1, seq);\r
427           }\r
428 \r
429           lastid = seq;\r
430         }\r
431         else\r
432         {\r
433           running = false;\r
434         }\r
435 \r
436         alignPanel.paintAlignment(false);\r
437 \r
438         try\r
439         {\r
440           Thread.sleep(100);\r
441         }\r
442         catch (Exception ex)\r
443         {\r
444         }\r
445       }\r
446     }\r
447   }\r
448 }\r