anatomist  5.1.2
3D neuroimaging data viewer
colortraits.h
Go to the documentation of this file.
1 /* This software and supporting documentation are distributed by
2  * Institut Federatif de Recherche 49
3  * CEA/NeuroSpin, Batiment 145,
4  * 91191 Gif-sur-Yvette cedex
5  * France
6  *
7  * This software is governed by the CeCILL-B license under
8  * French law and abiding by the rules of distribution of free software.
9  * You can use, modify and/or redistribute the software under the
10  * terms of the CeCILL-B license as circulated by CEA, CNRS
11  * and INRIA at the following URL "http://www.cecill.info".
12  *
13  * As a counterpart to the access to the source code and rights to copy,
14  * modify and redistribute granted by the license, users are provided only
15  * with a limited warranty and the software's author, the holder of the
16  * economic rights, and the successive licensors have only limited
17  * liability.
18  *
19  * In this respect, the user's attention is drawn to the risks associated
20  * with loading, using, modifying and/or developing or reproducing the
21  * software by the user in light of its specific status of free software,
22  * that may mean that it is complicated to manipulate, and that also
23  * therefore means that it is reserved for developers and experienced
24  * professionals having in-depth computer knowledge. Users are therefore
25  * encouraged to load and test the software's suitability as regards their
26  * requirements in conditions enabling the security of their systems and/or
27  * data to be ensured and, more generally, to use and operate it in the
28  * same conditions as regards security.
29  *
30  * The fact that you are presently reading this means that you have had
31  * knowledge of the CeCILL-B license and that you accept its terms.
32  */
33 
34 
35 #ifndef ANA_COLOR_COLORTRAITS_H
36 #define ANA_COLOR_COLORTRAITS_H
37 
39 #include <aims/def/general.h>
40 #include <aims/vector/vector.h>
41 #include <aims/rgb/rgb.h>
42 
43 namespace anatomist
44 {
45 
46  template<typename T> class ColorScalarPaletteTraits
47  {
48  public:
49  ColorScalarPaletteTraits( const AObjectPalette* pal, const T & mini,
50  const T & maxi );
51  AimsRGBA color( const T & ) const;
52  void setup( const T & mini, const T & maxi );
53  T neutralColor() const;
54 
55  private:
56  const AObjectPalette *palette;
57  const carto::Volume<AimsRGBA> *colors;
58  float scale0;
59  float scale1;
60  float decal0;
61  float decal1;
62  int cmin0;
63  int cmin1;
64  int cmax0;
65  int cmax1;
66  float minv0;
67  float maxv0;
68  float minv1;
69  float maxv1;
70  };
71 
72 
73  template<typename T> class ColorNoPaletteTraits
74  {
75  public:
76  ColorNoPaletteTraits( const AObjectPalette*, const T & mini,
77  const T & maxi );
78  AimsRGBA color( const T & ) const;
79  T neutralColor() const;
80  };
81 
82  namespace internal
83  {
84 
86  template<typename T> struct ColorTraitsType
87  {
89  };
90 
91  }
92 
94  template<typename T> class ColorTraits
95  {
96  public:
97  ColorTraits( const AObjectPalette*, const T & mini, const T & maxi );
98  AimsRGBA color( const T & ) const;
100  T neutralColor() const;
101 
102  private:
103  typename internal::ColorTraitsType<T>::traitstype _traitstype;
104  };
105 
106 
107  // implementation specializations
108 
109  namespace internal
110  {
111 
112 /* template<> struct ColorTraitsType<AimsRGB>
113  {
114  typedef ColorNoPaletteTraits<AimsRGB> traitstype;
115  };
116 
117  template<> struct ColorTraitsType<AimsRGBA>
118  {
119  typedef ColorNoPaletteTraits<AimsRGBA> traitstype;
120  };
121 */
122 
123  }
124 
125  template<typename T> inline
126  ColorTraits<T>::ColorTraits( const AObjectPalette* pal, const T & mini,
127  const T & maxi )
128  : _traitstype( pal, mini, maxi )
129  {
130  }
131 
132  template <typename T> inline
133  AimsRGBA ColorTraits<T>::color( const T & in ) const
134  {
135  return _traitstype.color( in );
136  }
137 
138  template <typename T> inline
140  {
141  return _traitstype.neutralColor();
142  }
143 
144  // ---
145 
146  template<typename T> inline
148  const T &, const T & )
149  {
150  }
151 
152  template <typename T> inline
154  {
155  // this assumes AimsRGBA::AimsRGBA(const T&) is defined on T
156  return in;
157  }
158 
159  template <typename T> inline
161  {
162  return 0;
163  }
164 
165  template <> inline
167  {
168  // transparent color
169  return AimsRGBA( 0, 0, 0, 0 );
170  }
171 
172  // ---
173 
174  template <typename T> inline
176  * pal,
177  const T & mini,
178  const T & maxi )
179  : palette( pal )
180  {
181  setup( mini, maxi );
182  }
183 
184  template <typename T> inline
186  {
187  int ival0, ival1;
188  double fval0, fval1, val = static_cast<double>( in );
189 
190  // Comparisons are written this way to accommodate NaN and Inf
191  fval0 = scale0 * val + decal0;
192  if( fval0 > cmin0 && fval0 < cmax0 )
193  {
194  ival0 = static_cast<int>( fval0 );
195  }
196  else if( fval0 <= cmin0 )
197  ival0 = cmin0;
198  else if( fval0 >= cmax0 )
199  ival0 = cmax0;
200  else
201  ival0 = cmin0;
202 
203  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
204  colors->getSizeY() == 1 )
205  ival1 = 0 ;
206  else
207  {
208  fval1 = scale1 * val + decal1;
209  if( fval1 > cmin1 && fval1 < cmax1 )
210  {
211  ival1 = static_cast<int>( fval1 );
212  }
213  else if( fval1 <= cmin1 )
214  ival1 = cmin1;
215  else if( fval1 >= cmax1 )
216  ival1 = cmax1;
217  else
218  ival1 = cmin1;
219  }
220 
221  return colors->at( ival0, ival1 );
222  }
223 
224  template <typename T> inline
226  {
227  return 0;
228  }
229 
230  template <> inline
232  {
233  AimsRGBA col;
234 
235  int ival0, ival1;
236  float fval0, fval1, val = static_cast<float>( in.red() );
237 
238  fval0 = scale0 * val + decal0;
239  if( fval0 > cmin0 && fval0 < cmax0 )
240  {
241  ival0 = static_cast<int>( fval0 );
242  }
243  else if( fval0 <= cmin0 )
244  ival0 = cmin0;
245  else if( fval0 >= cmax0 )
246  ival0 = cmax0;
247  else
248  ival0 = cmin0;
249 
250  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
251  colors->getSizeY() == 1 )
252  ival1 = 0 ;
253  else
254  {
255  fval1 = scale1 * val + decal1;
256  if( fval1 > cmin1 && fval1 < cmax1 )
257  {
258  ival1 = static_cast<int>( fval1 );
259  }
260  else if( fval1 <= cmin1 )
261  ival1 = cmin1;
262  else if( fval1 >= cmax1 )
263  ival1 = cmax1;
264  else
265  ival1 = cmin1;
266  }
267 
268  col[0] = colors->at( ival0, ival1 )[0];
269 
270  val = static_cast<float>( in.green() );
271 
272  fval0 = scale0 * val + decal0;
273  if( fval0 > cmin0 && fval0 < cmax0 )
274  {
275  ival0 = static_cast<int>( fval0 );
276  }
277  else if( fval0 <= cmin0 )
278  ival0 = cmin0;
279  else if( fval0 >= cmax0 )
280  ival0 = cmax0;
281  else
282  ival0 = cmin0;
283 
284  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
285  colors->getSizeY() == 1 )
286  ival1 = 0 ;
287  else
288  {
289  fval1 = scale1 * val + decal1;
290  if( fval1 > cmin1 && fval1 < cmax1 ) {
291  ival1 = static_cast<int>( fval1 );
292  } else if( fval1 <= cmin1 )
293  ival1 = cmin1;
294  else if( fval1 >= cmax1 )
295  ival1 = cmax1;
296  else
297  ival1 = cmin1;
298  }
299 
300  col[1] = colors->at( ival0, ival1 )[1];
301 
302  val = static_cast<float>( in.blue() );
303 
304  fval0 = scale0 * val + decal0;
305  if( fval0 > cmin0 && fval0 < cmax0 )
306  {
307  ival0 = static_cast<int>( fval0 );
308  }
309  else if( fval0 <= cmin0 )
310  ival0 = cmin0;
311  else if( fval0 >= cmax0 )
312  ival0 = cmax0;
313  else
314  ival0 = cmin0;
315 
316  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
317  colors->getSizeY() == 1 )
318  ival1 = 0 ;
319  else
320  {
321  fval1 = scale1 * val + decal1;
322  if( fval1 > cmin1 && fval1 < cmax1 ) {
323  ival1 = static_cast<int>( fval1 );
324  } else if( fval1 <= cmin1 )
325  ival1 = cmin1;
326  else if( fval1 >= cmax1 )
327  ival1 = cmax1;
328  else
329  ival1 = cmin1;
330  }
331 
332  col[2] = colors->at( ival0, ival1 )[2];
333 
334  val = static_cast<float>( std::sqrt( in.red() * in.red()
335  + in.green() * in.green()
336  + in.blue() * in.blue() ) );
337 
338  fval0 = scale0 * val + decal0;
339  if( fval0 > cmin0 && fval0 < cmax0 ) {
340  ival0 = static_cast<int>( fval0 );
341  } else if( fval0 <= cmin0 )
342  ival0 = cmin0;
343  else if( fval0 >= cmax0 )
344  ival0 = cmax0;
345  else
346  ival0 = cmin0;
347 
348  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
349  colors->getSizeY() == 1 )
350  ival1 = 0 ;
351  else
352  {
353  fval1 = scale1 * val + decal1;
354  if( fval1 > cmin1 && fval1 < cmax1 ) {
355  ival1 = static_cast<int>( fval1 );
356  } else if( fval1 <= cmin1 )
357  ival1 = cmin1;
358  else if( fval1 >= cmax1 )
359  ival1 = cmax1;
360  else
361  ival1 = cmin1;
362  }
363 
364  col[3] = colors->at( ival0, ival1 )[3];
365 
366  return col;
367  }
368 
369 
370  template <> inline
372  const
373  {
374  AimsRGBA col;
375 
376  int ival0, ival1;
377  float fval0, fval1, val = static_cast<float>( in.red() );
378 
379  fval0 = scale0 * val + decal0;
380  if( fval0 > cmin0 && fval0 < cmax0 )
381  {
382  ival0 = static_cast<int>( fval0 );
383  }
384  else if( fval0 <= cmin0 )
385  ival0 = cmin0;
386  else if( fval0 >= cmax0 )
387  ival0 = cmax0;
388  else
389  ival0 = cmin0;
390 
391  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
392  colors->getSizeY() == 1 )
393  ival1 = 0 ;
394  else
395  {
396  fval1 = scale1 * val + decal1;
397  if( fval1 > cmin1 && fval1 < cmax1 )
398  {
399  ival1 = static_cast<int>( fval1 );
400  }
401  else if( fval1 <= cmin1 )
402  ival1 = cmin1;
403  else if( fval1 >= cmax1 )
404  ival1 = cmax1;
405  else
406  ival1 = cmin1;
407  }
408 
409  col[0] = colors->at( ival0, ival1 )[0];
410 
411  val = static_cast<float>( in.green() );
412 
413  fval0 = scale0 * val + decal0;
414  if( fval0 > cmin0 && fval0 < cmax0 )
415  {
416  ival0 = static_cast<int>( fval0 );
417  }
418  else if( fval0 <= cmin0 )
419  ival0 = cmin0;
420  else if( fval0 >= cmax0 )
421  ival0 = cmax0;
422  else
423  ival0 = cmin0;
424 
425  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
426  colors->getSizeY() == 1 )
427  ival1 = 0 ;
428  else
429  {
430  fval1 = scale1 * val + decal1;
431  if( fval1 > cmin1 && fval1 < cmax1 )
432  {
433  ival1 = static_cast<int>( fval1 );
434  }
435  else if( fval1 <= cmin1 )
436  ival1 = cmin1;
437  else if( fval1 >= cmax1 )
438  ival1 = cmax1;
439  else
440  ival1 = cmin1;
441  }
442 
443  col[1] = colors->at( ival0, ival1 )[1];
444 
445  val = static_cast<float>( in.blue() );
446 
447  fval0 = scale0 * val + decal0;
448  if( fval0 > cmin0 && fval0 < cmax0 )
449  {
450  ival0 = static_cast<int>( fval0 );
451  }
452  else if( fval0 <= cmin0 )
453  ival0 = cmin0;
454  else if( fval0 >= cmax0 )
455  ival0 = cmax0;
456  else
457  ival0 = cmin0;
458 
459  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
460  colors->getSizeY() == 1 )
461  ival1 = 0 ;
462  else
463  {
464  fval1 = scale1 * val + decal1;
465  if( fval1 > cmin1 && fval1 < cmax1 )
466  {
467  ival1 = static_cast<int>( fval1 );
468  }
469  else if( fval1 <= cmin1 )
470  ival1 = cmin1;
471  else if( fval1 >= cmax1 )
472  ival1 = cmax1;
473  else
474  ival1 = cmin1;
475  }
476 
477  col[2] = colors->at( ival0, ival1 )[2];
478 
479  val = static_cast<float>( in.alpha() );
480 
481  fval0 = scale0 * val + decal0;
482  if( fval0 > cmin0 && fval0 < cmax0 )
483  {
484  ival0 = static_cast<int>( fval0 );
485  }
486  else if( fval0 <= cmin0 )
487  ival0 = cmin0;
488  else if( fval0 >= cmax0 )
489  ival0 = cmax0;
490  else
491  ival0 = cmin0;
492 
493  if( palette->palette1DMapping() == AObjectPalette::FIRSTLINE ||
494  colors->getSizeY() == 1 )
495  ival1 = 0 ;
496  else
497  {
498  fval1 = scale1 * val + decal1;
499  if( fval1 > cmin1 && fval1 < cmax1 )
500  {
501  ival1 = static_cast<int>( fval1 );
502  }
503  else if( fval1 <= cmin1 )
504  ival1 = cmin1;
505  else if( fval1 >= cmax1 )
506  ival1 = cmax1;
507  else
508  ival1 = cmin1;
509  }
510 
511  col[3] = colors->at( ival0, ival1 )[3];
512 
513  return col;
514  }
515 
516 }
517 
518 #endif
AimsRGBA color(const T &) const
Definition: colortraits.h:153
ColorNoPaletteTraits(const AObjectPalette *, const T &mini, const T &maxi)
Definition: colortraits.h:147
void setup(const T &mini, const T &maxi)
AimsRGBA color(const T &) const
Definition: colortraits.h:185
ColorScalarPaletteTraits(const AObjectPalette *pal, const T &mini, const T &maxi)
Definition: colortraits.h:175
Converter value -> RGBA (high-level)
Definition: colortraits.h:95
T neutralColor() const
returns a black / transparent / zero color
Definition: colortraits.h:139
ColorTraits(const AObjectPalette *, const T &mini, const T &maxi)
Definition: colortraits.h:126
AimsRGBA color(const T &) const
Definition: colortraits.h:133
const uint8_t & green() const
const uint8_t & blue() const
const uint8_t & alpha() const
const uint8_t & red() const
const uint8_t & red() const
const uint8_t & blue() const
const uint8_t & green() const
switch to the right color traits type
Definition: colortraits.h:87
ColorScalarPaletteTraits< T > traitstype
Definition: colortraits.h:88