2 * Jalview - A Sequence Alignment Editor and Viewer (Version 2.7)
\r
3 * Copyright (C) 2011 J Procter, AM Waterhouse, J Engelhardt, LM Lui, G Barton, M Clamp, S Searle
\r
5 * This file is part of Jalview.
\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
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
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
18 package jalview.io.vamsas;
\r
20 import java.util.Enumeration;
\r
21 import java.util.Vector;
\r
23 import uk.ac.vamsas.objects.core.DataSet;
\r
24 import uk.ac.vamsas.objects.core.DataSetAnnotations;
\r
25 import uk.ac.vamsas.objects.core.Link;
\r
26 import uk.ac.vamsas.objects.core.Property;
\r
27 import uk.ac.vamsas.objects.core.Provenance;
\r
28 import uk.ac.vamsas.objects.core.RangeAnnotation;
\r
29 import uk.ac.vamsas.objects.core.Score;
\r
30 import uk.ac.vamsas.objects.core.Seg;
\r
31 import uk.ac.vamsas.objects.core.Sequence;
\r
32 import uk.ac.vamsas.objects.utils.Properties;
\r
33 import jalview.bin.Cache;
\r
34 import jalview.datamodel.SequenceFeature;
\r
35 import jalview.datamodel.SequenceI;
\r
36 import jalview.io.VamsasAppDatastore;
\r
37 import jalview.util.UrlLink;
\r
43 public class Sequencefeature extends Rangetype
\r
46 uk.ac.vamsas.objects.core.DataSet dataset;
\r
48 uk.ac.vamsas.objects.core.Sequence sequence;
\r
50 private SequenceI dsSeq;
\r
52 public Sequencefeature(VamsasAppDatastore vamsasAppDatastore,
\r
53 SequenceFeature sequenceFeature,
\r
54 uk.ac.vamsas.objects.core.DataSet dataset,
\r
55 uk.ac.vamsas.objects.core.Sequence sequence)
\r
57 super(vamsasAppDatastore, sequenceFeature, DataSetAnnotations.class);
\r
58 this.dataset = dataset;
\r
59 this.sequence = sequence;
\r
63 public Sequencefeature(VamsasAppDatastore vamsasAppDatastore,
\r
64 DataSetAnnotations dseta, SequenceI dsSeq)
\r
66 super(vamsasAppDatastore, dseta,
\r
67 jalview.datamodel.SequenceFeature.class);
\r
72 public void addToDocument()
\r
74 DataSetAnnotations dsa = (DataSetAnnotations) vobj;
\r
75 jalview.datamodel.SequenceFeature feature = (jalview.datamodel.SequenceFeature) jvobj;
\r
76 dsa = (DataSetAnnotations) getDSAnnotationFromJalview(
\r
77 new DataSetAnnotations(), feature);
\r
78 if (dsa.getProvenance() == null)
\r
80 dsa.setProvenance(new Provenance());
\r
82 addProvenance(dsa.getProvenance(), "created"); // JBPNote - need
\r
84 dsa.addSeqRef(sequence); // we have just created this annotation
\r
85 // - so safe to use this
\r
86 bindjvvobj(feature, dsa);
\r
87 dataset.addDataSetAnnotations(dsa);
\r
90 public void addFromDocument()
\r
92 DataSetAnnotations dsa = (DataSetAnnotations) vobj;
\r
93 if (dsa.getSeqRefCount() != 1)
\r
96 .warn("Not binding "
\r
98 + " to Sequence Feature - has multiple dataset sequence references.");
\r
101 jalview.datamodel.SequenceFeature sf = (jalview.datamodel.SequenceFeature) jvobj;
\r
102 dsSeq.addSequenceFeature(sf = getJalviewSeqFeature(dsa));
\r
104 bindjvvobj(sf, dsa);
\r
107 public void conflict()
\r
109 log.warn("Untested sequencefeature conflict code");
\r
110 DataSetAnnotations dsa = (DataSetAnnotations) vobj;
\r
111 jalview.datamodel.SequenceFeature feature = (jalview.datamodel.SequenceFeature) jvobj;
\r
112 jalview.datamodel.SequenceFeature sf = getJalviewSeqFeature(dsa);
\r
113 replaceJvObjMapping(feature, sf); // switch binding of dsa from old feature
\r
114 // to newly created feature
\r
115 dsSeq.addSequenceFeature(sf); // add new imported feature
\r
116 addToDocument(); // and create a new feature in the document
\r
119 public void updateToDoc()
\r
121 DataSetAnnotations dsa = (DataSetAnnotations) vobj;
\r
122 jalview.datamodel.SequenceFeature feature = (jalview.datamodel.SequenceFeature) jvobj;
\r
123 if (dsa.getSeqRefCount() != 1)
\r
125 replaceJvObjMapping(feature, null);
\r
127 .warn("Binding of annotation to jalview feature has changed. Removing binding and recreating.");
\r
128 doSync(); // re-verify bindings.
\r
132 // Sync the features from Jalview
\r
133 long oldref = dsa.get__last_hash();
\r
134 getDSAnnotationFromJalview(dsa, feature);
\r
135 if (oldref != dsa.hashCode())
\r
138 .debug("Updated dataset sequence annotation from feature.");
\r
139 addProvenance(dsa.getProvenance(), "modified");
\r
145 public void updateFromDoc()
\r
147 DataSetAnnotations dsa = (DataSetAnnotations) vobj;
\r
148 jalview.datamodel.SequenceFeature feature = (jalview.datamodel.SequenceFeature) jvobj;
\r
149 if (dsa.getSeqRefCount() != 1)
\r
151 // conflicting update from document - we cannot map this feature anymore.
\r
152 replaceJvObjMapping(feature, null);
\r
154 .warn("annotation ("
\r
156 + " bound to jalview feature cannot be mapped. Removing binding, deleting feature, and deleting feature.");
\r
157 // - consider deleting the feature ?
\r
158 dsSeq.deleteFeature(feature);
\r
163 // Sync the features to Jalview - easiest to delete and add the feature
\r
165 jalview.datamodel.SequenceFeature newsf = getJalviewSeqFeature(dsa);
\r
166 dsSeq.deleteFeature(feature);
\r
167 replaceJvObjMapping(feature, newsf);
\r
168 dsSeq.addSequenceFeature(newsf);
\r
169 if (feature.otherDetails != null)
\r
171 // TODO later: leave this to finalise method ?
\r
172 feature.otherDetails.clear();
\r
178 * correctly create/update a RangeAnnotation from a jalview sequence feature
\r
179 * TODO: refactor to a method in jalview.io.vamsas.RangeAnnotation class
\r
182 * (typically DataSetAnnotations or AlignmentSequenceAnnotation)
\r
184 * (the feature to be mapped from)
\r
187 private RangeAnnotation getDSAnnotationFromJalview(RangeAnnotation dsa,
\r
188 jalview.datamodel.SequenceFeature feature)
\r
190 dsa.setType(feature.getType());
\r
191 Seg vSeg = new Seg();
\r
192 vSeg.setStart(feature.getBegin());
\r
193 vSeg.setEnd(feature.getEnd());
\r
194 vSeg.setInclusive(true);
\r
195 if (dsa.getSegCount() > 1)
\r
198 .debug("About to destroy complex annotation in vamsas document mapped to sequence feature ("
\r
199 + dsa.getVorbaId() + ")");
\r
201 dsa.setSeg(new Seg[]
\r
203 dsa.setDescription(feature.getDescription());
\r
204 dsa.setStatus(feature.getStatus());
\r
205 if (feature.links != null && feature.links.size() > 0)
\r
207 for (int i = 0, iSize = feature.links.size(); i < iSize; i++)
\r
209 String link = (String) feature.links.elementAt(i);
\r
210 UrlLink ulink = new UrlLink(link);
\r
211 if (ulink.isValid())
\r
213 // We only add static links to the document.
\r
214 Link vLink = new Link();
\r
215 vLink.setContent(ulink.getLabel());
\r
216 vLink.setHref(ulink.getTarget());
\r
217 dsa.addLink(vLink);
\r
221 dsa.setGroup(feature.getFeatureGroup());
\r
222 if (feature.getScore() != Float.NaN)
\r
224 Score fscore = new Score();
\r
225 dsa.setScore(new Score[]
\r
227 fscore.setContent(feature.getScore());
\r
228 fscore.setName(feature.getType());
\r
230 if (feature.otherDetails != null)
\r
232 Enumeration iter = feature.otherDetails.keys();
\r
233 Vector props = dsa.getPropertyAsReference();
\r
234 while (iter.hasMoreElements())
\r
236 String key = (String) iter.nextElement();
\r
237 if (!key.equalsIgnoreCase("score")
\r
238 && !key.equalsIgnoreCase("status"))
\r
240 Property nprop = new Property();
\r
241 nprop.setName(key);
\r
242 Object vlu = feature.getValue(key);
\r
243 nprop.setContent(feature.getValue(key).toString());
\r
244 boolean valid = false;
\r
245 if (vlu instanceof String)
\r
247 nprop.setType(uk.ac.vamsas.objects.utils.Properties.STRINGTYPE);
\r
250 else if (vlu instanceof Integer)
\r
253 nprop.setType(uk.ac.vamsas.objects.utils.Properties.INTEGERTYPE);
\r
255 else if (vlu instanceof Float)
\r
257 nprop.setType(uk.ac.vamsas.objects.utils.Properties.FLOATTYPE);
\r
264 uk.ac.vamsas.objects.utils.Properties.addOrReplace(props,
\r
269 dsa.addProperty(nprop);
\r
278 private SequenceFeature getJalviewSeqFeature(RangeAnnotation dseta)
\r
280 int[] se = getBounds(dseta);
\r
281 SequenceFeature sf = new jalview.datamodel.SequenceFeature(
\r
282 dseta.getType(), dseta.getDescription(), dseta.getStatus(),
\r
283 se[0], se[1], dseta.getGroup());
\r
284 if (dseta.getLinkCount() > 0)
\r
286 Link[] links = dseta.getLink();
\r
287 for (int i = 0; i < links.length; i++)
\r
289 // TODO: use URLLink parsing/validation here.
\r
290 sf.addLink(links[i].getContent() + "|" + links[i].getHref());
\r
293 if (dseta.getScoreCount() > 0)
\r
295 Enumeration scr = dseta.enumerateScore();
\r
296 while (scr.hasMoreElements())
\r
298 Score score = (Score) scr.nextElement();
\r
299 if (score.getName().equals(sf.getType()))
\r
301 sf.setScore(score.getContent());
\r
305 sf.setValue(score.getName(), "" + score.getContent());
\r
310 Enumeration props = dseta.enumerateProperty();
\r
311 while (props.hasMoreElements())
\r
313 Property p = (Property) props.nextElement();
\r
315 if (Properties.isValid(p))
\r
317 if (Properties.isString(p))
\r
319 val = p.getContent();
\r
321 if (Properties.isBoolean(p))
\r
325 val = new Boolean(p.getContent());
\r
326 } catch (Exception e)
\r
330 if (Properties.isFloat(p))
\r
334 val = new Float(p.getContent());
\r
336 } catch (Exception e)
\r
340 if (Properties.isInteger(p))
\r
344 val = new Integer(p.getContent());
\r
345 } catch (Exception e)
\r
351 sf.setValue(p.getName(), val);
\r