JAL-2704 don't shade gap colour for PID/conservation
[jalview.git] / test / jalview / renderer / ResidueShaderTest.java
1 package jalview.renderer;
2
3 import static org.testng.AssertJUnit.assertEquals;
4 import static org.testng.AssertJUnit.assertFalse;
5 import static org.testng.AssertJUnit.assertTrue;
6
7 import jalview.analysis.Conservation;
8 import jalview.datamodel.Profile;
9 import jalview.datamodel.ProfileI;
10 import jalview.datamodel.Profiles;
11 import jalview.datamodel.Sequence;
12 import jalview.datamodel.SequenceI;
13 import jalview.schemes.ColourSchemeI;
14 import jalview.schemes.PIDColourScheme;
15 import jalview.schemes.ResidueProperties;
16 import jalview.schemes.UserColourScheme;
17
18 import java.awt.Color;
19 import java.util.Collections;
20
21 import org.testng.annotations.Test;
22
23 public class ResidueShaderTest
24 {
25
26   @Test(groups = "Functional")
27   public void testAboveThreshold()
28   {
29     /*
30      * make up profiles for this alignment:
31      * AR-Q
32      * AR--
33      * SR-T
34      * SR-T
35      */
36     ProfileI[] profiles = new ProfileI[4];
37     profiles[0] = new Profile(4, 0, 2, "AS");
38     profiles[1] = new Profile(4, 0, 4, "R");
39     profiles[2] = new Profile(4, 4, 0, "");
40     profiles[3] = new Profile(4, 1, 2, "T");
41     ResidueShader ccs = new ResidueShader(new PIDColourScheme());
42     ccs.setConsensus(new Profiles(profiles));
43
44     /*
45      * no threshold
46      */
47     ccs.setThreshold(0, true);
48     assertTrue(ccs.aboveThreshold('a', 0));
49     assertTrue(ccs.aboveThreshold('S', 0));
50     assertTrue(ccs.aboveThreshold('W', 0));
51     assertTrue(ccs.aboveThreshold('R', 1));
52     assertTrue(ccs.aboveThreshold('W', 2));
53     assertTrue(ccs.aboveThreshold('t', 3));
54     assertTrue(ccs.aboveThreshold('Q', 3));
55
56     /*
57      * with threshold, include gaps
58      */
59     ccs.setThreshold(60, false);
60     assertFalse(ccs.aboveThreshold('a', 0));
61     assertFalse(ccs.aboveThreshold('S', 0));
62     assertTrue(ccs.aboveThreshold('R', 1));
63     assertFalse(ccs.aboveThreshold('W', 2));
64     assertFalse(ccs.aboveThreshold('t', 3)); // 50% < 60%
65
66     /*
67      * with threshold, ignore gaps
68      */
69     ccs.setThreshold(60, true);
70     assertFalse(ccs.aboveThreshold('a', 0));
71     assertFalse(ccs.aboveThreshold('S', 0));
72     assertTrue(ccs.aboveThreshold('R', 1));
73     assertFalse(ccs.aboveThreshold('W', 2));
74     assertTrue(ccs.aboveThreshold('t', 3)); // 67% > 60%
75   }
76
77   /**
78    * Test colour bleaching based on conservation score and conservation slider.
79    * Scores of 10 or 11 should leave colours unchanged. Gap is always white.
80    */
81   @Test(groups = "Functional")
82   public void testApplyConservation()
83   {
84     ResidueShader ccs = new ResidueShader(new PIDColourScheme());
85
86     // no conservation present - no fading
87     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 12));
88
89     /*
90      * stub Conservation to return a given consensus string
91      */
92     final String consSequence = "0123456789+*-";
93     Conservation cons = new Conservation(null,
94             Collections.<SequenceI> emptyList(), 0, 0)
95     {
96       @Override
97       public SequenceI getConsSequence()
98       {
99         return new Sequence("seq", consSequence);
100       }
101     };
102     ccs.setConservation(cons);
103
104     // column out of range:
105     assertEquals(Color.RED,
106             ccs.applyConservation(Color.RED, consSequence.length()));
107
108     /*
109      * with 100% threshold, 'fade factor' is 
110      * (11-score)/10 * 100/20 = (11-score)/2
111      * which is >= 1 for all scores i.e. all fade to white except +, *
112      */
113     ccs.setConservationInc(100);
114     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 0));
115     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 1));
116     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 2));
117     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 3));
118     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 4));
119     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 5));
120     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 6));
121     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 7));
122     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 8));
123     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 9));
124     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 10));
125     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 11));
126     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 12));
127
128     /*
129      * with 0% threshold, there should be no fading
130      */
131     ccs.setConservationInc(0);
132     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 0));
133     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 1));
134     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 2));
135     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 3));
136     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 4));
137     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 5));
138     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 6));
139     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 7));
140     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 8));
141     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 9));
142     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 10));
143     assertEquals(Color.RED, ccs.applyConservation(Color.RED, 11));
144     assertEquals(Color.WHITE, ccs.applyConservation(Color.RED, 12)); // gap
145
146     /*
147      * with 40% threshold, 'fade factor' is 
148      * (11-score)/10 * 40/20 = (11-score)/5
149      * which is {>1, >1, >1, >1, >1, >1, 1, 0.8, 0.6, 0.4} for score 0-9
150      * e.g. score 7 colour fades 80% of the way to white (255, 255, 255)
151      */
152     ccs.setConservationInc(40);
153     Color colour = new Color(155, 105, 55);
154     assertEquals(Color.WHITE, ccs.applyConservation(colour, 0));
155     assertEquals(Color.WHITE, ccs.applyConservation(colour, 1));
156     assertEquals(Color.WHITE, ccs.applyConservation(colour, 2));
157     assertEquals(Color.WHITE, ccs.applyConservation(colour, 3));
158     assertEquals(Color.WHITE, ccs.applyConservation(colour, 4));
159     assertEquals(Color.WHITE, ccs.applyConservation(colour, 5));
160     assertEquals(Color.WHITE, ccs.applyConservation(colour, 6));
161     assertEquals(new Color(235, 225, 215), ccs.applyConservation(colour, 7));
162     assertEquals(new Color(215, 195, 175), ccs.applyConservation(colour, 8));
163     assertEquals(new Color(195, 165, 135), ccs.applyConservation(colour, 9));
164     assertEquals(colour, ccs.applyConservation(colour, 10));
165     assertEquals(colour, ccs.applyConservation(colour, 11));
166     assertEquals(Color.WHITE, ccs.applyConservation(colour, 12));
167   }
168
169   /**
170    * A custom gap colour should not be affected by Colour by Conservation
171    */
172   @Test(groups = "Functional")
173   public void testFindColour_gapColour()
174   {
175     Color[] colours = new Color[ResidueProperties.maxProteinIndex + 1];
176     colours[5] = Color.blue; // Q colour
177     colours[23] = Color.red; // gap colour
178     ColourSchemeI cs = new UserColourScheme(colours);
179     ResidueShader ccs = new ResidueShader(cs);
180   
181     assertEquals(Color.red, ccs.findColour(' ', 7, null));
182   
183     /*
184      * stub Conservation to return a given consensus string
185      */
186     final String consSequence = "0123456789+*-";
187     Conservation cons = new Conservation(null,
188             Collections.<SequenceI> emptyList(), 0, 0)
189     {
190       @Override
191       public SequenceI getConsSequence()
192       {
193         return new Sequence("seq", consSequence);
194       }
195     };
196     ccs.setConservation(cons);
197   
198     /*
199      * with 0% threshold, there should be no fading
200      */
201     ccs.setConservationInc(0);
202     assertEquals(Color.red, ccs.findColour(' ', 7, null));
203     assertEquals(Color.blue, ccs.findColour('Q', 7, null));
204   
205     /*
206      * with 40% threshold, 'fade factor' is 
207      * (11-score)/10 * 40/20 = (11-score)/5
208      * so position 7, score 7 fades 80% of the way to white (255, 255, 255)
209      */
210     ccs.setConservationInc(40);
211
212     /*
213      * gap colour is unchanged for Conservation
214      */
215     assertEquals(Color.red, ccs.findColour(' ', 7, null));
216
217     /*
218      * residue colour is faded 80% of the way from
219      * blue(0, 0, 255) to white(255, 255, 255)
220      * making (204, 204, 255)
221      */
222     assertEquals(new Color(204, 204, 255), ccs.findColour('Q', 7, null));
223   }
224
225 }