Bug 11436 fixed: With matplot, color outside the colormap was replaced with the last...
[scilab.git] / scilab / modules / graphic_objects / src / cpp / ColorComputer.cpp
1 /*
2  *  Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
3  *  Copyright (C) 2011-2012 - DIGITEO - Manuel Juliachs
4  *
5  *  This file must be used under the terms of the CeCILL.
6  *  This source file is licensed as described in the file COPYING, which
7  *  you should have received as part of this distribution.  The terms
8  *  are also available at
9  *  http://www.cecill.info/licences/Licence_CeCILL_V2-en.txt
10  *
11  */
12
13 #include "ColorComputer.hxx"
14 #include  "DecompositionUtils.hxx"
15
16 extern "C"
17 {
18 #include <math.h>
19
20 #include "getGraphicObjectProperty.h"
21 #include "graphicObjectProperties.h"
22 }
23
24 void ColorComputer::getColor(double s, double smin, double srange, double indexOffset, double* colormap, int colormapSize, float* returnedColor)
25 {
26     double value = 0.;
27     int index = 0;
28
29     if (!DecompositionUtils::isANumber(s))
30     {
31         /* Black is output if s is a Nan */
32         returnedColor[0] = MIN_COMPONENT_VALUE;
33         returnedColor[1] = MIN_COMPONENT_VALUE;
34         returnedColor[2] = MIN_COMPONENT_VALUE;
35     }
36     else
37     {
38         value = (s - smin) / (srange);
39         index = (int) ((double)(colormapSize - 1) * value + indexOffset);
40
41         /* Clamp */
42         if (index < 0)
43         {
44             index = 0;
45         }
46         else if (index > colormapSize - 1)
47         {
48             index = colormapSize - 1;
49         }
50
51         returnedColor[0] = (float)colormap[index];
52         returnedColor[1] = (float)colormap[colormapSize + index];
53         returnedColor[2] = (float)colormap[2 * colormapSize + index];
54     }
55 }
56
57 void ColorComputer::getColor(double s, double smin, double srange, double indexOffset, double* colormap, int minIndex, int maxIndex, int colormapSize, float* returnedColor)
58 {
59     double value = 0.;
60     int index = 0;
61
62     if (!DecompositionUtils::isANumber(s))
63     {
64         /* Black is output if s is a Nan */
65         returnedColor[0] = MIN_COMPONENT_VALUE;
66         returnedColor[1] = MIN_COMPONENT_VALUE;
67         returnedColor[2] = MIN_COMPONENT_VALUE;
68     }
69     else
70     {
71         value = (s - smin) / (srange);
72         index = (int) ((double)(maxIndex - minIndex) * value + indexOffset + (double) minIndex);
73
74         /* Clamp */
75         if (index < minIndex)
76         {
77             index = minIndex;
78         }
79         else if (index > maxIndex)
80         {
81             index = maxIndex;
82         }
83
84         returnedColor[0] = (float)colormap[index];
85         returnedColor[1] = (float)colormap[colormapSize + index];
86         returnedColor[2] = (float)colormap[2 * colormapSize + index];
87     }
88 }
89
90 double ColorComputer::getIndex(double s, double smin, double srange, double indexOffset, int minIndex, int maxIndex)
91 {
92     double value = 0.;
93     double index = 0.;
94
95     if (!DecompositionUtils::isANumber(s))
96     {
97         /* Black is output if s is a Nan. */
98         index = BLACK_INDEX;
99     }
100     else
101     {
102         value = (s - smin) / (srange);
103         index = (double)(maxIndex - minIndex) * value + indexOffset + (double) minIndex;
104
105         index = floor(index);
106
107         /* Clamp */
108         if (index < (double) minIndex)
109         {
110             index = (double) minIndex;
111         }
112         else if (index > (double) maxIndex)
113         {
114             index = (double) maxIndex;
115         }
116     }
117
118     return index;
119 }
120
121 void ColorComputer::getDirectColor(double s, double* colormap, int colormapSize, float* returnedColor, bool clamped)
122 {
123     int index = 0;
124
125     if (s <= (double) BLACK_LOWER_INDEX)
126     {
127         /* Clamp to white */
128         returnedColor[0] = MAX_COMPONENT_VALUE;
129         returnedColor[1] = MAX_COMPONENT_VALUE;
130         returnedColor[2] = MAX_COMPONENT_VALUE;
131     }
132     else if ((((double) BLACK_LOWER_INDEX < s) && (s < (double) BLACK_UPPER_INDEX)) || !DecompositionUtils::isANumber(s))
133     {
134         /* Black is also output for Nan values */
135         returnedColor[0] = MIN_COMPONENT_VALUE;
136         returnedColor[1] = MIN_COMPONENT_VALUE;
137         returnedColor[2] = MIN_COMPONENT_VALUE;
138     }
139     else
140     {
141         if (s > (double)(colormapSize - 1))
142         {
143             if (clamped)
144             {
145                 s = (double) (colormapSize - 1);
146             }
147             else
148             {
149                 returnedColor[0] = -1;
150                 return;
151             }
152         }
153
154         index = (int) s;
155
156         returnedColor[0] = (float)colormap[index];
157         returnedColor[1] = (float)colormap[colormapSize + index];
158         returnedColor[2] = (float)colormap[2 * colormapSize + index];
159     }
160 }
161
162 double ColorComputer::getDirectIndex(double s, int colormapSize)
163 {
164     double index = 0.;
165
166     if (s <= (double) WHITE_LOWER_INDEX)
167     {
168         /* Lowest index if the color is below the white range's lower index */
169         index = 0.0;
170     }
171     else if (s <= (double) BLACK_LOWER_INDEX)
172     {
173         /* White is output */
174         index = WHITE_INDEX;
175     }
176     else if ((((double) BLACK_LOWER_INDEX < s) && (s < (double) BLACK_UPPER_INDEX)) || !DecompositionUtils::isANumber(s))
177     {
178         /* Black is also output for Nan values */
179         index = BLACK_INDEX;
180     }
181     else
182     {
183         index = floor(s);
184
185         if (index > (double)(colormapSize - 1))
186         {
187             index = (double) (colormapSize - 1);
188         }
189     }
190
191     return index;
192 }
193
194 void ColorComputer::getDirectByteColor(double s, double* colormap, int colormapSize, unsigned char* returnedColor, bool clamped)
195 {
196     float color[3];
197     getDirectColor(s, colormap, colormapSize, color, clamped);
198
199     returnedColor[0] = (unsigned char)(color[0] * 255);
200     returnedColor[1] = (unsigned char)(color[1] * 255);
201     returnedColor[2] = (unsigned char)(color[2] * 255);
202
203     if (!clamped && color[0] == -1)
204     {
205         returnedColor[3] = 0;
206     }
207     else
208     {
209         returnedColor[3] = 255;
210     }
211 }
212
213 double ColorComputer::getClampedDirectIndex(double s, int colormapSize)
214 {
215     double index = s;
216
217     /* Black is output if s is a Nan or if it corresponds to the black color */
218     if (!DecompositionUtils::isANumber(s) || ((BLACK_INDEX <= s) && (s < 0.0)))
219     {
220         index = BLACK_INDEX;
221     }
222     else
223     {
224         index = floor(index);
225
226         /* Clamp */
227         if (s < 0.0)
228         {
229             index = 0.0;
230         }
231         else if (s > (double)(colormapSize - 1))
232         {
233             index = (double) (colormapSize - 1);
234         }
235     }
236
237     return index;
238 }
239
240 void ColorComputer::getClampedDirectColor(double s, double* colormap, int colormapSize, float* returnedColor)
241 {
242     int index = 0;
243
244     if (!DecompositionUtils::isANumber(s))
245     {
246         /* Black is output if s is a Nan */
247         returnedColor[0] = MIN_COMPONENT_VALUE;
248         returnedColor[1] = MIN_COMPONENT_VALUE;
249         returnedColor[2] = MIN_COMPONENT_VALUE;
250     }
251     else
252     {
253         /* Clamp */
254         if (s < 0.0)
255         {
256             s = 0.0;
257         }
258         else if (s > (double)(colormapSize - 1))
259         {
260             s = (double) (colormapSize - 1);
261         }
262
263         index = (int) s;
264
265         returnedColor[0] = (float)colormap[index];
266         returnedColor[1] = (float)colormap[colormapSize + index];
267         returnedColor[2] = (float)colormap[2 * colormapSize + index];
268     }
269 }