/* * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$) * Copyright (C) $$Year-Rel$$ The Jalview Authors * * This file is part of Jalview. * * Jalview is free software: you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation, either version 3 * of the License, or (at your option) any later version. * * Jalview is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty * of MERCHANTABILITY or FITNESS FOR A PARTICULAR * PURPOSE. See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Jalview. If not, see . * The Jalview Authors are detailed in the 'AUTHORS' file. */ package jalview.ws.jws2.jabaws2; import jalview.analysis.AlignmentAnnotationUtils; import jalview.api.FeatureColourI; import jalview.bin.Cache; import jalview.bin.Console; import jalview.datamodel.AlignmentAnnotation; import jalview.datamodel.AlignmentI; import jalview.datamodel.GraphLine; import jalview.datamodel.SequenceFeature; import jalview.datamodel.SequenceI; import jalview.datamodel.features.FeatureMatcherSetI; import jalview.schemes.FeatureColour; import jalview.util.ColorUtils; import java.awt.Color; import java.util.ArrayList; import java.util.HashMap; import java.util.Hashtable; import java.util.Iterator; import java.util.List; import java.util.Map; import compbio.data.sequence.Range; import compbio.data.sequence.Score; import compbio.data.sequence.ScoreManager.ScoreHolder; public class AADisorderClient extends JabawsAnnotationInstance { // static configuration public static String getServiceActionText() { return "Submitting amino acid sequences for disorder prediction."; } // minSeq = 1; protein only, no gaps // instance public AADisorderClient(Jws2Instance handle) { super(handle); } @Override List annotationFromScoreManager(AlignmentI seqs, Map featureColours, Map featureFilters) { Map featureTypeMap = featureMap.get(our.getName()); Map> annotTypeMap = annotMap .get(our.getName()); boolean dispFeatures = false; Map fc = new Hashtable<>(), fex = new Hashtable(); List ourAnnot = new ArrayList<>(); int graphGroup = 1, lastAnnot = 0; for (SequenceI seq : seqs.getSequences()) { String seqId = seq.getName(); boolean sameGroup = false; SequenceI dseq, aseq; int base = seq.findPosition(0) - 1; aseq = seq; while ((dseq = seq).getDatasetSequence() != null) { seq = seq.getDatasetSequence(); } ScoreHolder scores = null; try { scores = scoremanager.getAnnotationForSequence(seqId); } catch (Exception q) { Console.info("Couldn't recover disorder prediction for sequence " + seq.getName() + "(Prediction name was " + seqId + ")" + "\nSee http://issues.jalview.org/browse/JAL-1319 for one possible reason why disorder predictions might fail.", q); } float last = Float.NaN, val = Float.NaN; if (scores != null && scores.scores != null) { for (Score scr : scores.scores) { if (scr.getRanges() != null && scr.getRanges().size() > 0) { Iterator vals = scr.getScores().iterator(); // make features on sequence for (Range rn : scr.getRanges()) { // TODO: Create virtual feature settings SequenceFeature sf; String[] type = featureTypeMap.get(scr.getMethod()); if (type == null) { // create a default type for this feature type = new String[] { typeName + " (" + scr.getMethod() + ")", our.getActionText() }; } if (vals.hasNext()) { val = vals.next().floatValue(); sf = new SequenceFeature(type[0], type[1], base + rn.from, base + rn.to, val, methodName); } else { sf = new SequenceFeature(type[0], type[1], base + rn.from, base + rn.to, methodName); } dseq.addSequenceFeature(sf); // mark feature as requiring a graduated colourscheme if has // variable scores if (!Float.isNaN(last) && !Float.isNaN(val) && last != val) { fc.put(sf.getType(), sf); } else { fex.put(sf.getType(), sf); } last = val; dispFeatures = true; } } else { if (scr.getScores().size() == 0) { continue; } String typename, calcName; AlignmentAnnotation annot = createAnnotationRowsForScores( seqs, null, ourAnnot, typename = our.getName() + " (" + scr.getMethod() + ")", calcName = our.getNameURI() + "/" + scr.getMethod(), aseq, base + 1, scr); annot.graph = AlignmentAnnotation.LINE_GRAPH; Map styleMap = (annotTypeMap == null) ? null : annotTypeMap.get(scr.getMethod()); annot.visible = (styleMap == null || styleMap.get(INVISIBLE) == null); double[] thrsh = (styleMap == null) ? null : (double[]) styleMap.get(THRESHOLD); float[] range = (styleMap == null) ? null : (float[]) styleMap.get(RANGE); if (range != null) { annot.graphMin = range[0]; annot.graphMax = range[1]; } if (styleMap == null || styleMap.get(DONTCOMBINE) == null) { { if (!sameGroup) { graphGroup++; sameGroup = true; } annot.graphGroup = graphGroup; } } annot.description = "" + our.getActionText() + " - raw scores"; if (thrsh != null) { String threshNote = (thrsh[0] > 0 ? "Above " : "Below ") + thrsh[1] + " indicates disorder"; annot.threshold = new GraphLine((float) thrsh[1], threshNote, Color.red); annot.description += "
" + threshNote; } annot.description += ""; Color col = ColorUtils .createColourFromName(typeName + scr.getMethod()); for (int p = 0, ps = annot.annotations.length; p < ps; p++) { if (annot.annotations[p] != null) { annot.annotations[p].colour = col; } } annot._linecolour = col; // finally, update any dataset annotation AlignmentAnnotationUtils.replaceAnnotationOnAlignmentWith(annot, typename, calcName); } } } if (lastAnnot + 1 == ourAnnot.size()) { // remove singleton alignment annotation row ourAnnot.get(lastAnnot).graphGroup = -1; } } { if (dispFeatures) { // TODO: virtual feature settings // feature colours need to merged with current viewport's colours // simple feature colours promoted to colour-by-score ranges using // currently assigned or created feature colour for (String ft : fex.keySet()) { Color col = ColorUtils.createColourFromName(ft); // set graduated color as fading to white for minimum, and // autoscaling to values on alignment FeatureColourI ggc; if (fc.get(ft) != null) { ggc = new FeatureColour(col, Color.white, col, Color.white, Float.MIN_VALUE, Float.MAX_VALUE); ggc.setAutoScaled(true); } else { ggc = new FeatureColour(col); } featureColours.put(ft, ggc); } } return ourAnnot; } } private static final String THRESHOLD = "THRESHOLD"; private static final String RANGE = "RANGE"; String typeName; String methodName; String groupName; private static Map> featureMap; private static Map>> annotMap; private static String DONTCOMBINE = "DONTCOMBINE"; private static String INVISIBLE = "INVISIBLE"; static { // TODO: turn this into some kind of configuration file that's a bit easier // to edit featureMap = new HashMap<>(); Map fmap; featureMap.put(compbio.ws.client.Services.IUPredWS.toString(), fmap = new HashMap<>()); fmap.put("Glob", new String[] { "Globular Domain", "Predicted globular domain" }); featureMap.put(compbio.ws.client.Services.JronnWS.toString(), fmap = new HashMap<>()); featureMap.put(compbio.ws.client.Services.DisemblWS.toString(), fmap = new HashMap<>()); fmap.put("REM465", new String[] { "REM465", "Missing density" }); fmap.put("HOTLOOPS", new String[] { "HOTLOOPS", "Flexible loops" }); fmap.put("COILS", new String[] { "COILS", "Random coil" }); featureMap.put(compbio.ws.client.Services.GlobPlotWS.toString(), fmap = new HashMap<>()); fmap.put("GlobDoms", new String[] { "Globular Domain", "Predicted globular domain" }); fmap.put("Disorder", new String[] { "Protein Disorder", "Probable unstructured peptide region" }); Map> amap; annotMap = new HashMap<>(); annotMap.put(compbio.ws.client.Services.GlobPlotWS.toString(), amap = new HashMap<>()); amap.put("Dydx", new HashMap()); amap.get("Dydx").put(DONTCOMBINE, DONTCOMBINE); amap.get("Dydx").put(THRESHOLD, new double[] { 1, 0 }); amap.get("Dydx").put(RANGE, new float[] { -1, +1 }); amap.put("SmoothedScore", new HashMap()); amap.get("SmoothedScore").put(INVISIBLE, INVISIBLE); amap.put("RawScore", new HashMap()); amap.get("RawScore").put(INVISIBLE, INVISIBLE); annotMap.put(compbio.ws.client.Services.DisemblWS.toString(), amap = new HashMap<>()); amap.put("COILS", new HashMap()); amap.put("HOTLOOPS", new HashMap()); amap.put("REM465", new HashMap()); amap.get("COILS").put(THRESHOLD, new double[] { 1, 0.516 }); amap.get("COILS").put(RANGE, new float[] { 0, 1 }); amap.get("HOTLOOPS").put(THRESHOLD, new double[] { 1, 0.6 }); amap.get("HOTLOOPS").put(RANGE, new float[] { 0, 1 }); amap.get("REM465").put(THRESHOLD, new double[] { 1, 0.1204 }); amap.get("REM465").put(RANGE, new float[] { 0, 1 }); annotMap.put(compbio.ws.client.Services.IUPredWS.toString(), amap = new HashMap<>()); amap.put("Long", new HashMap()); amap.put("Short", new HashMap()); amap.get("Long").put(THRESHOLD, new double[] { 1, 0.5 }); amap.get("Long").put(RANGE, new float[] { 0, 1 }); amap.get("Short").put(THRESHOLD, new double[] { 1, 0.5 }); amap.get("Short").put(RANGE, new float[] { 0, 1 }); annotMap.put(compbio.ws.client.Services.JronnWS.toString(), amap = new HashMap<>()); amap.put("JRonn", new HashMap()); amap.get("JRonn").put(THRESHOLD, new double[] { 1, 0.5 }); amap.get("JRonn").put(RANGE, new float[] { 0, 1 }); } }