2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
5 * This file is part of Jalview.
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.
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.
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.
23 import jalview.datamodel.DBRefEntry;
24 import jalview.datamodel.SequenceFeature;
25 import jalview.datamodel.SequenceI;
26 import jalview.util.UrlLink;
28 import java.util.ArrayList;
29 import java.util.List;
33 * generate HTML reports for a sequence
37 public class SequenceAnnotationReport
39 final String linkImageURL;
41 public SequenceAnnotationReport(String linkImageURL)
43 this.linkImageURL = linkImageURL;
47 * appends the features at rpos to the given stringbuffer ready for display in
54 * TODO refactor to Jalview 'utilities' somehow.
56 public void appendFeatures(final StringBuffer tooltipText2, int rpos,
57 List<SequenceFeature> features)
59 appendFeatures(tooltipText2, rpos, features, null);
62 public void appendFeatures(final StringBuffer tooltipText2, int rpos,
63 List<SequenceFeature> features, Map<String, float[][]> map)
68 for (SequenceFeature feature : features)
70 if (feature.getType().equals("disulfide bond"))
72 if (feature.getBegin() == rpos || feature.getEnd() == rpos)
74 if (tooltipText2.length() > 6)
76 tooltipText2.append("<br>");
78 tooltipText2.append("disulfide bond " + feature.getBegin()
79 + ":" + feature.getEnd());
84 if (tooltipText2.length() > 6)
86 tooltipText2.append("<br>");
88 // TODO: remove this hack to display link only features
89 boolean linkOnly = feature.getValue("linkonly") != null;
92 tooltipText2.append(feature.getType() + " ");
95 // we are marking a positional feature
96 tooltipText2.append(feature.begin);
98 if (feature.begin != feature.end)
100 tooltipText2.append(" " + feature.end);
103 if (feature.getDescription() != null
104 && !feature.description.equals(feature.getType()))
106 tmpString = feature.getDescription();
107 String tmp2up = tmpString.toUpperCase();
108 int startTag = tmp2up.indexOf("<HTML>");
111 tmpString = tmpString.substring(startTag + 6);
112 tmp2up = tmp2up.substring(startTag + 6);
114 int endTag = tmp2up.indexOf("</BODY>");
117 tmpString = tmpString.substring(0, endTag);
118 tmp2up = tmp2up.substring(0, endTag);
120 endTag = tmp2up.indexOf("</HTML>");
123 tmpString = tmpString.substring(0, endTag);
128 tooltipText2.append("; " + tmpString);
132 if (tmpString.indexOf("<") > -1
133 || tmpString.indexOf(">") > -1)
135 // The description does not specify html is to
136 // be used, so we must remove < > symbols
137 tmpString = tmpString.replaceAll("<", "<");
138 tmpString = tmpString.replaceAll(">", ">");
140 tooltipText2.append("; ");
141 tooltipText2.append(tmpString);
146 tooltipText2.append("; " + tmpString);
150 // check score should be shown
151 if (!Float.isNaN(feature.getScore()))
153 float[][] rng = (map == null) ? null : (map.get(feature
155 if (rng != null && rng[0] != null && rng[0][0] != rng[0][1])
157 tooltipText2.append(" Score=" + feature.getScore());
160 if (feature.getValue("status") != null)
162 String status = feature.getValue("status").toString();
163 if (status.length() > 0)
165 tooltipText2.append("; (" + feature.getValue("status")
171 if (feature.links != null)
173 if (linkImageURL != null)
175 tooltipText2.append(" <img src=\"" + linkImageURL + "\">");
179 for (String urlstring : feature.links)
183 for (String[] urllink : createLinksFrom(null, urlstring))
185 tooltipText2.append("<br/> <a href=\""
190 + (urllink[0].toLowerCase().equals(
191 urllink[1].toLowerCase()) ? urllink[0]
192 : (urllink[0] + ":" + urllink[1]))
195 } catch (Exception x)
197 System.err.println("problem when creating links from "
213 * @return String[][] { String[] { link target, link label, dynamic component
214 * inserted (if any), url }}
216 public String[][] createLinksFrom(SequenceI seq, String link)
218 ArrayList<String[]> urlSets = new ArrayList<String[]>();
219 ArrayList<String> uniques = new ArrayList<String>();
220 UrlLink urlLink = new UrlLink(link);
221 if (!urlLink.isValid())
223 System.err.println(urlLink.getInvalidMessage());
226 final String target = urlLink.getTarget(); // link.substring(0,
227 // link.indexOf("|"));
228 final String label = urlLink.getLabel();
229 if (seq != null && urlLink.isDynamic())
232 // collect matching db-refs
233 DBRefEntry[] dbr = jalview.util.DBRefUtils.selectRefs(seq.getDBRefs(),
234 new String[] { target });
235 // collect id string too
236 String id = seq.getName();
237 String descr = seq.getDescription();
238 if (descr != null && descr.length() < 1)
244 for (int r = 0; r < dbr.length; r++)
246 if (id != null && dbr[r].getAccessionId().equals(id))
248 // suppress duplicate link creation for the bare sequence ID
249 // string with this link
252 // create Bare ID link for this RUL
253 String[] urls = urlLink.makeUrls(dbr[r].getAccessionId(), true);
256 for (int u = 0; u < urls.length; u += 2)
258 String unq = urls[u] + "|" + urls[u + 1];
259 if (!uniques.contains(unq))
261 urlSets.add(new String[] { target, label, urls[u],
271 // create Bare ID link for this RUL
272 String[] urls = urlLink.makeUrls(id, true);
275 for (int u = 0; u < urls.length; u += 2)
277 String unq = urls[u] + "|" + urls[u + 1];
278 if (!uniques.contains(unq))
280 urlSets.add(new String[] { target, label, urls[u],
287 if (descr != null && urlLink.getRegexReplace() != null)
289 // create link for this URL from description only if regex matches
290 String[] urls = urlLink.makeUrls(descr, true);
293 for (int u = 0; u < urls.length; u += 2)
295 String unq = urls[u] + "|" + urls[u + 1];
296 if (!uniques.contains(unq))
298 urlSets.add(new String[] { target, label, urls[u],
309 String unq = label + "|" + urlLink.getUrl_prefix();
310 if (!uniques.contains(unq))
313 // Add a non-dynamic link
314 urlSets.add(new String[] { target, label, null,
315 urlLink.getUrl_prefix() });
319 return urlSets.toArray(new String[][] {});
322 public void createSequenceAnnotationReport(final StringBuffer tip,
323 SequenceI sequence, boolean showDbRefs, boolean showNpFeats,
324 Map<String, float[][]> minmax)
326 createSequenceAnnotationReport(tip, sequence, showDbRefs, showNpFeats,
330 public void createSequenceAnnotationReport(final StringBuffer tip,
331 SequenceI sequence, boolean showDbRefs, boolean showNpFeats,
332 boolean tableWrap, Map<String, float[][]> map)
338 if (sequence.getDescription() != null)
340 tmp = sequence.getDescription();
341 tip.append("<br>" + tmp);
342 maxWidth = Math.max(maxWidth, tmp.length());
344 SequenceI ds = sequence;
345 while (ds.getDatasetSequence() != null)
347 ds = ds.getDatasetSequence();
349 DBRefEntry[] dbrefs = ds.getDBRefs();
350 if (showDbRefs && dbrefs != null)
352 for (int i = 0; i < dbrefs.length; i++)
355 tmp = dbrefs[i].getSource() + " " + dbrefs[i].getAccessionId();
357 maxWidth = Math.max(maxWidth, tmp.length());
361 // ADD NON POSITIONAL SEQUENCE INFO
362 SequenceFeature[] features = sequence.getSequenceFeatures();
363 if (showNpFeats && features != null)
365 for (int i = 0; i < features.length; i++)
367 if (features[i].begin == 0 && features[i].end == 0)
369 int sz = -tip.length();
370 List<SequenceFeature> tfeat = new ArrayList<SequenceFeature>();
371 tfeat.add(features[i]);
372 appendFeatures(tip, 0, tfeat, map);
374 maxWidth = Math.max(maxWidth, sz);
379 if (tableWrap && maxWidth > 60)
381 tip.insert(0, "<table width=350 border=0><tr><td><i>");
382 tip.append("</i></td></tr></table>");