JAL-1620 version bump and release notes
[jalview.git] / src / jalview / gui / PaintRefresher.java
1 /*
2  * Jalview - A Sequence Alignment Editor and Viewer (Version 2.8.2b1)
3  * Copyright (C) 2014 The Jalview Authors
4  * 
5  * This file is part of Jalview.
6  * 
7  * Jalview is free software: you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License 
9  * as published by the Free Software Foundation, either version 3
10  * of the License, or (at your option) any later version.
11  *  
12  * Jalview is distributed in the hope that it will be useful, but 
13  * WITHOUT ANY WARRANTY; without even the implied warranty 
14  * of MERCHANTABILITY or FITNESS FOR A PARTICULAR 
15  * PURPOSE.  See the GNU General Public License for more details.
16  * 
17  * You should have received a copy of the GNU General Public License
18  * along with Jalview.  If not, see <http://www.gnu.org/licenses/>.
19  * The Jalview Authors are detailed in the 'AUTHORS' file.
20  */
21 package jalview.gui;
22
23 import java.util.*;
24 import java.util.List;
25
26 import java.awt.*;
27
28 import jalview.datamodel.*;
29
30 /**
31  * Route datamodel/view update events for a sequence set to any display
32  * components involved TODO: JV3 refactor to abstract gui/view package
33  * 
34  * @author $author$
35  * @version $Revision$
36  */
37 public class PaintRefresher
38 {
39   static Hashtable components;
40
41   /**
42    * DOCUMENT ME!
43    * 
44    * @param comp
45    *          DOCUMENT ME!
46    * @param al
47    *          DOCUMENT ME!
48    */
49   public static void Register(Component comp, String seqSetId)
50   {
51     if (components == null)
52     {
53       components = new Hashtable();
54     }
55
56     if (components.containsKey(seqSetId))
57     {
58       Vector comps = (Vector) components.get(seqSetId);
59       if (!comps.contains(comp))
60       {
61         comps.addElement(comp);
62       }
63     }
64     else
65     {
66       Vector vcoms = new Vector();
67       vcoms.addElement(comp);
68       components.put(seqSetId, vcoms);
69     }
70   }
71
72   public static void RemoveComponent(Component comp)
73   {
74     if (components == null)
75     {
76       return;
77     }
78
79     Enumeration en = components.keys();
80     while (en.hasMoreElements())
81     {
82       String id = en.nextElement().toString();
83       Vector comps = (Vector) components.get(id);
84       comps.remove(comp);
85       if (comps.size() == 0)
86       {
87         components.remove(id);
88       }
89     }
90   }
91
92   public static void Refresh(Component source, String id)
93   {
94     Refresh(source, id, false, false);
95   }
96
97   public static void Refresh(Component source, String id,
98           boolean alignmentChanged, boolean validateSequences)
99   {
100     if (components == null)
101     {
102       return;
103     }
104
105     Component comp;
106     Vector comps = (Vector) components.get(id);
107
108     if (comps == null)
109     {
110       return;
111     }
112
113     Enumeration e = comps.elements();
114     while (e.hasMoreElements())
115     {
116       comp = (Component) e.nextElement();
117
118       if (comp == source)
119       {
120         continue;
121       }
122
123       if (validateSequences && comp instanceof AlignmentPanel
124               && source instanceof AlignmentPanel)
125       {
126         validateSequences(((AlignmentPanel) source).av.getAlignment(),
127                 ((AlignmentPanel) comp).av.getAlignment());
128       }
129
130       if (comp instanceof AlignmentPanel && alignmentChanged)
131       {
132         ((AlignmentPanel) comp).alignmentChanged();
133       }
134
135       comp.repaint();
136     }
137   }
138
139   static void validateSequences(AlignmentI source, AlignmentI comp)
140   {
141     SequenceI[] a1;
142     if (source.getHiddenSequences().getSize() > 0)
143     {
144       a1 = source.getHiddenSequences().getFullAlignment()
145               .getSequencesArray();
146     }
147     else
148     {
149       a1 = source.getSequencesArray();
150     }
151
152     SequenceI[] a2;
153     if (comp.getHiddenSequences().getSize() > 0)
154     {
155       a2 = comp.getHiddenSequences().getFullAlignment().getSequencesArray();
156     }
157     else
158     {
159       a2 = comp.getSequencesArray();
160     }
161
162     int i, iSize = a1.length, j, jSize = a2.length;
163
164     if (iSize == jSize)
165     {
166       return;
167     }
168
169     boolean exists = false;
170     for (i = 0; i < iSize; i++)
171     {
172       exists = false;
173
174       for (j = 0; j < jSize; j++)
175       {
176         if (a2[j] == a1[i])
177         {
178           exists = true;
179           break;
180         }
181       }
182
183       if (!exists)
184       {
185         if (i < comp.getHeight())
186         {
187           // TODO: the following does not trigger any recalculation of
188           // height/etc, or maintain the dataset
189           if (comp.getDataset() != source.getDataset())
190           {
191             // raise an implementation warning here - not sure if this situation
192             // will ever occur
193             System.err
194                     .println("IMPLEMENTATION PROBLEM: DATASET out of sync due to an insert whilst calling PaintRefresher.validateSequences(AlignmentI, ALignmentI)");
195           }
196           List<SequenceI> alsq;
197           synchronized (alsq = comp.getSequences())
198           {
199             alsq.add(i, a1[i]);
200           }
201         }
202         else
203         {
204           comp.addSequence(a1[i]);
205         }
206
207         if (comp.getHiddenSequences().getSize() > 0)
208         {
209           a2 = comp.getHiddenSequences().getFullAlignment()
210                   .getSequencesArray();
211         }
212         else
213         {
214           a2 = comp.getSequencesArray();
215         }
216
217         jSize = a2.length;
218       }
219     }
220
221     iSize = a1.length;
222     jSize = a2.length;
223
224     for (j = 0; j < jSize; j++)
225     {
226       exists = false;
227       for (i = 0; i < iSize; i++)
228       {
229         if (a2[j] == a1[i])
230         {
231           exists = true;
232           break;
233         }
234       }
235
236       if (!exists)
237       {
238         comp.deleteSequence(a2[j]);
239       }
240     }
241   }
242
243   static AlignmentPanel[] getAssociatedPanels(String id)
244   {
245     if (components == null)
246     {
247       return new AlignmentPanel[0];
248     }
249     ;
250     Vector comps = (Vector) components.get(id);
251     if (comps == null)
252     {
253       return new AlignmentPanel[0];
254     }
255     ;
256     Vector tmp = new Vector();
257     int i, iSize = comps.size();
258     for (i = 0; i < iSize; i++)
259     {
260       if (comps.elementAt(i) instanceof AlignmentPanel)
261       {
262         tmp.addElement(comps.elementAt(i));
263       }
264     }
265     AlignmentPanel[] result = new AlignmentPanel[tmp.size()];
266     tmp.toArray(result);
267
268     return result;
269   }
270
271 }