Annotation adjustment moved to EditCommand
[jalview.git] / src / jalview / datamodel / AlignmentAnnotation.java
1 /*
2 * Jalview - A Sequence Alignment Editor and Viewer
3 * Copyright (C) 2006 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle
4 *
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
18 */
19 package jalview.datamodel;
20
21
22 /**
23  * DOCUMENT ME!
24  *
25  * @author $author$
26  * @version $Revision$
27  */
28 public class AlignmentAnnotation
29 {
30   /** If true, this annotations is calculated every edit,
31    * eg consensus, quality or conservation graphs */
32   public boolean autoCalculated = false;
33
34   public String annotationId = Math.random() +"";
35
36     public SequenceI sequenceRef;
37
38     /** DOCUMENT ME!! */
39     public String label;
40
41     /** DOCUMENT ME!! */
42     public String description;
43
44     /** DOCUMENT ME!! */
45     public Annotation[] annotations;
46
47     public java.util.Hashtable sequenceMapping;
48
49     /** DOCUMENT ME!! */
50     public float graphMin;
51
52     /** DOCUMENT ME!! */
53     public float graphMax;
54
55     public GraphLine threshold;
56
57     // Graphical hints and tips
58
59     /** DOCUMENT ME!! */
60     public boolean editable = false;
61
62     /** DOCUMENT ME!! */
63     public boolean hasIcons; //
64
65     /** DOCUMENT ME!! */
66     public boolean hasText;
67
68     /** DOCUMENT ME!! */
69     public boolean visible = true;
70
71     public int graphGroup = -1;
72
73     /** DOCUMENT ME!! */
74     public int height = 0;
75
76     public int graph = 0;
77
78     public int graphHeight = 40;
79
80     public static final int NO_GRAPH = 0;
81
82     public static final int BAR_GRAPH = 1;
83
84     public static final int LINE_GRAPH = 2;
85
86     public static int getGraphValueFromString(String string)
87     {
88       if(string.equalsIgnoreCase("BAR_GRAPH"))
89         return BAR_GRAPH;
90       else if(string.equalsIgnoreCase("LINE_GRAPH"))
91         return LINE_GRAPH;
92       else
93         return NO_GRAPH;
94     }
95
96     /**
97      * Creates a new AlignmentAnnotation object.
98      *
99      * @param label DOCUMENT ME!
100      * @param description DOCUMENT ME!
101      * @param annotations DOCUMENT ME!
102      */
103     public AlignmentAnnotation(String label, String description,
104         Annotation[] annotations)
105     {
106         // always editable?
107         editable = true;
108         this.label = label;
109         this.description = description;
110         this.annotations = annotations;
111
112        areLabelsSecondaryStructure();
113     }
114
115     void areLabelsSecondaryStructure()
116     {
117       boolean nonSSLabel = false;
118       for (int i = 0; i < annotations.length; i++)
119       {
120         if(annotations[i]==null)
121           continue;
122
123         if (annotations[i].secondaryStructure == 'H' ||
124             annotations[i].secondaryStructure == 'E')
125         {
126           hasIcons = true;
127         }
128
129         if (annotations[i].displayCharacter.length()==1
130             && !annotations[i].displayCharacter.equals("H")
131             && !annotations[i].displayCharacter.equals("E")
132             && !annotations[i].displayCharacter.equals("-"))
133         {
134           if(jalview.schemes.ResidueProperties.aaIndex
135              [annotations[i].displayCharacter.charAt(0)]>0)
136           {
137             nonSSLabel = true;
138           }
139         }
140
141         if (annotations[i].displayCharacter.length() > 0)
142         {
143           hasText = true;
144         }
145       }
146
147       if(nonSSLabel)
148       {
149         hasIcons = false;
150         for (int j = 0; j < annotations.length; j++)
151         {
152           if(annotations[j] !=null && annotations[j].secondaryStructure!=' ')
153           {
154             annotations[j].displayCharacter
155                 =String.valueOf(annotations[j].secondaryStructure);
156             annotations[j].secondaryStructure = ' ';
157           }
158
159         }
160
161       }
162
163     }
164
165     /**
166      * Creates a new AlignmentAnnotation object.
167      *
168      * @param label DOCUMENT ME!
169      * @param description DOCUMENT ME!
170      * @param annotations DOCUMENT ME!
171      * @param min DOCUMENT ME!
172      * @param max DOCUMENT ME!
173      * @param winLength DOCUMENT ME!
174      */
175     public AlignmentAnnotation(String label, String description,
176         Annotation[] annotations, float min, float max, int graphType)
177     {
178         // graphs are not editable
179         this.label = label;
180         this.description = description;
181         this.annotations = annotations;
182         graph = graphType;
183
184         boolean drawValues = true;
185
186         if (min == max)
187         {
188             min = 999999999;
189             for (int i = 0; i < annotations.length; i++)
190             {
191                 if (annotations[i] == null)
192                 {
193                     continue;
194                 }
195
196                 if(drawValues && annotations[i].displayCharacter.length() > 1 )
197                 {
198                   drawValues = false;
199                 }
200
201                 if (annotations[i].value > max)
202                 {
203                     max = annotations[i].value;
204                 }
205
206                 if (annotations[i].value < min)
207                 {
208                     min = annotations[i].value;
209                 }
210             }
211         }
212
213         graphMin = min;
214         graphMax = max;
215
216         areLabelsSecondaryStructure();
217
218         if(!drawValues && graphType!=NO_GRAPH)
219         {
220           for (int i = 0; i < annotations.length; i++)
221           {
222             if (annotations[i] != null)
223               annotations[i].displayCharacter = "";
224           }
225         }
226     }
227
228     /**
229      * DOCUMENT ME!
230      *
231      * @return DOCUMENT ME!
232      */
233     public String toString()
234     {
235         StringBuffer buffer = new StringBuffer();
236
237         for (int i = 0; i < annotations.length; i++)
238         {
239             if (annotations[i] != null)
240             {
241                 if (graph!=0)
242                 {
243                     buffer.append(annotations[i].value);
244                 }
245                 else if (hasIcons)
246                 {
247                     buffer.append(annotations[i].secondaryStructure);
248                 }
249                 else
250                 {
251                     buffer.append(annotations[i].displayCharacter);
252                 }
253             }
254
255             buffer.append(", ");
256         }
257
258         if (label.equals("Consensus"))
259         {
260             buffer.append("\n");
261
262             for (int i = 0; i < annotations.length; i++)
263             {
264                 if (annotations[i] != null)
265                 {
266                     buffer.append(annotations[i].description);
267                 }
268
269                 buffer.append(", ");
270             }
271         }
272
273         return buffer.toString();
274       }
275
276       public void setThreshold(GraphLine line)
277       {
278         threshold = line;
279       }
280
281       public GraphLine getThreshold()
282       {
283           return threshold;
284       }
285
286       /**
287        * Attach the annotation to seqRef, starting from startRes position. If alreadyMapped is true then the indices of the annotation[] array are sequence positions rather than alignment column positions.
288        * @param seqRef
289        * @param startRes
290        * @param alreadyMapped
291        */
292       public void createSequenceMapping(SequenceI seqRef,
293                                         int startRes,
294                                         boolean alreadyMapped)
295       {
296         if(seqRef == null)
297           return;
298
299         sequenceMapping = new java.util.Hashtable();
300
301         sequenceRef = seqRef;
302         int seqPos;
303
304         for(int i = 0; i < annotations.length; i++)
305         {
306             if (annotations[i] != null)
307             {
308               if(alreadyMapped)
309                 seqPos = seqRef.findPosition(i);
310               else
311                 seqPos = i+startRes;
312
313               sequenceMapping.put(new Integer(seqPos), annotations[i]);
314             }
315          }
316
317         adjustForAlignment();
318       }
319
320       public void adjustForAlignment()
321       {
322           int a=0, aSize = sequenceRef.getLength();
323
324           if(aSize == 0)
325           {
326             //Its been deleted
327             return;
328           }
329
330           int position;
331           Annotation[] temp = new Annotation[aSize];
332           Integer index;
333
334           for (a = sequenceRef.getStart(); a <= sequenceRef.getEnd(); a++)
335           {
336               index = new Integer(a);
337               if(sequenceMapping.containsKey(index))
338               {
339                 position = sequenceRef.findIndex(a)-1;
340
341                 temp[position] = (Annotation)sequenceMapping.get(index);
342               }
343           }
344
345           annotations = temp;
346       }
347 }
348
349