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.
21 package jalview.renderer.seqfeatures;
23 import jalview.api.FeatureRenderer;
24 import jalview.api.FeaturesDisplayedI;
25 import jalview.datamodel.SequenceI;
26 import jalview.util.Platform;
27 import jalview.viewmodel.seqfeatures.FeatureRendererModel;
29 import java.awt.Color;
30 import java.awt.Graphics;
31 import java.awt.image.BufferedImage;
34 * A helper class to find feature colour using an associated FeatureRenderer
39 public class FeatureColourFinder
42 * the class we delegate feature finding to
44 private FeatureRenderer featureRenderer;
47 * a 1-pixel image on which features can be drawn, for the case where
48 * transparency allows 'see-through' of multiple feature colours
50 private BufferedImage offscreenImage;
52 private Graphics goff;
59 public FeatureColourFinder(FeatureRenderer fr)
62 offscreenImage = new BufferedImage(1, 1, BufferedImage.TYPE_INT_ARGB);
63 goff = offscreenImage.getGraphics();
67 * Answers the feature colour to show for the given sequence and column
68 * position. This delegates to the FeatureRenderer to find the colour, which
69 * will depend on feature location, visibility, ordering, colour scheme, and
70 * whether or not transparency is applied. For feature rendering with
71 * transparency, this class provides a dummy 'offscreen' graphics context
72 * where multiple feature colours can be overlaid and the combined colour read
75 * This method is not thread-safe when transparency is applied, since a shared
76 * BufferedImage would be used by all threads to hold the composite colour at
77 * a position. Each thread should use a separate instance of this class.
79 * @param defaultColour
82 * alignment column position (0..)
85 public Color findFeatureColour(Color defaultColour, SequenceI seq,
88 if (noFeaturesDisplayed())
96 * if transparency applies, provide a notional 1x1 graphics context
97 * that has been primed with the default colour
99 if (featureRenderer.getTransparency() != 1f)
102 Color c = (defaultColour == null ? Color.white : defaultColour);
105 // Clear the HTML5 canvas color.
106 // otherwise we get a smearing.
107 // For whatever reason, this is necessary BH 2019.10.01.
109 g.fillRect(0, 0, 1, 1);
111 offscreenImage.setRGB(0, 0, c.getRGB());
114 Color c = featureRenderer.findFeatureColour(seq, column + 1, g);
117 return defaultColour;
125 * for JavaScript the pixel itself
126 * is a resource that needs to be recreated in getRGB(0,0)
128 offscreenImage.flush();
130 c = new Color(offscreenImage.getRGB(0, 0));
137 * Answers true if feature display is turned off, or there are no features
138 * configured to be visible
142 public boolean noFeaturesDisplayed()
144 if (featureRenderer == null
145 || !featureRenderer.getViewport().isShowSequenceFeatures())
150 if (!((FeatureRendererModel) featureRenderer).hasRenderOrder())
155 FeaturesDisplayedI displayed = featureRenderer.getFeaturesDisplayed();
156 if (displayed == null || displayed.getVisibleFeatureCount() == 0)