comment concerning null exceptions generated when annotations read from a file are...
[jalview.git] / src / jalview / io / AnnotationFile.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 \r
20 package jalview.io;\r
21 \r
22 import java.io.*;\r
23 import java.net.*;\r
24 import java.util.*;\r
25 \r
26 import jalview.analysis.*;\r
27 import jalview.datamodel.*;\r
28 import jalview.schemes.*;\r
29 \r
30 public class AnnotationFile\r
31 {\r
32   StringBuffer text = new StringBuffer(\r
33       "JALVIEW_ANNOTATION\n"\r
34       + "# Created: "\r
35       + new java.util.Date() + "\n\n");\r
36 \r
37   public String printAnnotations(AlignmentAnnotation[] annotations,\r
38                                  Vector groups,\r
39                                  Hashtable properties)\r
40   {\r
41     if (annotations != null)\r
42     {\r
43       boolean oneColour = true;\r
44       AlignmentAnnotation row;\r
45       String comma;\r
46       SequenceI refSeq = null;\r
47 \r
48       StringBuffer colours = new StringBuffer();\r
49       StringBuffer graphLine = new StringBuffer();\r
50 \r
51       Hashtable graphGroup = new Hashtable();\r
52 \r
53       java.awt.Color color;\r
54 \r
55       for (int i = 0; i < annotations.length; i++)\r
56       {\r
57         row = annotations[i];\r
58 \r
59         if (!row.visible && !row.hasScore())\r
60         {\r
61           continue;\r
62         }\r
63 \r
64         color = null;\r
65         oneColour = true;\r
66 \r
67         if (row.sequenceRef == null)\r
68         {\r
69           if (refSeq != null)\r
70           {\r
71             text.append("\nSEQUENCE_REF\tALIGNMENT\n");\r
72           }\r
73 \r
74           refSeq = null;\r
75         }\r
76 \r
77         else if (refSeq == null || refSeq != row.sequenceRef)\r
78         {\r
79           refSeq = row.sequenceRef;\r
80           text.append("\nSEQUENCE_REF\t" + refSeq.getName() + "\n");\r
81         }\r
82 \r
83         if (row.graph == AlignmentAnnotation.NO_GRAPH)\r
84         {\r
85           text.append("NO_GRAPH\t");\r
86         }\r
87         else\r
88         {\r
89           if (row.graph == AlignmentAnnotation.BAR_GRAPH)\r
90           {\r
91             text.append("BAR_GRAPH\t");\r
92           }\r
93           else if (row.graph == AlignmentAnnotation.LINE_GRAPH)\r
94           {\r
95             text.append("LINE_GRAPH\t");\r
96           }\r
97 \r
98           if (row.getThreshold() != null)\r
99           {\r
100             graphLine.append("GRAPHLINE\t"\r
101                              + row.label + "\t"\r
102                              + row.getThreshold().value + "\t"\r
103                              + row.getThreshold().label + "\t"\r
104                              + jalview.util.Format.getHexString(\r
105                                  row.getThreshold().colour) + "\n"\r
106                 );\r
107           }\r
108 \r
109           if (row.graphGroup > -1)\r
110           {\r
111             String key = String.valueOf(row.graphGroup);\r
112             if (graphGroup.containsKey(key))\r
113             {\r
114               graphGroup.put(key, graphGroup.get(key)\r
115                              + "\t" + row.label);\r
116             }\r
117             else\r
118             {\r
119               graphGroup.put(key, row.label);\r
120             }\r
121           }\r
122         }\r
123 \r
124         text.append(row.label + "\t");\r
125         if (row.description != null)\r
126         {\r
127           text.append(row.description + "\t");\r
128         }\r
129 \r
130         for (int j = 0; row.annotations!=null && j < row.annotations.length; j++)\r
131         {\r
132           if (refSeq != null &&\r
133               jalview.util.Comparison.isGap(refSeq.getCharAt(j)))\r
134           {\r
135             continue;\r
136           }\r
137 \r
138           if (row.annotations[j] != null)\r
139           {\r
140             comma = "";\r
141             if (row.annotations[j].secondaryStructure != ' ')\r
142             {\r
143               text.append(comma + row.annotations[j].secondaryStructure);\r
144               comma = ",";\r
145             }\r
146             if (row.annotations[j].displayCharacter!=null\r
147                 && row.annotations[j].displayCharacter.length() > 0\r
148                 && !row.annotations[j].displayCharacter.equals(" "))\r
149             {\r
150               text.append(comma + row.annotations[j].displayCharacter);\r
151               comma = ",";\r
152             }\r
153 \r
154             if (row.annotations[j] != null)\r
155             {\r
156               if(color!=null && !color.equals(row.annotations[j].colour))\r
157               {\r
158                 oneColour = false;\r
159               }\r
160 \r
161               color = row.annotations[j].colour;\r
162               if (row.annotations[j].value != 0f)\r
163               {\r
164                 text.append(comma + row.annotations[j].value);\r
165               }\r
166             }\r
167 \r
168             if(row.annotations[j].colour!=null\r
169                && row.annotations[j].colour!=java.awt.Color.black)\r
170             {\r
171               text.append(comma+"["+\r
172                           jalview.util.Format.getHexString(\r
173                           row.annotations[j].colour)+"]");\r
174             }\r
175           }\r
176           text.append("|");\r
177         }\r
178 \r
179         if(row.hasScore())\r
180           text.append("\t"+row.score);\r
181 \r
182         text.append("\n");\r
183 \r
184         if (color != null && color != java.awt.Color.black && oneColour)\r
185         {\r
186           colours.append("COLOUR\t"\r
187                          + row.label + "\t"\r
188                          + jalview.util.Format.getHexString(color) + "\n");\r
189         }\r
190 \r
191       }\r
192 \r
193       text.append("\n");\r
194 \r
195       text.append(colours.toString());\r
196       text.append(graphLine.toString());\r
197       if (graphGroup.size() > 0)\r
198       {\r
199         text.append("COMBINE\t");\r
200         Enumeration en = graphGroup.elements();\r
201         while (en.hasMoreElements())\r
202         {\r
203           text.append(en.nextElement() + "\n");\r
204         }\r
205       }\r
206     }\r
207 \r
208     if (groups != null)\r
209     {\r
210       printGroups(groups);\r
211     }\r
212 \r
213     if(properties!=null)\r
214     {\r
215       text.append("\n\nALIGNMENT");\r
216       Enumeration en = properties.keys();\r
217       while(en.hasMoreElements())\r
218       {\r
219         String key = en.nextElement().toString();\r
220         text.append("\t"+key+"="+properties.get(key));\r
221       }\r
222 \r
223     }\r
224 \r
225     return text.toString();\r
226   }\r
227 \r
228   public void printGroups(Vector sequenceGroups)\r
229   {\r
230     SequenceGroup sg;\r
231     for (int i = 0; i < sequenceGroups.size(); i++)\r
232     {\r
233       sg = (SequenceGroup) sequenceGroups.elementAt(i);\r
234       text.append("SEQUENCE_GROUP\t"\r
235                   + sg.getName() + "\t"\r
236                   + (sg.getStartRes() + 1) + "\t"\r
237                   + (sg.getEndRes() + 1) + "\t" + "-1\t");\r
238       for (int s = 0; s < sg.getSize(); s++)\r
239       {\r
240         text.append(sg.getSequenceAt(s).getName() + "\t");\r
241       }\r
242 \r
243       text.append("\nPROPERTIES\t" + sg.getName() + "\t");\r
244 \r
245       if (sg.getDescription() != null)\r
246       {\r
247         text.append("description=" + sg.getDescription() + "\t");\r
248       }\r
249       if (sg.cs != null)\r
250       {\r
251         text.append("colour=" + ColourSchemeProperty.getColourName(sg.cs) +\r
252                     "\t");\r
253         if (sg.cs.getThreshold() != 0)\r
254         {\r
255           text.append("pidThreshold=" + sg.cs.getThreshold());\r
256         }\r
257         if (sg.cs.conservationApplied())\r
258         {\r
259           text.append("consThreshold=" + sg.cs.getConservationInc() + "\t");\r
260         }\r
261       }\r
262       text.append("outlineColour=" +\r
263                   jalview.util.Format.getHexString(sg.getOutlineColour()) +\r
264                   "\t");\r
265 \r
266       text.append("displayBoxes=" + sg.getDisplayBoxes() + "\t");\r
267       text.append("displayText=" + sg.getDisplayText() + "\t");\r
268       text.append("colourText=" + sg.getColourText() + "\t");\r
269 \r
270       if (sg.textColour != java.awt.Color.black)\r
271       {\r
272         text.append("textCol1=" +\r
273                     jalview.util.Format.getHexString(sg.textColour) + "\t");\r
274       }\r
275       if (sg.textColour2 != java.awt.Color.white)\r
276       {\r
277         text.append("textCol2=" +\r
278                     jalview.util.Format.getHexString(sg.textColour2) + "\t");\r
279       }\r
280       if (sg.thresholdTextColour != 0)\r
281       {\r
282         text.append("textColThreshold=" + sg.thresholdTextColour);\r
283       }\r
284 \r
285       text.append("\n\n");\r
286 \r
287     }\r
288   }\r
289 \r
290   SequenceI refSeq = null;\r
291   public boolean readAnnotationFile(AlignmentI al,\r
292                                     String file,\r
293                                     String protocol)\r
294   {\r
295     try\r
296     {\r
297       BufferedReader in = null;\r
298       if (protocol.equals(AppletFormatAdapter.FILE))\r
299       {\r
300         in = new BufferedReader(new FileReader(file));\r
301       }\r
302       else if (protocol.equals(AppletFormatAdapter.URL))\r
303       {\r
304         URL url = new URL(file);\r
305         in = new BufferedReader(new InputStreamReader(url.openStream()));\r
306       }\r
307       else if (protocol.equals(AppletFormatAdapter.PASTE))\r
308       {\r
309         in = new BufferedReader(new StringReader(file));\r
310       }\r
311       else if (protocol.equals(AppletFormatAdapter.CLASSLOADER))\r
312       {\r
313         java.io.InputStream is = getClass().getResourceAsStream("/" + file);\r
314         if (is != null)\r
315         {\r
316           in = new BufferedReader(new java.io.InputStreamReader(is));\r
317         }\r
318       }\r
319 \r
320       String line, label, description, token;\r
321       int graphStyle, index;\r
322       int refSeqIndex = 1;\r
323       int existingAnnotations = 0;\r
324       if (al.getAlignmentAnnotation() != null)\r
325       {\r
326         existingAnnotations = al.getAlignmentAnnotation().length;\r
327       }\r
328 \r
329       int alWidth = al.getWidth();\r
330 \r
331       StringTokenizer st;\r
332       Annotation[] annotations;\r
333       AlignmentAnnotation annotation = null;\r
334 \r
335       // First confirm this is an Annotation file\r
336       boolean jvAnnotationFile = false;\r
337       while ( (line = in.readLine()) != null)\r
338       {\r
339         if (line.indexOf("#") == 0)\r
340         {\r
341           continue;\r
342         }\r
343 \r
344         if (line.indexOf("JALVIEW_ANNOTATION") > -1)\r
345         {\r
346           jvAnnotationFile = true;\r
347           break;\r
348         }\r
349       }\r
350 \r
351       if (!jvAnnotationFile)\r
352       {\r
353         in.close();\r
354         return false;\r
355       }\r
356 \r
357       while ( (line = in.readLine()) != null)\r
358       {\r
359         if (line.indexOf("#") == 0\r
360             || line.indexOf("JALVIEW_ANNOTATION") > -1\r
361             || line.length() == 0)\r
362         {\r
363           continue;\r
364         }\r
365 \r
366         st = new StringTokenizer(line, "\t");\r
367         token = st.nextToken();\r
368         if (token.equalsIgnoreCase("COLOUR"))\r
369         {\r
370           colourAnnotations(al, st.nextToken(), st.nextToken());\r
371           continue;\r
372         }\r
373 \r
374         else if (token.equalsIgnoreCase("COMBINE"))\r
375         {\r
376           combineAnnotations(al, st);\r
377           continue;\r
378         }\r
379 \r
380         else if (token.equalsIgnoreCase("GRAPHLINE"))\r
381         {\r
382           addLine(al, st);\r
383           continue;\r
384         }\r
385 \r
386         else if (token.equalsIgnoreCase("SEQUENCE_REF"))\r
387         {\r
388           refSeq = al.findName(st.nextToken());\r
389           try\r
390           {\r
391             refSeqIndex = Integer.parseInt(st.nextToken());\r
392             if (refSeqIndex < 1)\r
393             {\r
394               refSeqIndex = 1;\r
395               System.out.println(\r
396                   "WARNING: SEQUENCE_REF index must be > 0 in AnnotationFile");\r
397             }\r
398           }\r
399           catch (Exception ex)\r
400           {\r
401             refSeqIndex = 1;\r
402           }\r
403 \r
404           continue ;\r
405         }\r
406 \r
407         else if (token.equalsIgnoreCase("SEQUENCE_GROUP"))\r
408         {\r
409           addGroup(al, st);\r
410           continue;\r
411         }\r
412 \r
413         else if (token.equalsIgnoreCase("PROPERTIES"))\r
414         {\r
415           addProperties(al, st);\r
416           continue;\r
417         }\r
418 \r
419         else if( token.equalsIgnoreCase("BELOW_ALIGNMENT"))\r
420         {\r
421           setBelowAlignment(al, st);\r
422           continue;\r
423         }\r
424         else if( token.equalsIgnoreCase("ALIGNMENT"))\r
425         {\r
426           addAlignmentDetails(al, st);\r
427           continue;\r
428         }\r
429 \r
430         graphStyle = AlignmentAnnotation.getGraphValueFromString(token);\r
431         label = st.nextToken();\r
432 \r
433 \r
434         index = 0;\r
435         annotations = new Annotation[alWidth];\r
436         description = null;\r
437         float score = Float.NaN;\r
438 \r
439         if(st.hasMoreTokens())\r
440         {\r
441           line = st.nextToken();\r
442 \r
443           if (line.indexOf("|") ==-1)\r
444           {\r
445             description = line;\r
446             if (st.hasMoreTokens())\r
447               line = st.nextToken();\r
448           }\r
449 \r
450           if(st.hasMoreTokens())\r
451           {\r
452             //This must be the score\r
453             score = Float.valueOf(st.nextToken()).floatValue();\r
454           }\r
455 \r
456           st = new StringTokenizer(line, "|", true);\r
457 \r
458 \r
459           boolean emptyColumn = true;\r
460           boolean onlyOneElement = (st.countTokens()==1);\r
461 \r
462           while (st.hasMoreElements() && index < alWidth)\r
463           {\r
464             token = st.nextToken().trim();\r
465 \r
466             if(onlyOneElement)\r
467             {\r
468               try\r
469               {\r
470                 score = Float.valueOf(token).floatValue();\r
471                 break;\r
472               }\r
473               catch(NumberFormatException ex){}\r
474             }\r
475 \r
476             if (token.equals("|"))\r
477             {\r
478               if (emptyColumn)\r
479               {\r
480                 index++;\r
481               }\r
482 \r
483               emptyColumn = true;\r
484             }\r
485             else\r
486             {\r
487               annotations[index++] = parseAnnotation(token);\r
488               emptyColumn = false;\r
489             }\r
490           }\r
491 \r
492         }\r
493 \r
494         annotation = new AlignmentAnnotation(label,\r
495                                              description,\r
496                                              (index==0) ? null : annotations,\r
497                                              0,\r
498                                              0,\r
499                                              graphStyle);\r
500 \r
501         annotation.score = score;\r
502 \r
503         if (refSeq != null)\r
504         {\r
505           annotation.belowAlignment=false;\r
506           annotation.createSequenceMapping(refSeq, refSeqIndex, false);\r
507           annotation.adjustForAlignment();\r
508           refSeq.addAlignmentAnnotation(annotation);\r
509         }\r
510 \r
511         al.addAnnotation(annotation);\r
512 \r
513         al.setAnnotationIndex(annotation,\r
514                               al.getAlignmentAnnotation().length - existingAnnotations -\r
515                               1);\r
516       }\r
517 \r
518     }\r
519     catch (Exception ex)\r
520     {\r
521       ex.printStackTrace();\r
522       System.out.println("Problem reading annotation file: " + ex);\r
523       return false;\r
524     }\r
525     return true;\r
526   }\r
527 \r
528   Annotation parseAnnotation(String string)\r
529   {\r
530     String desc = null, displayChar = null;\r
531     char ss = ' '; // secondaryStructure\r
532     float value = 0;\r
533     boolean parsedValue = false;\r
534 \r
535     //find colour here\r
536     java.awt.Color colour = null;\r
537     int i=string.indexOf("[");\r
538     int j=string.indexOf("]");\r
539     if(i>-1 && j>-1)\r
540     {\r
541       UserColourScheme ucs = new UserColourScheme();\r
542 \r
543       colour = ucs.getColourFromString(string.substring(i+1,j));\r
544 \r
545       string = string.substring(0,i)+string.substring(j+1);\r
546     }\r
547 \r
548     StringTokenizer st = new StringTokenizer(string, ",");\r
549     String token;\r
550     while (st.hasMoreTokens())\r
551     {\r
552       token = st.nextToken().trim();\r
553       if (token.length() == 0)\r
554       {\r
555         continue;\r
556       }\r
557 \r
558       if (!parsedValue)\r
559       {\r
560         try\r
561         {\r
562           displayChar = token;\r
563           value = new Float(token).floatValue();\r
564           parsedValue = true;\r
565           continue;\r
566         }\r
567         catch (NumberFormatException ex)\r
568         {}\r
569       }\r
570 \r
571       if (token.equals("H") || token.equals("E"))\r
572       {\r
573         // Either this character represents a helix or sheet\r
574         // or an integer which can be displayed\r
575         ss = token.charAt(0);\r
576         if (displayChar.equals(token.substring(0, 1)))\r
577         {\r
578           displayChar = "";\r
579         }\r
580       }\r
581       else if (desc == null)\r
582       {\r
583         desc = token;\r
584       }\r
585 \r
586     }\r
587 \r
588     if (displayChar!=null\r
589         && displayChar.length() > 1\r
590         &&  desc!=null\r
591         && desc.length() == 1)\r
592     {\r
593       String tmp = displayChar;\r
594       displayChar = desc;\r
595       desc = tmp;\r
596     }\r
597     /*\r
598      * In principle, this code will ensure that the Annotation element generated is renderable by any of the applet or application rendering code\r
599      * but instead we check for null strings when the display character is rendered. \r
600     if (displayChar==null)\r
601     {\r
602       displayChar="";\r
603     }\r
604     */\r
605     Annotation anot = new Annotation(displayChar, desc, ss, value);\r
606 \r
607     anot.colour = colour;\r
608 \r
609     return anot;\r
610   }\r
611 \r
612   void colourAnnotations(AlignmentI al, String label, String colour)\r
613   {\r
614     UserColourScheme ucs = new UserColourScheme(colour);\r
615     Annotation[] annotations;\r
616     for (int i = 0; i < al.getAlignmentAnnotation().length; i++)\r
617     {\r
618       if (al.getAlignmentAnnotation()[i].label.equalsIgnoreCase(label))\r
619       {\r
620         annotations = al.getAlignmentAnnotation()[i].annotations;\r
621         for (int j = 0; j < annotations.length; j++)\r
622         {\r
623           if (annotations[j] != null)\r
624           {\r
625             annotations[j].colour = ucs.findColour('A');\r
626           }\r
627         }\r
628       }\r
629     }\r
630   }\r
631 \r
632   void combineAnnotations(AlignmentI al, StringTokenizer st)\r
633   {\r
634     int graphGroup = -1;\r
635     String group = st.nextToken();\r
636     //First make sure we are not overwriting the graphIndex\r
637     for (int i = 0; i < al.getAlignmentAnnotation().length; i++)\r
638     {\r
639       if (al.getAlignmentAnnotation()[i].label.equalsIgnoreCase(group))\r
640       {\r
641         graphGroup = al.getAlignmentAnnotation()[i].graphGroup + 1;\r
642         al.getAlignmentAnnotation()[i].graphGroup = graphGroup;\r
643         break;\r
644       }\r
645     }\r
646 \r
647     //Now update groups\r
648     while (st.hasMoreTokens())\r
649     {\r
650       group = st.nextToken();\r
651       for (int i = 0; i < al.getAlignmentAnnotation().length; i++)\r
652       {\r
653         if (al.getAlignmentAnnotation()[i].label.equalsIgnoreCase(group))\r
654         {\r
655           al.getAlignmentAnnotation()[i].graphGroup = graphGroup;\r
656           break;\r
657         }\r
658       }\r
659     }\r
660   }\r
661 \r
662   void addLine(AlignmentI al, StringTokenizer st)\r
663   {\r
664     String group = st.nextToken();\r
665     AlignmentAnnotation annotation = null;\r
666 \r
667     for (int i = 0; i < al.getAlignmentAnnotation().length; i++)\r
668     {\r
669       if (al.getAlignmentAnnotation()[i].label.equalsIgnoreCase(group))\r
670       {\r
671         annotation = al.getAlignmentAnnotation()[i];\r
672         break;\r
673       }\r
674     }\r
675 \r
676     if (annotation == null)\r
677     {\r
678       return;\r
679     }\r
680     float value = new Float(st.nextToken()).floatValue();\r
681     String label = st.hasMoreTokens() ? st.nextToken() : null;\r
682     java.awt.Color colour = null;\r
683     if (st.hasMoreTokens())\r
684     {\r
685       UserColourScheme ucs = new UserColourScheme(st.nextToken());\r
686       colour = ucs.findColour('A');\r
687     }\r
688 \r
689     annotation.setThreshold(new GraphLine(value, label, colour));\r
690   }\r
691 \r
692   void addGroup(AlignmentI al, StringTokenizer st)\r
693   {\r
694     SequenceGroup sg = new SequenceGroup();\r
695     sg.setName(st.nextToken());\r
696     sg.setStartRes(Integer.parseInt(st.nextToken()) - 1);\r
697     sg.setEndRes(Integer.parseInt(st.nextToken()) - 1);\r
698 \r
699     String index = st.nextToken();\r
700     if (index.equals("-1"))\r
701     {\r
702       while (st.hasMoreElements())\r
703       {\r
704         sg.addSequence(al.findName(st.nextToken()), false);\r
705       }\r
706     }\r
707     else\r
708     {\r
709       StringTokenizer st2 = new StringTokenizer(index, ",");\r
710 \r
711       while (st2.hasMoreTokens())\r
712       {\r
713         String tmp = st2.nextToken();\r
714         if (tmp.equals("*"))\r
715         {\r
716           for (int i = 0; i < al.getHeight(); i++)\r
717           {\r
718             sg.addSequence(al.getSequenceAt(i), false);\r
719           }\r
720         }\r
721         else if (tmp.indexOf("-") >= 0)\r
722         {\r
723           StringTokenizer st3 = new StringTokenizer(tmp, "-");\r
724 \r
725           int start = (Integer.parseInt(st3.nextToken()));\r
726           int end = (Integer.parseInt(st3.nextToken()));\r
727 \r
728           if (end > start)\r
729           {\r
730             for (int i = start; i <= end; i++)\r
731             {\r
732               sg.addSequence(al.getSequenceAt(i - 1), false);\r
733             }\r
734           }\r
735         }\r
736         else\r
737         {\r
738           sg.addSequence(al.getSequenceAt(Integer.parseInt(tmp) - 1), false);\r
739         }\r
740       }\r
741     }\r
742 \r
743 \r
744 \r
745     if (refSeq != null)\r
746     {\r
747       sg.setStartRes(refSeq.findIndex(sg.getStartRes() + 1) - 1);\r
748       sg.setEndRes(refSeq.findIndex(sg.getEndRes() + 1) - 1);\r
749     }\r
750 \r
751     if (sg.getSize() > 0)\r
752     {\r
753       al.addGroup(sg);\r
754     }\r
755   }\r
756 \r
757   void addProperties(AlignmentI al, StringTokenizer st)\r
758   {\r
759 \r
760     //So far we have only added groups to the annotationHash,\r
761     //the idea is in the future properties can be added to\r
762     //alignments, other annotations etc\r
763     if (al.getGroups() == null)\r
764     {\r
765       return;\r
766     }\r
767     SequenceGroup sg = null;\r
768 \r
769     String name = st.nextToken();\r
770 \r
771     Vector groups = al.getGroups();\r
772     for (int i = 0; i < groups.size(); i++)\r
773     {\r
774       sg = (SequenceGroup) groups.elementAt(i);\r
775       if (sg.getName().equals(name))\r
776       {\r
777         break;\r
778       }\r
779       else\r
780       {\r
781         sg = null;\r
782       }\r
783     }\r
784 \r
785     if (sg != null)\r
786     {\r
787       String keyValue, key, value;\r
788       while (st.hasMoreTokens())\r
789       {\r
790         keyValue = st.nextToken();\r
791         key = keyValue.substring(0, keyValue.indexOf("="));\r
792         value = keyValue.substring(keyValue.indexOf("=") + 1);\r
793 \r
794         if (key.equalsIgnoreCase("description"))\r
795         {\r
796           sg.setDescription(value);\r
797         }\r
798         else if (key.equalsIgnoreCase("colour"))\r
799         {\r
800           sg.cs = ColourSchemeProperty.getColour(al, value);\r
801         }\r
802         else if (key.equalsIgnoreCase("pidThreshold"))\r
803         {\r
804           sg.cs.setThreshold(Integer.parseInt(value), true);\r
805 \r
806         }\r
807         else if (key.equalsIgnoreCase("consThreshold"))\r
808         {\r
809           sg.cs.setConservationInc(Integer.parseInt(value));\r
810           Conservation c = new Conservation("Group",\r
811                                             ResidueProperties.propHash, 3,\r
812                                             sg.getSequences(null),\r
813                                             sg.getStartRes(),\r
814                                             sg.getEndRes() + 1);\r
815 \r
816           c.calculate();\r
817           c.verdict(false, 25);\r
818 \r
819           sg.cs.setConservation(c);\r
820 \r
821         }\r
822         else if (key.equalsIgnoreCase("outlineColour"))\r
823         {\r
824           sg.setOutlineColour(new UserColourScheme(value).findColour('A'));\r
825         }\r
826         else if (key.equalsIgnoreCase("displayBoxes"))\r
827         {\r
828           sg.setDisplayBoxes(Boolean.valueOf(value).booleanValue());\r
829         }\r
830         else if (key.equalsIgnoreCase("displayText"))\r
831         {\r
832           sg.setDisplayText(Boolean.valueOf(value).booleanValue());\r
833         }\r
834         else if (key.equalsIgnoreCase("colourText"))\r
835         {\r
836           sg.setColourText(Boolean.valueOf(value).booleanValue());\r
837         }\r
838         else if (key.equalsIgnoreCase("textCol1"))\r
839         {\r
840           sg.textColour = new UserColourScheme(value).findColour('A');\r
841         }\r
842         else if (key.equalsIgnoreCase("textCol2"))\r
843         {\r
844           sg.textColour2 = new UserColourScheme(value).findColour('A');\r
845         }\r
846         else if (key.equalsIgnoreCase("textColThreshold"))\r
847         {\r
848           sg.thresholdTextColour = Integer.parseInt(value);\r
849         }\r
850 \r
851         sg.recalcConservation();\r
852       }\r
853     }\r
854   }\r
855 \r
856   void setBelowAlignment(AlignmentI al, StringTokenizer st)\r
857   {\r
858     String token;\r
859     AlignmentAnnotation aa;\r
860     while(st.hasMoreTokens())\r
861     {\r
862       token = st.nextToken();\r
863       for(int i=0; i<al.getAlignmentAnnotation().length; i++)\r
864       {\r
865         aa = al.getAlignmentAnnotation()[i];\r
866         if(aa.sequenceRef==refSeq && aa.label.equals(token))\r
867         {\r
868           aa.belowAlignment = true;\r
869         }\r
870       }\r
871     }\r
872   }\r
873 \r
874   void addAlignmentDetails(AlignmentI al, StringTokenizer st)\r
875   {\r
876     String keyValue, key, value;\r
877     while (st.hasMoreTokens())\r
878     {\r
879       keyValue = st.nextToken();\r
880       key = keyValue.substring(0, keyValue.indexOf("="));\r
881       value = keyValue.substring(keyValue.indexOf("=") + 1);\r
882       al.setProperty(key,value);\r
883     }\r
884   }\r
885 }\r