f04441171161944e1d554b8948484d7ae7e41460
[jalview.git] / src / jalview / bin / JalviewLite.java
1 /*\r
2  * Jalview - A Sequence Alignment Editor and Viewer (Version 2.6)\r
3  * Copyright (C) 2010 J Procter, AM Waterhouse, G Barton, M Clamp, S Searle\r
4  * \r
5  * This file is part of Jalview.\r
6  * \r
7  * Jalview is free software: you can redistribute it and/or\r
8  * modify it under the terms of the GNU General Public License \r
9  * as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.\r
10  * \r
11  * Jalview is distributed in the hope that it will be useful, but \r
12  * WITHOUT ANY WARRANTY; without even the implied warranty \r
13  * of MERCHANTABILITY or FITNESS FOR A PARTICULAR \r
14  * PURPOSE.  See the GNU General Public License for more details.\r
15  * \r
16  * You should have received a copy of the GNU General Public License along with Jalview.  If not, see <http://www.gnu.org/licenses/>.\r
17  */\r
18 package jalview.bin;\r
19 \r
20 import jalview.api.StructureSelectionManagerProvider;\r
21 import jalview.appletgui.AlignFrame;\r
22 import jalview.appletgui.AlignViewport;\r
23 import jalview.appletgui.EmbmenuFrame;\r
24 import jalview.appletgui.FeatureSettings;\r
25 import jalview.datamodel.Alignment;\r
26 import jalview.datamodel.AlignmentI;\r
27 import jalview.datamodel.AlignmentOrder;\r
28 import jalview.datamodel.ColumnSelection;\r
29 import jalview.datamodel.PDBEntry;\r
30 import jalview.datamodel.Sequence;\r
31 import jalview.datamodel.SequenceGroup;\r
32 import jalview.datamodel.SequenceI;\r
33 import jalview.io.AnnotationFile;\r
34 import jalview.io.AppletFormatAdapter;\r
35 import jalview.io.FileParse;\r
36 import jalview.io.IdentifyFile;\r
37 import jalview.io.JnetAnnotationMaker;\r
38 import jalview.javascript.JSFunctionExec;\r
39 import jalview.javascript.JalviewLiteJsApi;\r
40 import jalview.javascript.JsCallBack;\r
41 import jalview.structure.SelectionListener;\r
42 import jalview.structure.StructureSelectionManager;\r
43 \r
44 import java.applet.Applet;\r
45 import java.awt.Button;\r
46 import java.awt.Color;\r
47 import java.awt.Component;\r
48 import java.awt.Font;\r
49 import java.awt.Frame;\r
50 import java.awt.Graphics;\r
51 import java.awt.event.ActionEvent;\r
52 import java.awt.event.WindowAdapter;\r
53 import java.awt.event.WindowEvent;\r
54 import java.io.BufferedReader;\r
55 import java.io.InputStreamReader;\r
56 import java.util.Hashtable;\r
57 import java.util.StringTokenizer;\r
58 import java.util.Vector;\r
59 \r
60 import netscape.javascript.JSObject;\r
61 \r
62 /**\r
63  * Jalview Applet. Runs in Java 1.18 runtime\r
64  * \r
65  * @author $author$\r
66  * @version $Revision: 1.92 $\r
67  */\r
68 public class JalviewLite extends Applet implements StructureSelectionManagerProvider, JalviewLiteJsApi\r
69 {\r
70 \r
71   // /////////////////////////////////////////\r
72   // The following public methods maybe called\r
73   // externally, eg via javascript in HTML page\r
74   /* (non-Javadoc)\r
75    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequences()\r
76    */\r
77   public String getSelectedSequences()\r
78   {\r
79     return getSelectedSequencesFrom(getDefaultTargetFrame());\r
80   }\r
81 \r
82   /* (non-Javadoc)\r
83    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequences(java.lang.String)\r
84    */\r
85   public String getSelectedSequences(String sep)\r
86   {\r
87     return getSelectedSequencesFrom(getDefaultTargetFrame(), sep);\r
88   }\r
89 \r
90   /* (non-Javadoc)\r
91    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequencesFrom(jalview.appletgui.AlignFrame)\r
92    */\r
93   public String getSelectedSequencesFrom(AlignFrame alf)\r
94   {\r
95     return getSelectedSequencesFrom(alf, separator); // ""+0x00AC);\r
96   }\r
97 \r
98   /* (non-Javadoc)\r
99    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequencesFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
100    */\r
101   public String getSelectedSequencesFrom(AlignFrame alf, String sep)\r
102   {\r
103     StringBuffer result = new StringBuffer("");\r
104     if (sep == null || sep.length() == 0)\r
105     {\r
106       sep = separator; // "+0x00AC;\r
107     }\r
108     if (alf.viewport.getSelectionGroup() != null)\r
109     {\r
110       SequenceI[] seqs = alf.viewport.getSelectionGroup()\r
111               .getSequencesInOrder(alf.viewport.getAlignment());\r
112 \r
113       for (int i = 0; i < seqs.length; i++)\r
114       {\r
115         result.append(seqs[i].getName());\r
116         result.append(sep);\r
117       }\r
118     }\r
119 \r
120     return result.toString();\r
121   }\r
122 \r
123   /* (non-Javadoc)\r
124    * @see jalview.bin.JalviewLiteJsApi#highlight(java.lang.String, java.lang.String, java.lang.String)\r
125    */\r
126   public void highlight(String sequenceId, String position,\r
127           String alignedPosition)\r
128   {\r
129     highlightIn(getDefaultTargetFrame(), sequenceId, position,\r
130             alignedPosition);\r
131   }\r
132 \r
133   /* (non-Javadoc)\r
134    * @see jalview.bin.JalviewLiteJsApi#highlightIn(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String, java.lang.String)\r
135    */\r
136   public void highlightIn(AlignFrame alf, String sequenceId,\r
137           String position, String alignedPosition)\r
138   {\r
139     // TODO: could try to highlight in all alignments if alf==null\r
140     jalview.analysis.SequenceIdMatcher matcher = new jalview.analysis.SequenceIdMatcher(\r
141             alf.viewport.getAlignment().getSequencesArray());\r
142     SequenceI sq = matcher.findIdMatch(sequenceId);\r
143     if (sq != null)\r
144     {\r
145       int pos, apos = -1;\r
146       try\r
147       {\r
148         apos = new Integer(position).intValue();\r
149         apos--;\r
150       } catch (NumberFormatException ex)\r
151       {\r
152         return;\r
153       }\r
154       // use vamsas listener to broadcast to all listeners in scope\r
155       if (alignedPosition != null\r
156               && (alignedPosition.trim().length() == 0 || alignedPosition\r
157                       .toLowerCase().indexOf("false") > -1))\r
158       {\r
159         StructureSelectionManager.getStructureSelectionManager(this)\r
160                 .mouseOverVamsasSequence(sq, sq.findIndex(apos), null);\r
161       }\r
162       else\r
163       {\r
164         StructureSelectionManager.getStructureSelectionManager(this)\r
165                 .mouseOverVamsasSequence(sq, apos, null);\r
166       }\r
167 \r
168     }\r
169   }\r
170 \r
171   /* (non-Javadoc)\r
172    * @see jalview.bin.JalviewLiteJsApi#select(java.lang.String, java.lang.String)\r
173    */\r
174   public void select(String sequenceIds, String columns)\r
175   {\r
176     selectIn(getDefaultTargetFrame(), sequenceIds, columns, separator);\r
177   }\r
178 \r
179   /* (non-Javadoc)\r
180    * @see jalview.bin.JalviewLiteJsApi#select(java.lang.String, java.lang.String, java.lang.String)\r
181    */\r
182   public void select(String sequenceIds, String columns, String sep)\r
183   {\r
184     selectIn(getDefaultTargetFrame(), sequenceIds, columns, sep);\r
185   }\r
186 \r
187   /* (non-Javadoc)\r
188    * @see jalview.bin.JalviewLiteJsApi#selectIn(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String)\r
189    */\r
190   public void selectIn(AlignFrame alf, String sequenceIds, String columns)\r
191   {\r
192     selectIn(alf, sequenceIds, columns, separator);\r
193   }\r
194 \r
195   /* (non-Javadoc)\r
196    * @see jalview.bin.JalviewLiteJsApi#selectIn(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String, java.lang.String)\r
197    */\r
198   public void selectIn(AlignFrame alf, String sequenceIds, String columns,\r
199           String sep)\r
200   {\r
201     if (sep == null || sep.length() == 0)\r
202     {\r
203       sep = separator;\r
204     }\r
205     else\r
206     {\r
207       if (debug)\r
208       {\r
209         System.err.println("Selecting region using separator string '"\r
210                 + separator + "'");\r
211       }\r
212     }\r
213     // deparse fields\r
214     String[] ids = separatorListToArray(sequenceIds, sep);\r
215     String[] cols = separatorListToArray(columns, sep);\r
216     SequenceGroup sel = new SequenceGroup();\r
217     ColumnSelection csel = new ColumnSelection();\r
218     AlignmentI al = alf.viewport.getAlignment();\r
219     jalview.analysis.SequenceIdMatcher matcher = new jalview.analysis.SequenceIdMatcher(\r
220             alf.viewport.getAlignment().getSequencesArray());\r
221     int start = 0, end = al.getWidth(), alw = al.getWidth();\r
222     boolean seqsfound = true;\r
223     if (ids != null && ids.length > 0)\r
224     {\r
225       seqsfound = false;\r
226       for (int i = 0; i < ids.length; i++)\r
227       {\r
228         if (ids[i].trim().length() == 0)\r
229         {\r
230           continue;\r
231         }\r
232         SequenceI sq = matcher.findIdMatch(ids[i]);\r
233         if (sq != null)\r
234         {\r
235           seqsfound = true;\r
236           sel.addSequence(sq, false);\r
237         }\r
238       }\r
239     }\r
240     boolean inseqpos = false;\r
241     if (cols != null && cols.length > 0)\r
242     {\r
243       boolean seset = false;\r
244       for (int i = 0; i < cols.length; i++)\r
245       {\r
246         String cl = cols[i].trim();\r
247         if (cl.length() == 0)\r
248         {\r
249           continue;\r
250         }\r
251         int p;\r
252         if ((p = cl.indexOf("-")) > -1)\r
253         {\r
254           int from = -1, to = -1;\r
255           try\r
256           {\r
257             from = new Integer(cl.substring(0, p)).intValue();\r
258             from--;\r
259           } catch (NumberFormatException ex)\r
260           {\r
261             System.err\r
262                     .println("ERROR: Couldn't parse first integer in range element column selection string '"\r
263                             + cl + "' - format is 'from-to'");\r
264             return;\r
265           }\r
266           try\r
267           {\r
268             to = new Integer(cl.substring(p + 1)).intValue();\r
269             to--;\r
270           } catch (NumberFormatException ex)\r
271           {\r
272             System.err\r
273                     .println("ERROR: Couldn't parse second integer in range element column selection string '"\r
274                             + cl + "' - format is 'from-to'");\r
275             return;\r
276           }\r
277           if (from >= 0 && to >= 0)\r
278           {\r
279             // valid range\r
280             if (from < to)\r
281             {\r
282               int t = to;\r
283               to = from;\r
284               to = t;\r
285             }\r
286             if (!seset)\r
287             {\r
288               start = from;\r
289               end = to;\r
290               seset = true;\r
291             }\r
292             else\r
293             {\r
294               // comment to prevent range extension\r
295               if (start > from)\r
296               {\r
297                 start = from;\r
298               }\r
299               if (end < to)\r
300               {\r
301                 end = to;\r
302               }\r
303             }\r
304             for (int r = from; r <= to; r++)\r
305             {\r
306               if (r >= 0 && r < alw)\r
307               {\r
308                 csel.addElement(r);\r
309               }\r
310             }\r
311             if (debug)\r
312             {\r
313               System.err.println("Range '" + cl + "' deparsed as [" + from\r
314                       + "," + to + "]");\r
315             }\r
316           }\r
317           else\r
318           {\r
319             System.err.println("ERROR: Invalid Range '" + cl\r
320                     + "' deparsed as [" + from + "," + to + "]");\r
321           }\r
322         }\r
323         else\r
324         {\r
325           int r = -1;\r
326           try\r
327           {\r
328             r = new Integer(cl).intValue();\r
329             r--;\r
330           } catch (NumberFormatException ex)\r
331           {\r
332             if (cl.toLowerCase().equals("sequence"))\r
333             {\r
334               // we are in the dataset sequence's coordinate frame.\r
335               inseqpos = true;\r
336             }\r
337             else\r
338             {\r
339               System.err\r
340                       .println("ERROR: Couldn't parse integer from point selection element of column selection string '"\r
341                               + cl + "'");\r
342               return;\r
343             }\r
344           }\r
345           if (r >= 0 && r <= alw)\r
346           {\r
347             if (!seset)\r
348             {\r
349               start = r;\r
350               end = r;\r
351               seset = true;\r
352             }\r
353             else\r
354             {\r
355               // comment to prevent range extension\r
356               if (start > r)\r
357               {\r
358                 start = r;\r
359               }\r
360               if (end < r)\r
361               {\r
362                 end = r;\r
363               }\r
364             }\r
365             csel.addElement(r);\r
366             if (debug)\r
367             {\r
368               System.err.println("Point selection '" + cl\r
369                       + "' deparsed as [" + r + "]");\r
370             }\r
371           }\r
372           else\r
373           {\r
374             System.err.println("ERROR: Invalid Point selection '" + cl\r
375                     + "' deparsed as [" + r + "]");\r
376           }\r
377         }\r
378       }\r
379     }\r
380     if (seqsfound)\r
381     {\r
382       // we only propagate the selection when it was the null selection, or the\r
383       // given sequences were found in the alignment.\r
384       if (inseqpos && sel.getSize() > 0)\r
385       {\r
386         // assume first sequence provides reference frame ?\r
387         SequenceI rs = sel.getSequenceAt(0);\r
388         start = rs.findIndex(start);\r
389         end = rs.findIndex(end);\r
390         if (csel != null)\r
391         {\r
392           Vector cs = csel.getSelected();\r
393           csel.clear();\r
394           for (int csi = 0, csiS = cs.size(); csi < csiS; csi++)\r
395           {\r
396             csel.addElement(rs.findIndex(((Integer) cs.elementAt(csi))\r
397                     .intValue()));\r
398           }\r
399         }\r
400       }\r
401       sel.setStartRes(start);\r
402       sel.setEndRes(end);\r
403       alf.select(sel, csel);\r
404     }\r
405   }\r
406 \r
407   /* (non-Javadoc)\r
408    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequencesAsAlignment(java.lang.String, java.lang.String)\r
409    */\r
410   public String getSelectedSequencesAsAlignment(String format, String suffix)\r
411   {\r
412     return getSelectedSequencesAsAlignmentFrom(getDefaultTargetFrame(),\r
413             format, suffix);\r
414   }\r
415 \r
416   /* (non-Javadoc)\r
417    * @see jalview.bin.JalviewLiteJsApi#getSelectedSequencesAsAlignmentFrom(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String)\r
418    */\r
419   public String getSelectedSequencesAsAlignmentFrom(AlignFrame alf,\r
420           String format, String suffix)\r
421   {\r
422     try\r
423     {\r
424       boolean seqlimits = suffix.equalsIgnoreCase("true");\r
425       if (alf.viewport.getSelectionGroup() != null)\r
426       {\r
427         String reply = new AppletFormatAdapter().formatSequences(format,\r
428                 new Alignment(alf.viewport.getSelectionAsNewSequence()),\r
429                 seqlimits);\r
430         return reply;\r
431       }\r
432     } catch (Exception ex)\r
433     {\r
434       ex.printStackTrace();\r
435       return "Error retrieving alignment in " + format + " format. ";\r
436     }\r
437     return "";\r
438   }\r
439 \r
440   /* (non-Javadoc)\r
441    * @see jalview.bin.JalviewLiteJsApi#getAlignmentOrder()\r
442    */\r
443   public String getAlignmentOrder()\r
444   {\r
445     return getAlignmentOrderFrom(getDefaultTargetFrame());\r
446   }\r
447 \r
448   /* (non-Javadoc)\r
449    * @see jalview.bin.JalviewLiteJsApi#getAlignmentOrderFrom(jalview.appletgui.AlignFrame)\r
450    */\r
451   public String getAlignmentOrderFrom(AlignFrame alf)\r
452   {\r
453     return getAlignmentOrderFrom(alf, separator);\r
454   }\r
455 \r
456   /* (non-Javadoc)\r
457    * @see jalview.bin.JalviewLiteJsApi#getAlignmentOrderFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
458    */\r
459   public String getAlignmentOrderFrom(AlignFrame alf, String sep)\r
460   {\r
461     AlignmentI alorder = alf.getAlignViewport().getAlignment();\r
462     String[] order = new String[alorder.getHeight()];\r
463     for (int i = 0; i < order.length; i++)\r
464     {\r
465       order[i] = alorder.getSequenceAt(i).getName();\r
466     }\r
467     return arrayToSeparatorList(order);\r
468   }\r
469 \r
470   /* (non-Javadoc)\r
471    * @see jalview.bin.JalviewLiteJsApi#orderBy(java.lang.String, java.lang.String)\r
472    */\r
473   public String orderBy(String order, String undoName)\r
474   {\r
475     return orderBy(order, undoName, separator);\r
476   }\r
477 \r
478   /* (non-Javadoc)\r
479    * @see jalview.bin.JalviewLiteJsApi#orderBy(java.lang.String, java.lang.String, java.lang.String)\r
480    */\r
481   public String orderBy(String order, String undoName, String sep)\r
482   {\r
483     return orderAlignmentBy(getDefaultTargetFrame(), order, undoName, sep);\r
484   }\r
485 \r
486   /* (non-Javadoc)\r
487    * @see jalview.bin.JalviewLiteJsApi#orderAlignmentBy(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String, java.lang.String)\r
488    */\r
489   public String orderAlignmentBy(AlignFrame alf, String order,\r
490           String undoName, String sep)\r
491   {\r
492     String[] ids = separatorListToArray(order, sep);\r
493     SequenceI[] sqs = null;\r
494     if (ids != null && ids.length > 0)\r
495     {\r
496       jalview.analysis.SequenceIdMatcher matcher = new jalview.analysis.SequenceIdMatcher(\r
497               alf.viewport.getAlignment().getSequencesArray());\r
498       int s = 0;\r
499       sqs = new SequenceI[ids.length];\r
500       for (int i = 0; i < ids.length; i++)\r
501       {\r
502         if (ids[i].trim().length() == 0)\r
503         {\r
504           continue;\r
505         }\r
506         SequenceI sq = matcher.findIdMatch(ids[i]);\r
507         if (sq != null)\r
508         {\r
509           sqs[s++] = sq;\r
510         }\r
511       }\r
512       if (s > 0)\r
513       {\r
514         SequenceI[] sqq = new SequenceI[s];\r
515         System.arraycopy(sqs, 0, sqq, 0, s);\r
516         sqs = sqq;\r
517       }\r
518       else\r
519       {\r
520         sqs = null;\r
521       }\r
522     }\r
523     if (sqs == null)\r
524     {\r
525       return "";\r
526     }\r
527     ;\r
528     AlignmentOrder aorder = new AlignmentOrder(sqs);\r
529 \r
530     if (undoName != null && undoName.trim().length() == 0)\r
531     {\r
532       undoName = null;\r
533     }\r
534 \r
535     return alf.sortBy(aorder, undoName) ? "true" : "";\r
536   }\r
537 \r
538   /* (non-Javadoc)\r
539    * @see jalview.bin.JalviewLiteJsApi#getAlignment(java.lang.String)\r
540    */\r
541   public String getAlignment(String format)\r
542   {\r
543     return getAlignmentFrom(getDefaultTargetFrame(), format, "true");\r
544   }\r
545 \r
546   /* (non-Javadoc)\r
547    * @see jalview.bin.JalviewLiteJsApi#getAlignmentFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
548    */\r
549   public String getAlignmentFrom(AlignFrame alf, String format)\r
550   {\r
551     return getAlignmentFrom(alf, format, "true");\r
552   }\r
553 \r
554   /* (non-Javadoc)\r
555    * @see jalview.bin.JalviewLiteJsApi#getAlignment(java.lang.String, java.lang.String)\r
556    */\r
557   public String getAlignment(String format, String suffix)\r
558   {\r
559     return getAlignmentFrom(getDefaultTargetFrame(), format, suffix);\r
560   }\r
561 \r
562   /* (non-Javadoc)\r
563    * @see jalview.bin.JalviewLiteJsApi#getAlignmentFrom(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String)\r
564    */\r
565   public String getAlignmentFrom(AlignFrame alf, String format,\r
566           String suffix)\r
567   {\r
568     try\r
569     {\r
570       boolean seqlimits = suffix.equalsIgnoreCase("true");\r
571 \r
572       String reply = new AppletFormatAdapter().formatSequences(format,\r
573               alf.viewport.getAlignment(), seqlimits);\r
574       return reply;\r
575     } catch (Exception ex)\r
576     {\r
577       ex.printStackTrace();\r
578       return "Error retrieving alignment in " + format + " format. ";\r
579     }\r
580   }\r
581 \r
582   /* (non-Javadoc)\r
583    * @see jalview.bin.JalviewLiteJsApi#loadAnnotation(java.lang.String)\r
584    */\r
585   public void loadAnnotation(String annotation)\r
586   {\r
587     loadAnnotationFrom(getDefaultTargetFrame(), annotation);\r
588   }\r
589 \r
590   /* (non-Javadoc)\r
591    * @see jalview.bin.JalviewLiteJsApi#loadAnnotationFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
592    */\r
593   public void loadAnnotationFrom(AlignFrame alf, String annotation)\r
594   {\r
595     if (new AnnotationFile().readAnnotationFile(alf.getAlignViewport()\r
596             .getAlignment(), annotation, AppletFormatAdapter.PASTE))\r
597     {\r
598       alf.alignPanel.fontChanged();\r
599       alf.alignPanel.setScrollValues(0, 0);\r
600     }\r
601     else\r
602     {\r
603       alf.parseFeaturesFile(annotation, AppletFormatAdapter.PASTE);\r
604     }\r
605   }\r
606 \r
607   /* (non-Javadoc)\r
608    * @see jalview.bin.JalviewLiteJsApi#getFeatures(java.lang.String)\r
609    */\r
610   public String getFeatures(String format)\r
611   {\r
612     return getFeaturesFrom(getDefaultTargetFrame(), format);\r
613   }\r
614 \r
615   /* (non-Javadoc)\r
616    * @see jalview.bin.JalviewLiteJsApi#getFeaturesFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
617    */\r
618   public String getFeaturesFrom(AlignFrame alf, String format)\r
619   {\r
620     return alf.outputFeatures(false, format);\r
621   }\r
622 \r
623   /* (non-Javadoc)\r
624    * @see jalview.bin.JalviewLiteJsApi#getAnnotation()\r
625    */\r
626   public String getAnnotation()\r
627   {\r
628     return getAnnotationFrom(getDefaultTargetFrame());\r
629   }\r
630 \r
631   /* (non-Javadoc)\r
632    * @see jalview.bin.JalviewLiteJsApi#getAnnotationFrom(jalview.appletgui.AlignFrame)\r
633    */\r
634   public String getAnnotationFrom(AlignFrame alf)\r
635   {\r
636     return alf.outputAnnotations(false);\r
637   }\r
638 \r
639   /* (non-Javadoc)\r
640    * @see jalview.bin.JalviewLiteJsApi#newView()\r
641    */\r
642   public AlignFrame newView()\r
643   {\r
644     return newViewFrom(getDefaultTargetFrame());\r
645   }\r
646 \r
647   /* (non-Javadoc)\r
648    * @see jalview.bin.JalviewLiteJsApi#newView(java.lang.String)\r
649    */\r
650   public AlignFrame newView(String name)\r
651   {\r
652     return newViewFrom(getDefaultTargetFrame(), name);\r
653   }\r
654 \r
655   /* (non-Javadoc)\r
656    * @see jalview.bin.JalviewLiteJsApi#newViewFrom(jalview.appletgui.AlignFrame)\r
657    */\r
658   public AlignFrame newViewFrom(AlignFrame alf)\r
659   {\r
660     return alf.newView(null);\r
661   }\r
662 \r
663   /* (non-Javadoc)\r
664    * @see jalview.bin.JalviewLiteJsApi#newViewFrom(jalview.appletgui.AlignFrame, java.lang.String)\r
665    */\r
666   public AlignFrame newViewFrom(AlignFrame alf, String name)\r
667   {\r
668     return alf.newView(name);\r
669   }\r
670 \r
671   /* (non-Javadoc)\r
672    * @see jalview.bin.JalviewLiteJsApi#loadAlignment(java.lang.String, java.lang.String)\r
673    */\r
674   public AlignFrame loadAlignment(String text, String title)\r
675   {\r
676     Alignment al = null;\r
677 \r
678     String format = new IdentifyFile().Identify(text,\r
679             AppletFormatAdapter.PASTE);\r
680     try\r
681     {\r
682       al = new AppletFormatAdapter().readFile(text,\r
683               AppletFormatAdapter.PASTE, format);\r
684       if (al.getHeight() > 0)\r
685       {\r
686         return new AlignFrame(al, this, title, false);\r
687       }\r
688     } catch (java.io.IOException ex)\r
689     {\r
690       ex.printStackTrace();\r
691     }\r
692     return null;\r
693   }\r
694 \r
695   /* (non-Javadoc)\r
696    * @see jalview.bin.JalviewLiteJsApi#setMouseoverListener(java.lang.String)\r
697    */\r
698   public void setMouseoverListener(String listener)\r
699   {\r
700     setMouseoverListener(currentAlignFrame, listener);\r
701   }\r
702 \r
703   private Vector<jalview.javascript.JSFunctionExec> javascriptListeners = new Vector<jalview.javascript.JSFunctionExec>();\r
704 \r
705   /* (non-Javadoc)\r
706    * @see jalview.bin.JalviewLiteJsApi#setMouseoverListener(jalview.appletgui.AlignFrame, java.lang.String)\r
707    */\r
708   public void setMouseoverListener(AlignFrame af, String listener)\r
709   {\r
710     if (listener != null)\r
711     {\r
712       listener = listener.trim();\r
713       if (listener.length() == 0)\r
714       {\r
715         System.err\r
716                 .println("jalview Javascript error: Ignoring empty function for mouseover listener.");\r
717         return;\r
718       }\r
719     }\r
720     jalview.javascript.MouseOverListener mol = new jalview.javascript.MouseOverListener(\r
721             this, af, listener);\r
722     javascriptListeners.addElement(mol);\r
723     StructureSelectionManager.getStructureSelectionManager(this)\r
724             .addStructureViewerListener(mol);\r
725     if (debug)\r
726     {\r
727       System.err.println("Added a mouseover listener for "\r
728               + ((af == null) ? "All frames" : "Just views for "\r
729                       + af.getAlignViewport().getSequenceSetId()));\r
730       System.err.println("There are now " + javascriptListeners.size()\r
731               + " listeners in total.");\r
732     }\r
733   }\r
734 \r
735   /* (non-Javadoc)\r
736    * @see jalview.bin.JalviewLiteJsApi#setSelectionListener(java.lang.String)\r
737    */\r
738   public void setSelectionListener(String listener)\r
739   {\r
740     setSelectionListener(null, listener);\r
741   }\r
742 \r
743   /* (non-Javadoc)\r
744    * @see jalview.bin.JalviewLiteJsApi#setSelectionListener(jalview.appletgui.AlignFrame, java.lang.String)\r
745    */\r
746   public void setSelectionListener(AlignFrame af, String listener)\r
747   {\r
748     if (listener != null)\r
749     {\r
750       listener = listener.trim();\r
751       if (listener.length() == 0)\r
752       {\r
753         System.err\r
754                 .println("jalview Javascript error: Ignoring empty function for selection listener.");\r
755         return;\r
756       }\r
757     }\r
758     jalview.javascript.JsSelectionSender mol = new jalview.javascript.JsSelectionSender(\r
759             this, af, listener);\r
760     javascriptListeners.addElement(mol);\r
761     StructureSelectionManager.getStructureSelectionManager(this)\r
762             .addSelectionListener(mol);\r
763     if (debug)\r
764     {\r
765       System.err.println("Added a selection listener for "\r
766               + ((af == null) ? "All frames" : "Just views for "\r
767                       + af.getAlignViewport().getSequenceSetId()));\r
768       System.err.println("There are now " + javascriptListeners.size()\r
769               + " listeners in total.");\r
770     }\r
771   }\r
772 \r
773   /* (non-Javadoc)\r
774    * @see jalview.bin.JalviewLiteJsApi#setStructureListener(java.lang.String, java.lang.String)\r
775    */\r
776   public void setStructureListener(String listener, String modelSet)\r
777   {\r
778     if (listener != null)\r
779     {\r
780       listener = listener.trim();\r
781       if (listener.length() == 0)\r
782       {\r
783         System.err\r
784                 .println("jalview Javascript error: Ignoring empty function for selection listener.");\r
785         return;\r
786       }\r
787     }\r
788     jalview.javascript.MouseOverStructureListener mol = new jalview.javascript.MouseOverStructureListener(\r
789             this, listener, separatorListToArray(modelSet));\r
790     javascriptListeners.addElement(mol);\r
791     StructureSelectionManager.getStructureSelectionManager(this)\r
792             .addStructureViewerListener(mol);\r
793     if (debug)\r
794     {\r
795       System.err.println("Added a javascript structure viewer listener '"\r
796               + listener + "'");\r
797       System.err.println("There are now " + javascriptListeners.size()\r
798               + " listeners in total.");\r
799     }\r
800   }\r
801 \r
802   /* (non-Javadoc)\r
803    * @see jalview.bin.JalviewLiteJsApi#removeJavascriptListener(jalview.appletgui.AlignFrame, java.lang.String)\r
804    */\r
805   public void removeJavascriptListener(AlignFrame af, String listener)\r
806   {\r
807     if (listener != null)\r
808     {\r
809       listener = listener.trim();\r
810       if (listener.length() == 0)\r
811       {\r
812         listener = null;\r
813       }\r
814     }\r
815     boolean rprt = false;\r
816     for (int ms = 0, msSize = javascriptListeners.size(); ms < msSize;)\r
817     {\r
818       Object lstn = javascriptListeners.elementAt(ms);\r
819       JsCallBack lstner = (JsCallBack) lstn;\r
820       if ((af == null || lstner.getAlignFrame() == af)\r
821               && (listener == null || lstner.getListenerFunction().equals(\r
822                       listener)))\r
823       {\r
824         javascriptListeners.removeElement(lstner);\r
825         msSize--;\r
826         if (lstner instanceof SelectionListener)\r
827         {\r
828           StructureSelectionManager.getStructureSelectionManager(this)\r
829                   .removeSelectionListener((SelectionListener) lstner);\r
830         }\r
831         else\r
832         {\r
833           StructureSelectionManager.getStructureSelectionManager(this)\r
834                   .removeStructureViewerListener(lstner, null);\r
835         }\r
836         rprt = debug;\r
837         if (debug)\r
838         {\r
839           System.err.println("Removed listener '" + listener + "'");\r
840         }\r
841       }\r
842       else\r
843       {\r
844         ms++;\r
845       }\r
846     }\r
847     if (rprt)\r
848     {\r
849       System.err.println("There are now " + javascriptListeners.size()\r
850               + " listeners in total.");\r
851     }\r
852   }\r
853 \r
854   public void stop()\r
855   {\r
856     System.err.println("Applet "+getName()+" stop().");\r
857     tidyUp();\r
858   }\r
859   public void destroy()\r
860   {\r
861     System.err.println("Applet "+getName()+" destroy().");\r
862     tidyUp();\r
863   }\r
864   private void tidyUp()\r
865   {\r
866     removeAll();\r
867     if (currentAlignFrame!=null && currentAlignFrame.viewport!=null\r
868             && currentAlignFrame.viewport.applet!=null)\r
869     {\r
870       AlignViewport av = currentAlignFrame.viewport;\r
871       currentAlignFrame.closeMenuItem_actionPerformed();\r
872       av.applet=null;\r
873       currentAlignFrame=null;\r
874     }\r
875     if (javascriptListeners != null)\r
876     {\r
877       while (javascriptListeners.size() > 0)\r
878       {\r
879         jalview.javascript.JSFunctionExec mol = javascriptListeners.elementAt(0);\r
880         javascriptListeners.removeElement(mol);\r
881         if (mol instanceof SelectionListener)\r
882         {\r
883           StructureSelectionManager.getStructureSelectionManager(this)\r
884                   .removeSelectionListener((SelectionListener) mol);\r
885         }\r
886         else\r
887         {\r
888           StructureSelectionManager.getStructureSelectionManager(this)\r
889                   .removeStructureViewerListener(mol, null);\r
890         }\r
891         mol.jvlite=null;\r
892       }\r
893     }\r
894     if (jsFunctionExec!=null) {\r
895       jsFunctionExec.stopQueue();\r
896       jsFunctionExec.jvlite=null;\r
897     }\r
898     initialAlignFrame=null;\r
899     jsFunctionExec = null;\r
900     javascriptListeners=null;\r
901     StructureSelectionManager.release(this);\r
902   }\r
903   private jalview.javascript.JSFunctionExec jsFunctionExec;\r
904   /* (non-Javadoc)\r
905    * @see jalview.bin.JalviewLiteJsApi#mouseOverStructure(java.lang.String, java.lang.String, java.lang.String)\r
906    */\r
907   public void mouseOverStructure(String pdbResNum, String chain,\r
908           String pdbfile)\r
909   {\r
910     try\r
911     {\r
912       StructureSelectionManager.getStructureSelectionManager(this)\r
913               .mouseOverStructure(new Integer(pdbResNum).intValue(), chain,\r
914                       pdbfile);\r
915       if (debug)\r
916       {\r
917         System.err.println("mouseOver for '" + pdbResNum + "' in chain '"\r
918                 + chain + "' in structure '" + pdbfile + "'");\r
919       }\r
920     } catch (NumberFormatException e)\r
921     {\r
922       System.err.println("Ignoring invalid residue number string '"\r
923               + pdbResNum + "'");\r
924     }\r
925   }\r
926   /* (non-Javadoc)\r
927    * @see jalview.bin.JalviewLiteJsApi#scrollViewToIn(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String)\r
928    */\r
929   public void scrollViewToIn(AlignFrame alf, String topRow, String leftHandColumn)\r
930   {\r
931     try {\r
932       alf.scrollTo(new Integer(topRow).intValue(), new Integer(leftHandColumn).intValue());\r
933       \r
934     } catch (Exception ex)\r
935     {\r
936       System.err.println("Couldn't parse integer arguments (topRow='"+topRow+"' and leftHandColumn='"+leftHandColumn+"'");\r
937       ex.printStackTrace();\r
938     }\r
939   }\r
940 \r
941   // //////////////////////////////////////////////\r
942   // //////////////////////////////////////////////\r
943 \r
944   public static int lastFrameX = 200;\r
945 \r
946   public static int lastFrameY = 200;\r
947 \r
948   boolean fileFound = true;\r
949 \r
950   String file = "No file";\r
951 \r
952   Button launcher = new Button("Start Jalview");\r
953 \r
954   /**\r
955    * The currentAlignFrame is static, it will change if and when the user\r
956    * selects a new window. Note that it will *never* point back to the embedded\r
957    * AlignFrame if the applet is started as embedded on the page and then\r
958    * afterwards a new view is created.\r
959    */\r
960   public AlignFrame currentAlignFrame = null;\r
961 \r
962   /**\r
963    * This is the first frame to be displayed, and does not change. API calls\r
964    * will default to this instance if currentAlignFrame is null.\r
965    */\r
966   AlignFrame initialAlignFrame = null;\r
967 \r
968   boolean embedded = false;\r
969 \r
970   private boolean checkForJmol = true;\r
971 \r
972   private boolean checkedForJmol = false; // ensure we don't check for jmol\r
973 \r
974   // every time the app is re-inited\r
975 \r
976   public boolean jmolAvailable = false;\r
977 \r
978   private boolean alignPdbStructures = false;\r
979 \r
980   /**\r
981    * use an external structure viewer exclusively (no jmols or MCViews will be\r
982    * opened by JalviewLite itself)\r
983    */\r
984   public boolean useXtrnalSviewer = false;\r
985 \r
986   public static boolean debug = false;\r
987 \r
988   static String builddate = null, version = null;\r
989 \r
990   private static void initBuildDetails()\r
991   {\r
992     if (builddate == null)\r
993     {\r
994       builddate = "unknown";\r
995       version = "test";\r
996       java.net.URL url = JalviewLite.class\r
997               .getResource("/.build_properties");\r
998       if (url != null)\r
999       {\r
1000         try\r
1001         {\r
1002           BufferedReader reader = new BufferedReader(new InputStreamReader(\r
1003                   url.openStream()));\r
1004           String line;\r
1005           while ((line = reader.readLine()) != null)\r
1006           {\r
1007             if (line.indexOf("VERSION") > -1)\r
1008             {\r
1009               version = line.substring(line.indexOf("=") + 1);\r
1010             }\r
1011             if (line.indexOf("BUILD_DATE") > -1)\r
1012             {\r
1013               builddate = line.substring(line.indexOf("=") + 1);\r
1014             }\r
1015           }\r
1016         } catch (Exception ex)\r
1017         {\r
1018           ex.printStackTrace();\r
1019         }\r
1020       }\r
1021     }\r
1022   }\r
1023 \r
1024   public static String getBuildDate()\r
1025   {\r
1026     initBuildDetails();\r
1027     return builddate;\r
1028   }\r
1029 \r
1030   public static String getVersion()\r
1031   {\r
1032     initBuildDetails();\r
1033     return version;\r
1034   }\r
1035 \r
1036   // public JSObject scriptObject = null;\r
1037 \r
1038   /**\r
1039    * init method for Jalview Applet\r
1040    */\r
1041   public void init()\r
1042   {\r
1043     // remove any handlers that might be hanging around from an earlier instance\r
1044     try\r
1045     {\r
1046       if (debug)\r
1047       {\r
1048         System.err.println("Applet context is '"\r
1049                 + getAppletContext().getClass().toString() + "'");\r
1050       }\r
1051       JSObject scriptObject = JSObject.getWindow(this);\r
1052       if (debug && scriptObject != null)\r
1053       {\r
1054         System.err.println("Applet has Javascript callback support.");\r
1055       }\r
1056 \r
1057     } catch (Exception ex)\r
1058     {\r
1059       System.err\r
1060               .println("Warning: No JalviewLite javascript callbacks available.");\r
1061       if (debug)\r
1062       {\r
1063         ex.printStackTrace();\r
1064       }\r
1065     }\r
1066     /**\r
1067      * turn on extra applet debugging\r
1068      */\r
1069     String dbg = getParameter("debug");\r
1070     if (dbg != null)\r
1071     {\r
1072       debug = dbg.toLowerCase().equals("true");\r
1073     }\r
1074     if (debug)\r
1075     {\r
1076 \r
1077       System.err.println("JalviewLite Version " + getVersion());\r
1078       System.err.println("Build Date : " + getBuildDate());\r
1079 \r
1080     }\r
1081     String externalsviewer = getParameter("externalstructureviewer");\r
1082     if (externalsviewer != null)\r
1083     {\r
1084       useXtrnalSviewer = externalsviewer.trim().toLowerCase()\r
1085               .equals("true");\r
1086     }\r
1087     /**\r
1088      * if true disable the check for jmol\r
1089      */\r
1090     String chkforJmol = getParameter("nojmol");\r
1091     if (chkforJmol != null)\r
1092     {\r
1093       checkForJmol = !chkforJmol.equals("true");\r
1094     }\r
1095     /**\r
1096      * get the separator parameter if present\r
1097      */\r
1098     String sep = getParameter("separator");\r
1099     if (sep != null)\r
1100     {\r
1101       if (sep.length() > 0)\r
1102       {\r
1103         separator = sep;\r
1104         if (debug)\r
1105         {\r
1106           System.err.println("Separator set to '" + separator + "'");\r
1107         }\r
1108       }\r
1109       else\r
1110       {\r
1111         throw new Error(\r
1112                 "Invalid separator parameter - must be non-zero length");\r
1113       }\r
1114     }\r
1115     int r = 255;\r
1116     int g = 255;\r
1117     int b = 255;\r
1118     String param = getParameter("RGB");\r
1119 \r
1120     if (param != null)\r
1121     {\r
1122       try\r
1123       {\r
1124         r = Integer.parseInt(param.substring(0, 2), 16);\r
1125         g = Integer.parseInt(param.substring(2, 4), 16);\r
1126         b = Integer.parseInt(param.substring(4, 6), 16);\r
1127       } catch (Exception ex)\r
1128       {\r
1129         r = 255;\r
1130         g = 255;\r
1131         b = 255;\r
1132       }\r
1133     }\r
1134     param = getParameter("label");\r
1135     if (param != null)\r
1136     {\r
1137       launcher.setLabel(param);\r
1138     }\r
1139 \r
1140     setBackground(new Color(r, g, b));\r
1141 \r
1142     file = getParameter("file");\r
1143 \r
1144     if (file == null)\r
1145     {\r
1146       // Maybe the sequences are added as parameters\r
1147       StringBuffer data = new StringBuffer("PASTE");\r
1148       int i = 1;\r
1149       while ((file = getParameter("sequence" + i)) != null)\r
1150       {\r
1151         data.append(file.toString() + "\n");\r
1152         i++;\r
1153       }\r
1154       if (data.length() > 5)\r
1155       {\r
1156         file = data.toString();\r
1157       }\r
1158     }\r
1159 \r
1160     final JalviewLite jvapplet = this;\r
1161     if (getParameter("embedded") != null\r
1162             && getParameter("embedded").equalsIgnoreCase("true"))\r
1163     {\r
1164       // Launch as embedded applet in page\r
1165       embedded = true;\r
1166       LoadingThread loader = new LoadingThread(file, jvapplet);\r
1167       loader.start();\r
1168     }\r
1169     else if (file != null)\r
1170     {\r
1171       if (getParameter("showbutton") == null\r
1172               || !getParameter("showbutton").equalsIgnoreCase("false"))\r
1173       {\r
1174         // Add the JalviewLite 'Button' to the page\r
1175         add(launcher);\r
1176         launcher.addActionListener(new java.awt.event.ActionListener()\r
1177         {\r
1178           public void actionPerformed(ActionEvent e)\r
1179           {\r
1180             LoadingThread loader = new LoadingThread(file, jvapplet);\r
1181             loader.start();\r
1182           }\r
1183         });\r
1184       }\r
1185       else\r
1186       {\r
1187         // Open jalviewLite immediately.\r
1188         LoadingThread loader = new LoadingThread(file, jvapplet);\r
1189         loader.start();\r
1190       }\r
1191     }\r
1192     else\r
1193     {\r
1194       // jalview initialisation with no alignment. loadAlignment() method can\r
1195       // still be called to open new alignments.\r
1196       file = "NO FILE";\r
1197       fileFound = false;\r
1198       // callInitCallback();\r
1199     }\r
1200   }\r
1201 \r
1202   private void callInitCallback()\r
1203   {\r
1204     String initjscallback = getParameter("oninit");\r
1205     if (initjscallback == null)\r
1206     {\r
1207       return;\r
1208     }\r
1209     initjscallback = initjscallback.trim();\r
1210     if (initjscallback.length() > 0)\r
1211     {\r
1212       JSObject scriptObject = null;\r
1213       try\r
1214       {\r
1215         scriptObject = JSObject.getWindow(this);\r
1216       } catch (Exception ex)\r
1217       {\r
1218       }\r
1219       ;\r
1220       if (scriptObject != null)\r
1221       {\r
1222         try\r
1223         {\r
1224           // do onInit with the JS executor thread\r
1225           new JSFunctionExec(this).executeJavascriptFunction(true,\r
1226                   initjscallback, null, "Calling oninit callback '"\r
1227                           + initjscallback + "'.");\r
1228         } catch (Exception e)\r
1229         {\r
1230           System.err.println("Exception when executing _oninit callback '"\r
1231                   + initjscallback + "'.");\r
1232           e.printStackTrace();\r
1233         }\r
1234       }\r
1235       else\r
1236       {\r
1237         System.err.println("Not executing _oninit callback '"\r
1238                 + initjscallback + "' - no scripting allowed.");\r
1239       }\r
1240     }\r
1241   }\r
1242 \r
1243   /**\r
1244    * Initialises and displays a new java.awt.Frame\r
1245    * \r
1246    * @param frame\r
1247    *          java.awt.Frame to be displayed\r
1248    * @param title\r
1249    *          title of new frame\r
1250    * @param width\r
1251    *          width if new frame\r
1252    * @param height\r
1253    *          height of new frame\r
1254    */\r
1255   public static void addFrame(final Frame frame, String title, int width,\r
1256           int height)\r
1257   {\r
1258     frame.setLocation(lastFrameX, lastFrameY);\r
1259     lastFrameX += 40;\r
1260     lastFrameY += 40;\r
1261     frame.setSize(width, height);\r
1262     frame.setTitle(title);\r
1263     frame.addWindowListener(new WindowAdapter()\r
1264     {\r
1265       public void windowClosing(WindowEvent e)\r
1266       {\r
1267         if (frame instanceof AlignFrame)\r
1268         {\r
1269           AlignViewport vp = ((AlignFrame) frame).viewport;\r
1270           ((AlignFrame) frame).closeMenuItem_actionPerformed();\r
1271           if (vp.applet.currentAlignFrame == frame)\r
1272           {\r
1273             vp.applet.currentAlignFrame = null;\r
1274           }\r
1275           vp.applet=null;\r
1276           vp=null;\r
1277           \r
1278         }\r
1279         lastFrameX -= 40;\r
1280         lastFrameY -= 40;\r
1281         if (frame instanceof EmbmenuFrame)\r
1282         {\r
1283           ((EmbmenuFrame) frame).destroyMenus();\r
1284         }\r
1285         frame.setMenuBar(null);\r
1286         frame.dispose();\r
1287       }\r
1288 \r
1289       public void windowActivated(WindowEvent e)\r
1290       {\r
1291         if (frame instanceof AlignFrame)\r
1292         {\r
1293           ((AlignFrame) frame).viewport.applet.currentAlignFrame = (AlignFrame) frame;\r
1294           if (debug)\r
1295           {\r
1296             System.err.println("Activated window " + frame);\r
1297           }\r
1298         }\r
1299         // be good.\r
1300         super.windowActivated(e);\r
1301       }\r
1302       /*\r
1303        * Probably not necessary to do this - see TODO above. (non-Javadoc)\r
1304        * \r
1305        * @see\r
1306        * java.awt.event.WindowAdapter#windowDeactivated(java.awt.event.WindowEvent\r
1307        * )\r
1308        * \r
1309        * public void windowDeactivated(WindowEvent e) { if (currentAlignFrame ==\r
1310        * frame) { currentAlignFrame = null; if (debug) {\r
1311        * System.err.println("Deactivated window "+frame); } }\r
1312        * super.windowDeactivated(e); }\r
1313        */\r
1314     });\r
1315     frame.setVisible(true);\r
1316   }\r
1317 \r
1318   /**\r
1319    * This paints the background surrounding the "Launch Jalview button" <br>\r
1320    * <br>\r
1321    * If file given in parameter not found, displays error message\r
1322    * \r
1323    * @param g\r
1324    *          graphics context\r
1325    */\r
1326   public void paint(Graphics g)\r
1327   {\r
1328     if (!fileFound)\r
1329     {\r
1330       g.setColor(new Color(200, 200, 200));\r
1331       g.setColor(Color.cyan);\r
1332       g.fillRect(0, 0, getSize().width, getSize().height);\r
1333       g.setColor(Color.red);\r
1334       g.drawString("Jalview can't open file", 5, 15);\r
1335       g.drawString("\"" + file + "\"", 5, 30);\r
1336     }\r
1337     else if (embedded)\r
1338     {\r
1339       g.setColor(Color.black);\r
1340       g.setFont(new Font("Arial", Font.BOLD, 24));\r
1341       g.drawString("Jalview Applet", 50, getSize().height / 2 - 30);\r
1342       g.drawString("Loading Data...", 50, getSize().height / 2);\r
1343     }\r
1344   }\r
1345 \r
1346   /**\r
1347    * get all components associated with the applet of the given type\r
1348    * \r
1349    * @param class1\r
1350    * @return\r
1351    */\r
1352   public Vector getAppletWindow(Class class1)\r
1353   {\r
1354     Vector wnds = new Vector();\r
1355     Component[] cmp = getComponents();\r
1356     if (cmp != null)\r
1357     {\r
1358       for (int i = 0; i < cmp.length; i++)\r
1359       {\r
1360         if (class1.isAssignableFrom(cmp[i].getClass()))\r
1361         {\r
1362           wnds.addElement(cmp);\r
1363         }\r
1364       }\r
1365     }\r
1366     return wnds;\r
1367   }\r
1368 \r
1369   class LoadJmolThread extends Thread\r
1370   {\r
1371     private boolean running = false;\r
1372 \r
1373     public void run()\r
1374     {\r
1375       if (running || checkedForJmol)\r
1376       {\r
1377         return;\r
1378       }\r
1379       running = true;\r
1380       if (checkForJmol)\r
1381       {\r
1382         try\r
1383         {\r
1384           if (!System.getProperty("java.version").startsWith("1.1"))\r
1385           {\r
1386             Class.forName("org.jmol.adapter.smarter.SmarterJmolAdapter");\r
1387             jmolAvailable = true;\r
1388           }\r
1389           if (!jmolAvailable)\r
1390           {\r
1391             System.out\r
1392                     .println("Jmol not available - Using MCview for structures");\r
1393           }\r
1394         } catch (java.lang.ClassNotFoundException ex)\r
1395         {\r
1396         }\r
1397       }\r
1398       else\r
1399       {\r
1400         jmolAvailable = false;\r
1401         if (debug)\r
1402         {\r
1403           System.err\r
1404                   .println("Skipping Jmol check. Will use MCView (probably)");\r
1405         }\r
1406       }\r
1407       checkedForJmol = true;\r
1408       running = false;\r
1409     }\r
1410 \r
1411     public boolean notFinished()\r
1412     {\r
1413       return running || !checkedForJmol;\r
1414     }\r
1415   }\r
1416 \r
1417   class LoadingThread extends Thread\r
1418   {\r
1419     /**\r
1420      * State variable: File source\r
1421      */\r
1422     String file;\r
1423 \r
1424     /**\r
1425      * State variable: protocol for access to file source\r
1426      */\r
1427     String protocol;\r
1428 \r
1429     /**\r
1430      * State variable: format of file source\r
1431      */\r
1432     String format;\r
1433 \r
1434     String _file;\r
1435 \r
1436     JalviewLite applet;\r
1437 \r
1438     private void dbgMsg(String msg)\r
1439     {\r
1440       if (applet.debug)\r
1441       {\r
1442         System.err.println(msg);\r
1443       }\r
1444     }\r
1445 \r
1446     /**\r
1447      * update the protocol state variable for accessing the datasource located\r
1448      * by file.\r
1449      * \r
1450      * @param file\r
1451      * @return possibly updated datasource string\r
1452      */\r
1453     public String setProtocolState(String file)\r
1454     {\r
1455       if (file.startsWith("PASTE"))\r
1456       {\r
1457         file = file.substring(5);\r
1458         protocol = AppletFormatAdapter.PASTE;\r
1459       }\r
1460       else if (inArchive(file))\r
1461       {\r
1462         protocol = AppletFormatAdapter.CLASSLOADER;\r
1463       }\r
1464       else\r
1465       {\r
1466         file = addProtocol(file);\r
1467         protocol = AppletFormatAdapter.URL;\r
1468       }\r
1469       dbgMsg("Protocol identified as '" + protocol + "'");\r
1470       return file;\r
1471     }\r
1472 \r
1473     public LoadingThread(String _file, JalviewLite _applet)\r
1474     {\r
1475       this._file = _file;\r
1476       applet = _applet;\r
1477     }\r
1478 \r
1479     public void run()\r
1480     {\r
1481       LoadJmolThread jmolchecker = new LoadJmolThread();\r
1482       jmolchecker.start();\r
1483       while (jmolchecker.notFinished())\r
1484       {\r
1485         // wait around until the Jmol check is complete.\r
1486         try\r
1487         {\r
1488           Thread.sleep(2);\r
1489         } catch (Exception e)\r
1490         {\r
1491         }\r
1492         ;\r
1493       }\r
1494       startLoading();\r
1495       // applet.callInitCallback();\r
1496     }\r
1497 \r
1498     private void startLoading()\r
1499     {\r
1500       AlignFrame newAlignFrame;\r
1501       dbgMsg("Loading thread started with:\n>>file\n" + _file + ">>endfile");\r
1502       file = setProtocolState(_file);\r
1503 \r
1504       format = new jalview.io.IdentifyFile().Identify(file, protocol);\r
1505       dbgMsg("File identified as '" + format + "'");\r
1506       dbgMsg("Loading started.");\r
1507       Alignment al = null;\r
1508       try\r
1509       {\r
1510         al = new AppletFormatAdapter().readFile(file, protocol, format);\r
1511       } catch (java.io.IOException ex)\r
1512       {\r
1513         dbgMsg("File load exception.");\r
1514         ex.printStackTrace();\r
1515         if (debug)\r
1516         {\r
1517           try\r
1518           {\r
1519             FileParse fp = new FileParse(file, protocol);\r
1520             String ln = null;\r
1521             dbgMsg(">>>Dumping contents of '" + file + "' " + "("\r
1522                     + protocol + ")");\r
1523             while ((ln = fp.nextLine()) != null)\r
1524             {\r
1525               dbgMsg(ln);\r
1526             }\r
1527             dbgMsg(">>>Dump finished.");\r
1528           } catch (Exception e)\r
1529           {\r
1530             System.err\r
1531                     .println("Exception when trying to dump the content of the file parameter.");\r
1532             e.printStackTrace();\r
1533           }\r
1534         }\r
1535       }\r
1536       if ((al != null) && (al.getHeight() > 0))\r
1537       {\r
1538         dbgMsg("Successfully loaded file.");\r
1539         newAlignFrame = new AlignFrame(al, applet, file, embedded);\r
1540         if (initialAlignFrame == null)\r
1541         {\r
1542           initialAlignFrame = newAlignFrame;\r
1543         }\r
1544         // update the focus.\r
1545         currentAlignFrame = newAlignFrame;\r
1546 \r
1547         if (protocol == jalview.io.AppletFormatAdapter.PASTE)\r
1548         {\r
1549           newAlignFrame.setTitle("Sequences from "\r
1550                   + applet.getDocumentBase());\r
1551         }\r
1552 \r
1553         newAlignFrame.statusBar.setText("Successfully loaded file " + file);\r
1554 \r
1555         String treeFile = applet.getParameter("tree");\r
1556         if (treeFile == null)\r
1557         {\r
1558           treeFile = applet.getParameter("treeFile");\r
1559         }\r
1560 \r
1561         if (treeFile != null)\r
1562         {\r
1563           try\r
1564           {\r
1565             treeFile = setProtocolState(treeFile);\r
1566             /*\r
1567              * if (inArchive(treeFile)) { protocol =\r
1568              * AppletFormatAdapter.CLASSLOADER; } else { protocol =\r
1569              * AppletFormatAdapter.URL; treeFile = addProtocol(treeFile); }\r
1570              */\r
1571             jalview.io.NewickFile fin = new jalview.io.NewickFile(treeFile,\r
1572                     protocol);\r
1573 \r
1574             fin.parse();\r
1575 \r
1576             if (fin.getTree() != null)\r
1577             {\r
1578               newAlignFrame.loadTree(fin, treeFile);\r
1579               dbgMsg("Successfuly imported tree.");\r
1580             }\r
1581             else\r
1582             {\r
1583               dbgMsg("Tree parameter did not resolve to a valid tree.");\r
1584             }\r
1585           } catch (Exception ex)\r
1586           {\r
1587             ex.printStackTrace();\r
1588           }\r
1589         }\r
1590 \r
1591         String param = applet.getParameter("features");\r
1592         if (param != null)\r
1593         {\r
1594           param = setProtocolState(param);\r
1595 \r
1596           newAlignFrame.parseFeaturesFile(param, protocol);\r
1597         }\r
1598 \r
1599         param = applet.getParameter("showFeatureSettings");\r
1600         if (param != null && param.equalsIgnoreCase("true"))\r
1601         {\r
1602           newAlignFrame.viewport.showSequenceFeatures(true);\r
1603           new FeatureSettings(newAlignFrame.alignPanel);\r
1604         }\r
1605 \r
1606         param = applet.getParameter("annotations");\r
1607         if (param != null)\r
1608         {\r
1609           param = setProtocolState(param);\r
1610 \r
1611           if (new AnnotationFile().readAnnotationFile(\r
1612                   newAlignFrame.viewport.getAlignment(), param, protocol))\r
1613           {\r
1614             newAlignFrame.alignPanel.fontChanged();\r
1615             newAlignFrame.alignPanel.setScrollValues(0, 0);\r
1616           }\r
1617           else\r
1618           {\r
1619             System.err\r
1620                     .println("Annotations were not added from annotation file '"\r
1621                             + param + "'");\r
1622           }\r
1623 \r
1624         }\r
1625 \r
1626         param = applet.getParameter("jnetfile");\r
1627         if (param != null)\r
1628         {\r
1629           try\r
1630           {\r
1631             param = setProtocolState(param);\r
1632             jalview.io.JPredFile predictions = new jalview.io.JPredFile(\r
1633                     param, protocol);\r
1634             JnetAnnotationMaker.add_annotation(predictions,\r
1635                     newAlignFrame.viewport.getAlignment(), 0, false); // false==do\r
1636             // not\r
1637             // add\r
1638             // sequence\r
1639             // profile\r
1640             // from\r
1641             // concise\r
1642             // output\r
1643             newAlignFrame.alignPanel.fontChanged();\r
1644             newAlignFrame.alignPanel.setScrollValues(0, 0);\r
1645           } catch (Exception ex)\r
1646           {\r
1647             ex.printStackTrace();\r
1648           }\r
1649         }\r
1650         /*\r
1651          * <param name="alignpdbfiles" value="false/true"/> Undocumented for 2.6\r
1652          * - related to JAL-434\r
1653          */\r
1654         applet.setAlignPdbStructures(getDefaultParameter("alignpdbfiles",\r
1655                 false));\r
1656         /*\r
1657          * <param name="PDBfile" value="1gaq.txt PDB|1GAQ|1GAQ|A PDB|1GAQ|1GAQ|B\r
1658          * PDB|1GAQ|1GAQ|C">\r
1659          * \r
1660          * <param name="PDBfile2" value="1gaq.txt A=SEQA B=SEQB C=SEQB">\r
1661          * \r
1662          * <param name="PDBfile3" value="1q0o Q45135_9MICO">\r
1663          */\r
1664 \r
1665         int pdbFileCount = 0;\r
1666         // Accumulate pdbs here if they are heading for the same view (if\r
1667         // alignPdbStructures is true)\r
1668         Vector pdbs = new Vector();\r
1669         // create a lazy matcher if we're asked to\r
1670         jalview.analysis.SequenceIdMatcher matcher = (applet\r
1671                 .getDefaultParameter("relaxedidmatch", false)) ? new jalview.analysis.SequenceIdMatcher(\r
1672                 newAlignFrame.getAlignViewport().getAlignment()\r
1673                         .getSequencesArray()) : null;\r
1674 \r
1675         do\r
1676         {\r
1677           if (pdbFileCount > 0)\r
1678           {\r
1679             param = applet.getParameter("PDBFILE" + pdbFileCount);\r
1680           }\r
1681           else\r
1682           {\r
1683             param = applet.getParameter("PDBFILE");\r
1684           }\r
1685 \r
1686           if (param != null)\r
1687           {\r
1688             PDBEntry pdb = new PDBEntry();\r
1689 \r
1690             String seqstring;\r
1691             SequenceI[] seqs = null;\r
1692             String[] chains = null;\r
1693 \r
1694             StringTokenizer st = new StringTokenizer(param, " ");\r
1695 \r
1696             if (st.countTokens() < 2)\r
1697             {\r
1698               String sequence = applet.getParameter("PDBSEQ");\r
1699               if (sequence != null)\r
1700                 seqs = new SequenceI[]\r
1701                 { matcher == null ? (Sequence) newAlignFrame\r
1702                         .getAlignViewport().getAlignment()\r
1703                         .findName(sequence) : matcher.findIdMatch(sequence) };\r
1704 \r
1705             }\r
1706             else\r
1707             {\r
1708               param = st.nextToken();\r
1709               Vector tmp = new Vector();\r
1710               Vector tmp2 = new Vector();\r
1711 \r
1712               while (st.hasMoreTokens())\r
1713               {\r
1714                 seqstring = st.nextToken();\r
1715                 StringTokenizer st2 = new StringTokenizer(seqstring, "=");\r
1716                 if (st2.countTokens() > 1)\r
1717                 {\r
1718                   // This is the chain\r
1719                   tmp2.addElement(st2.nextToken());\r
1720                   seqstring = st2.nextToken();\r
1721                 }\r
1722                 tmp.addElement(matcher == null ? (Sequence) newAlignFrame\r
1723                         .getAlignViewport().getAlignment()\r
1724                         .findName(seqstring) : matcher\r
1725                         .findIdMatch(seqstring));\r
1726               }\r
1727 \r
1728               seqs = new SequenceI[tmp.size()];\r
1729               tmp.copyInto(seqs);\r
1730               if (tmp2.size() == tmp.size())\r
1731               {\r
1732                 chains = new String[tmp2.size()];\r
1733                 tmp2.copyInto(chains);\r
1734               }\r
1735             }\r
1736             param = setProtocolState(param);\r
1737 \r
1738             if (// !jmolAvailable\r
1739             // &&\r
1740             protocol == AppletFormatAdapter.CLASSLOADER\r
1741                     && !useXtrnalSviewer)\r
1742             {\r
1743               // Re: JAL-357 : the bug isn't a problem if we are using an\r
1744               // external viewer!\r
1745               // TODO: verify this Re:\r
1746               // https://mantis.lifesci.dundee.ac.uk/view.php?id=36605\r
1747               // This exception preserves the current behaviour where, even if\r
1748               // the local pdb file was identified in the class loader\r
1749               protocol = AppletFormatAdapter.URL; // this is probably NOT\r
1750               // CORRECT!\r
1751               param = addProtocol(param); //\r
1752             }\r
1753 \r
1754             pdb.setFile(param);\r
1755 \r
1756             if (seqs != null)\r
1757             {\r
1758               for (int i = 0; i < seqs.length; i++)\r
1759               {\r
1760                 if (seqs[i] != null)\r
1761                 {\r
1762                   ((Sequence) seqs[i]).addPDBId(pdb);\r
1763                 }\r
1764                 else\r
1765                 {\r
1766                   if (JalviewLite.debug)\r
1767                   {\r
1768                     // this may not really be a problem but we give a warning\r
1769                     // anyway\r
1770                     System.err\r
1771                             .println("Warning: Possible input parsing error: Null sequence for attachment of PDB (sequence "\r
1772                                     + i + ")");\r
1773                   }\r
1774                 }\r
1775               }\r
1776 \r
1777               if (!alignPdbStructures)\r
1778               {\r
1779                 newAlignFrame.newStructureView(applet, pdb, seqs, chains,\r
1780                         protocol);\r
1781               }\r
1782               else\r
1783               {\r
1784                 pdbs.addElement(new Object[]\r
1785                 { pdb, seqs, chains, new String(protocol) });\r
1786               }\r
1787             }\r
1788           }\r
1789 \r
1790           pdbFileCount++;\r
1791         } while (param != null || pdbFileCount < 10);\r
1792         if (pdbs.size() > 0)\r
1793         {\r
1794           SequenceI[][] seqs = new SequenceI[pdbs.size()][];\r
1795           PDBEntry[] pdb = new PDBEntry[pdbs.size()];\r
1796           String[][] chains = new String[pdbs.size()][];\r
1797           String[] protocols = new String[pdbs.size()];\r
1798           for (int pdbsi = 0, pdbsiSize = pdbs.size(); pdbsi < pdbsiSize; pdbsi++)\r
1799           {\r
1800             Object[] o = (Object[]) pdbs.elementAt(pdbsi);\r
1801             pdb[pdbsi] = (PDBEntry) o[0];\r
1802             seqs[pdbsi] = (SequenceI[]) o[1];\r
1803             chains[pdbsi] = (String[]) o[2];\r
1804             protocols[pdbsi] = (String) o[3];\r
1805           }\r
1806           newAlignFrame.alignedStructureView(applet, pdb, seqs, chains,\r
1807                   protocols);\r
1808 \r
1809         }\r
1810         // ///////////////////////////\r
1811         // modify display of features\r
1812         //\r
1813         // hide specific groups\r
1814         param = applet.getParameter("hidefeaturegroups");\r
1815         if (param != null)\r
1816         {\r
1817           applet.setFeatureGroupStateOn(newAlignFrame, param, false);\r
1818         }\r
1819         // show specific groups\r
1820         param = applet.getParameter("showfeaturegroups");\r
1821         if (param != null)\r
1822         {\r
1823           applet.setFeatureGroupStateOn(newAlignFrame, param, true);\r
1824         }\r
1825       }\r
1826       else\r
1827       {\r
1828         fileFound = false;\r
1829         applet.remove(launcher);\r
1830         applet.repaint();\r
1831       }\r
1832       callInitCallback();\r
1833     }\r
1834 \r
1835     /**\r
1836      * Discovers whether the given file is in the Applet Archive\r
1837      * \r
1838      * @param file\r
1839      *          String\r
1840      * @return boolean\r
1841      */\r
1842     boolean inArchive(String file)\r
1843     {\r
1844       // This might throw a security exception in certain browsers\r
1845       // Netscape Communicator for instance.\r
1846       try\r
1847       {\r
1848         boolean rtn = (getClass().getResourceAsStream("/" + file) != null);\r
1849         if (debug)\r
1850         {\r
1851           System.err.println("Resource '" + file + "' was "\r
1852                   + (rtn ? "" : "not") + " located by classloader.");\r
1853         }\r
1854         return rtn;\r
1855       } catch (Exception ex)\r
1856       {\r
1857         System.out.println("Exception checking resources: " + file + " "\r
1858                 + ex);\r
1859         return false;\r
1860       }\r
1861     }\r
1862 \r
1863     String addProtocol(String file)\r
1864     {\r
1865       if (file.indexOf("://") == -1)\r
1866       {\r
1867         String fl = applet.getDocumentBase() + file;\r
1868         try\r
1869         {\r
1870           if (new java.net.URL(fl).openStream() != null)\r
1871           {\r
1872             if (debug)\r
1873             {\r
1874               System.err.println("Prepended document base for resource: '"\r
1875                       + file + "'");\r
1876             }\r
1877             return fl;\r
1878           }\r
1879         } catch (Exception x)\r
1880         {\r
1881         }\r
1882         ;\r
1883         fl = applet.getCodeBase() + file;\r
1884         try\r
1885         {\r
1886           if (new java.net.URL(fl).openStream() != null)\r
1887           {\r
1888             if (debug)\r
1889             {\r
1890               if (debug)\r
1891               {\r
1892                 System.err.println("Prepended codebase for resource: '"\r
1893                         + file + "'");\r
1894               }\r
1895               return fl;\r
1896             }\r
1897           }\r
1898         } catch (Exception x)\r
1899         {\r
1900         }\r
1901         ;\r
1902 \r
1903       }\r
1904 \r
1905       return file;\r
1906     }\r
1907   }\r
1908 \r
1909   /**\r
1910    * @return the default alignFrame acted on by the public applet methods. May\r
1911    *         return null with an error message on System.err indicating the\r
1912    *         fact.\r
1913    */\r
1914   public AlignFrame getDefaultTargetFrame()\r
1915   {\r
1916     if (currentAlignFrame != null)\r
1917     {\r
1918       return currentAlignFrame;\r
1919     }\r
1920     if (initialAlignFrame != null)\r
1921     {\r
1922       return initialAlignFrame;\r
1923     }\r
1924     System.err\r
1925             .println("Implementation error: Jalview Applet API cannot work out which AlignFrame to use.");\r
1926     return null;\r
1927   }\r
1928 \r
1929   /**\r
1930    * separator used for separatorList\r
1931    */\r
1932   protected String separator = "" + ((char) 0x00AC); // the default used to be\r
1933                                                      // '|' but many sequence\r
1934                                                      // IDS include pipes.\r
1935 \r
1936   /**\r
1937    * set to enable the URL based javascript execution mechanism \r
1938    */\r
1939   public boolean jsfallbackEnabled=false;\r
1940 \r
1941   /**\r
1942    * parse the string into a list\r
1943    * \r
1944    * @param list\r
1945    * @return elements separated by separator\r
1946    */\r
1947   public String[] separatorListToArray(String list)\r
1948   {\r
1949     return separatorListToArray(list, separator);\r
1950   }\r
1951 \r
1952   /**\r
1953    * parse the string into a list\r
1954    * \r
1955    * @param list\r
1956    * @param separator\r
1957    * @return elements separated by separator\r
1958    */\r
1959   public String[] separatorListToArray(String list, String separator)\r
1960   {\r
1961     // note separator local variable intentionally masks object field\r
1962     int seplen = separator.length();\r
1963     if (list == null || list.equals("") || list.equals(separator))\r
1964       return null;\r
1965     java.util.Vector jv = new Vector();\r
1966     int cp = 0, pos;\r
1967     while ((pos = list.indexOf(separator, cp)) > cp)\r
1968     {\r
1969       jv.addElement(list.substring(cp, pos));\r
1970       cp = pos + seplen;\r
1971     }\r
1972     if (cp < list.length())\r
1973     {\r
1974       String c = list.substring(cp);\r
1975       if (!c.equals(separator))\r
1976       {\r
1977         jv.addElement(c);\r
1978       }\r
1979     }\r
1980     if (jv.size() > 0)\r
1981     {\r
1982       String[] v = new String[jv.size()];\r
1983       for (int i = 0; i < v.length; i++)\r
1984       {\r
1985         v[i] = (String) jv.elementAt(i);\r
1986       }\r
1987       jv.removeAllElements();\r
1988       if (debug)\r
1989       {\r
1990         System.err.println("Array from '" + separator\r
1991                 + "' separated List:\n" + v.length);\r
1992         for (int i = 0; i < v.length; i++)\r
1993         {\r
1994           System.err.println("item " + i + " '" + v[i] + "'");\r
1995         }\r
1996       }\r
1997       return v;\r
1998     }\r
1999     if (debug)\r
2000     {\r
2001       System.err.println("Empty Array from '" + separator\r
2002               + "' separated List");\r
2003     }\r
2004     return null;\r
2005   }\r
2006 \r
2007   /**\r
2008    * concatenate the list with separator\r
2009    * \r
2010    * @param list\r
2011    * @return concatenated string\r
2012    */\r
2013   public String arrayToSeparatorList(String[] list)\r
2014   {\r
2015     return arrayToSeparatorList(list, separator);\r
2016   }\r
2017 \r
2018   /**\r
2019    * concatenate the list with separator\r
2020    * \r
2021    * @param list\r
2022    * @param separator\r
2023    * @return concatenated string\r
2024    */\r
2025   public String arrayToSeparatorList(String[] list, String separator)\r
2026   {\r
2027     StringBuffer v = new StringBuffer();\r
2028     if (list != null && list.length > 0)\r
2029     {\r
2030       for (int i = 0, iSize = list.length; i < iSize; i++)\r
2031       {\r
2032         if (list[i] != null)\r
2033         {\r
2034           if (i > 0)\r
2035           {\r
2036             v.append(separator);\r
2037           }\r
2038           v.append(list[i]);\r
2039         }\r
2040       }\r
2041       if (debug)\r
2042       {\r
2043         System.err.println("Returning '" + separator\r
2044                 + "' separated List:\n");\r
2045         System.err.println(v);\r
2046       }\r
2047       return v.toString();\r
2048     }\r
2049     if (debug)\r
2050     {\r
2051       System.err.println("Returning empty '" + separator\r
2052               + "' separated List\n");\r
2053     }\r
2054     return "" + separator;\r
2055   }\r
2056 \r
2057   /* (non-Javadoc)\r
2058    * @see jalview.bin.JalviewLiteJsApi#getFeatureGroups()\r
2059    */\r
2060   public String getFeatureGroups()\r
2061   {\r
2062     String lst = arrayToSeparatorList(getDefaultTargetFrame()\r
2063             .getFeatureGroups());\r
2064     return lst;\r
2065   }\r
2066 \r
2067   /* (non-Javadoc)\r
2068    * @see jalview.bin.JalviewLiteJsApi#getFeatureGroupsOn(jalview.appletgui.AlignFrame)\r
2069    */\r
2070   public String getFeatureGroupsOn(AlignFrame alf)\r
2071   {\r
2072     String lst = arrayToSeparatorList(alf.getFeatureGroups());\r
2073     return lst;\r
2074   }\r
2075 \r
2076   /* (non-Javadoc)\r
2077    * @see jalview.bin.JalviewLiteJsApi#getFeatureGroupsOfState(boolean)\r
2078    */\r
2079   public String getFeatureGroupsOfState(boolean visible)\r
2080   {\r
2081     return arrayToSeparatorList(getDefaultTargetFrame()\r
2082             .getFeatureGroupsOfState(visible));\r
2083   }\r
2084 \r
2085   /* (non-Javadoc)\r
2086    * @see jalview.bin.JalviewLiteJsApi#getFeatureGroupsOfStateOn(jalview.appletgui.AlignFrame, boolean)\r
2087    */\r
2088   public String getFeatureGroupsOfStateOn(AlignFrame alf, boolean visible)\r
2089   {\r
2090     return arrayToSeparatorList(alf.getFeatureGroupsOfState(visible));\r
2091   }\r
2092 \r
2093   /* (non-Javadoc)\r
2094    * @see jalview.bin.JalviewLiteJsApi#setFeatureGroupStateOn(jalview.appletgui.AlignFrame, java.lang.String, boolean)\r
2095    */\r
2096   public void setFeatureGroupStateOn(AlignFrame alf, String groups,\r
2097           boolean state)\r
2098   {\r
2099     boolean st = state;// !(state==null || state.equals("") ||\r
2100     // state.toLowerCase().equals("false"));\r
2101     alf.setFeatureGroupState(separatorListToArray(groups), st);\r
2102   }\r
2103 \r
2104   /* (non-Javadoc)\r
2105    * @see jalview.bin.JalviewLiteJsApi#setFeatureGroupState(java.lang.String, boolean)\r
2106    */\r
2107   public void setFeatureGroupState(String groups, boolean state)\r
2108   {\r
2109     setFeatureGroupStateOn(getDefaultTargetFrame(), groups, state);\r
2110   }\r
2111 \r
2112   /* (non-Javadoc)\r
2113    * @see jalview.bin.JalviewLiteJsApi#getSeparator()\r
2114    */\r
2115   public String getSeparator()\r
2116   {\r
2117     return separator;\r
2118   }\r
2119 \r
2120   /* (non-Javadoc)\r
2121    * @see jalview.bin.JalviewLiteJsApi#setSeparator(java.lang.String)\r
2122    */\r
2123   public void setSeparator(String separator)\r
2124   {\r
2125     if (separator == null || separator.length() < 1)\r
2126     {\r
2127       // reset to default\r
2128       separator = "" + ((char) 0x00AC);\r
2129     }\r
2130     this.separator = separator;\r
2131     if (debug)\r
2132     {\r
2133       System.err.println("Default Separator now: '" + separator + "'");\r
2134     }\r
2135   }\r
2136 \r
2137   /**\r
2138    * get boolean value of applet parameter 'name' and return default if\r
2139    * parameter is not set\r
2140    * \r
2141    * @param name\r
2142    *          name of paremeter\r
2143    * @param def\r
2144    *          the value to return otherwise\r
2145    * @return true or false\r
2146    */\r
2147   public boolean getDefaultParameter(String name, boolean def)\r
2148   {\r
2149     String stn;\r
2150     if ((stn = getParameter(name)) == null)\r
2151     {\r
2152       return def;\r
2153     }\r
2154     if (stn.toLowerCase().equals("true"))\r
2155     {\r
2156       return true;\r
2157     }\r
2158     return false;\r
2159   }\r
2160 \r
2161   /* (non-Javadoc)\r
2162    * @see jalview.bin.JalviewLiteJsApi#addPdbFile(jalview.appletgui.AlignFrame, java.lang.String, java.lang.String, java.lang.String)\r
2163    */\r
2164   public boolean addPdbFile(AlignFrame alFrame, String sequenceId,\r
2165           String pdbEntryString, String pdbFile)\r
2166   {\r
2167     return alFrame.addPdbFile(sequenceId, pdbEntryString, pdbFile);\r
2168   }\r
2169 \r
2170   protected void setAlignPdbStructures(boolean alignPdbStructures)\r
2171   {\r
2172     this.alignPdbStructures = alignPdbStructures;\r
2173   }\r
2174 \r
2175   public boolean isAlignPdbStructures()\r
2176   {\r
2177     return alignPdbStructures;\r
2178   }\r
2179 \r
2180   public void start()\r
2181   {\r
2182 //    callInitCallback();\r
2183   }\r
2184   private Hashtable<String,long[]> jshashes=new Hashtable<String,long[]>();\r
2185   private Hashtable<String,Hashtable<String,String[]>> jsmessages=new Hashtable<String,Hashtable<String,String[]>>();\r
2186   public void setJsMessageSet(String messageclass, String viewId,\r
2187           String[] colcommands)\r
2188   {\r
2189     Hashtable<String,String[]> msgset = jsmessages.get(messageclass);\r
2190     if (msgset==null)\r
2191     {\r
2192       msgset=new Hashtable<String,String[]>();\r
2193       jsmessages.put(messageclass, msgset);\r
2194     }\r
2195     msgset.put(viewId, colcommands);\r
2196     long[] l = new long[colcommands.length];\r
2197     for (int i=0;i<colcommands.length;i++) { l[i] = colcommands[i].hashCode();}\r
2198     jshashes.put(messageclass+"|"+viewId,l);\r
2199   }\r
2200   /* (non-Javadoc)\r
2201    * @see jalview.bin.JalviewLiteJsApi#getJsMessage(java.lang.String, java.lang.String)\r
2202    */\r
2203   public String getJsMessage(String messageclass, String viewId)\r
2204   {\r
2205     Hashtable<String,String[]> msgset = jsmessages.get(messageclass);\r
2206     if (msgset!=null)\r
2207     {\r
2208       String[] msgs = msgset.get(viewId);\r
2209       if (msgs!=null)\r
2210       {\r
2211         for (int i=0;i<msgs.length;i++) {\r
2212           if (msgs[i]!=null) {\r
2213             String m = msgs[i];\r
2214             msgs[i]=null;\r
2215             return m;\r
2216           }\r
2217         }\r
2218       }\r
2219     }\r
2220     return "";\r
2221   }\r
2222 \r
2223   public boolean isJsMessageSetChanged(String string, String string2,\r
2224           String[] colcommands)\r
2225   {\r
2226     long[] l=jshashes.get(string+"|"+string2);\r
2227     if (l==null && colcommands!=null)\r
2228     {\r
2229       return true;\r
2230     }\r
2231     for (int i=0;i<colcommands.length;i++) { if (l[i] != colcommands[i].hashCode()) { return true; }}\r
2232     return false;\r
2233   }\r
2234 \r
2235   private Vector jsExecQueue=new Vector();\r
2236   public Vector getJsExecQueue()\r
2237   {\r
2238     return jsExecQueue;\r
2239   }\r
2240 \r
2241   public void setExecutor(JSFunctionExec jsFunctionExec2)\r
2242   {\r
2243     jsFunctionExec=jsFunctionExec2;\r
2244   }\r
2245 \r
2246   /**\r
2247    * bind structures in a viewer to any matching sequences in an alignFrame (use\r
2248    * sequenceIds to limit scope of search to specific sequences)\r
2249    * \r
2250    * @param alFrame\r
2251    * @param viewer\r
2252    * @param sequenceIds\r
2253    * @return TODO: consider making an exception structure for indicating when\r
2254    *         binding fails public SequenceStructureBinding\r
2255    *         addStructureViewInstance( AlignFrame alFrame, Object viewer, String\r
2256    *         sequenceIds) {\r
2257    * \r
2258    *         if (sequenceIds != null && sequenceIds.length() > 0) { return\r
2259    *         alFrame.addStructureViewInstance(viewer,\r
2260    *         separatorListToArray(sequenceIds)); } else { return\r
2261    *         alFrame.addStructureViewInstance(viewer, null); } // return null; }\r
2262    */\r
2263 }\r