iLab Neuromorphic Robotics Toolkit  0.1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
PixelTypes.H
Go to the documentation of this file.
1 /*! @file
2  @author Randolph Voorhies
3  @copyright GNU Public License (GPL v3)
4  @section License
5  @verbatim
6  // ////////////////////////////////////////////////////////////////////////
7  // The iLab Neuromorphic Robotics Toolkit (NRT) //
8  // Copyright 2010-2012 by the University of Southern California (USC) //
9  // and the iLab at USC. //
10  // //
11  // iLab - University of Southern California //
12  // Hedco Neurociences Building, Room HNB-10 //
13  // Los Angeles, Ca 90089-2520 - USA //
14  // //
15  // See http://ilab.usc.edu for information about this project. //
16  // ////////////////////////////////////////////////////////////////////////
17  // This file is part of The iLab Neuromorphic Robotics Toolkit. //
18  // //
19  // The iLab Neuromorphic Robotics Toolkit is free software: you can //
20  // redistribute it and/or modify it under the terms of the GNU General //
21  // Public License as published by the Free Software Foundation, either //
22  // version 3 of the License, or (at your option) any later version. //
23  // //
24  // The iLab Neuromorphic Robotics Toolkit is distributed in the hope //
25  // that it will be useful, but WITHOUT ANY WARRANTY; without even the //
26  // implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR //
27  // PURPOSE. See the GNU General Public License for more details. //
28  // //
29  // You should have received a copy of the GNU General Public License //
30  // along with The iLab Neuromorphic Robotics Toolkit. If not, see //
31  // <http://www.gnu.org/licenses/>. //
32  // ////////////////////////////////////////////////////////////////////////
33  @endverbatim */
34 
35 
36 #ifndef INCLUDE_NRT_CORE_IMAGE_PIXELTYPES_H
37 #define INCLUDE_NRT_CORE_IMAGE_PIXELTYPES_H
38 
40 #include <nrt/Core/Debugging/Log.H>
41 #include <boost/lexical_cast.hpp>
42 #include <nrt/External/cereal/types/base_class.hpp>
43 
44 namespace nrt
45 {
46  // ######################################################################
47  //! A pixel class to hold red-green-blue color components
48  template <class T>
49  struct PixRGB : public PixelBase<T, 3, PixRGB>
50  {
51  template<class Q> struct rebind { typedef PixRGB<Q> type; };
52 
53  //! Default Constructor
54  /*! All components will be uninitialized */
55  PixRGB();
56 
57  //! Copy Constructor
58  template<class T2>
59  PixRGB(PixRGB<T2> const& other);
60 
61  //! initialize with a POD type or pixel
62  template <typename T1>
63  explicit PixRGB(T1 val);
64 
65  //! Value Constructor
66  /*! All components will be initialized to the given values */
67  PixRGB(T r, T g, T b);
68 
69  //! Clamping Value Constructor
70  /*! All components will be initialized to the given values and clamped/rounded if necessary */
71  template<class rType, class gType, class bType>
72  PixRGB(rType r, gType g, bType b);
73 
74  //! Read the red channel
75  T r() const;
76  //! Read the green channel
77  T g() const;
78  //! Read the blue channel
79  T b() const;
80 
81  //! Set the red channel
82  void setR(T value);
83  //! Set the green channel
84  void setG(T value);
85  //! Set the blue channel
86  void setB(T value);
87  //! Set the red channel and clamp/round if necessary
88  template<class T2> void setR(T2 value);
89  //! Set the green channel and clamp/round if necessary
90  template<class T2> void setG(T2 value);
91  //! Set the blue channel and clamp/round if necessary
92  template<class T2> void setB(T2 value);
93 
94  //! Convert this color space to RGB
95  PixRGB<T> toRGB() const;
96  //! Convert to this color space from RGB
97  static PixRGB<T> fromRGB(PixRGB<T> const & other);
98  };
99 
100  //! Stream out as PixRGB(r,g,b)
101  /*! \relates PixRGB */
102  template<class T>
103  inline std::ostream& operator<< (std::ostream &out, PixRGB<T> pix)
104  {
105  out << "PixRGB" << pix.toString();
106  return out;
107  }
108 
109  //! Stream in as a PixRGB(r,g,b)
110  template<class T>
111  inline typename std::enable_if<sizeof(T) != sizeof(nrt::byte), std::istream>::type &
112  operator>> (std::istream &in, PixRGB<T> & pix)
113  {
114  std::string stringRep; in >> stringRep;
115  std::vector<std::string> splitVec = nrt::splitString(stringRep, '(');
116 
117  // check parentheses
118  if(splitVec.size() != 2 || splitVec[0].compare("PixRGB") != 0 || *(splitVec[1].end() - 1) != ')')
120  (sformat("Could not parse PixRGB from [%s]",stringRep.c_str()).c_str());
121 
122  // erase trailing ')'
123  splitVec[1].erase(splitVec[1].end() - 1);
124 
125  // split numbers
126  std::vector<std::string> numVec = nrt::splitString(splitVec[1], ',');
127 
128  // ensure proper sizing
129  if(numVec.size() != 3)
131  (sformat("Could Not Parse PixRGB From [%s]: wrong number of arguments", stringRep.c_str()).c_str());
132 
133  // get numeric arguments
134  T col[3];
135  try {for(int i = 0; i < 3; i++) col[i] = boost::lexical_cast<T>(numVec[i]);}
136  catch (boost::bad_lexical_cast & e) {
138  (sformat("Could not parse numbers in PixRGB from [%s]",stringRep.c_str()).c_str());
139  }
140  pix = nrt::PixRGB<T>(col[0],col[1],col[2]);
141 
142  return in;
143  }
144 
145  template <class T>
146  inline typename std::enable_if<sizeof(T) == sizeof(nrt::byte), std::istream>::type &
147  operator>> (std::istream &in, PixRGB<T> & pix)
148  {
149  std::string stringRep; in >> stringRep;
150  std::vector<std::string> splitVec = nrt::splitString(stringRep, '(');
151 
152  // check parentheses
153  if(splitVec.size() != 2 || splitVec[0].compare("PixRGB") != 0 || *(splitVec[1].end() - 1) != ')')
155  (sformat("Could not parse PixRGB from [%s]",stringRep.c_str()).c_str());
156 
157  // erase trailing ')'
158  splitVec[1].erase(splitVec[1].end() - 1);
159 
160  // split numbers
161  std::vector<std::string> numVec = nrt::splitString(splitVec[1], ',');
162 
163  // ensure proper sizing
164  if(numVec.size() != 3)
166  (sformat("Could Not Parse PixRGB From [%s]: wrong number of arguments", stringRep.c_str()).c_str());
167 
168  // get numeric arguments
169  T col[3];
170 
171  // direct lexical cast to byte does not work
172  try {for(int i = 0; i < 3; i++) col[i] = nrt::clamped_convert<T>(boost::lexical_cast<int>(numVec[i]));}
173  catch (boost::bad_lexical_cast & e) {
175  (sformat("Could not parse numbers in PixRGB from [%s]",stringRep.c_str()).c_str());
176  }
177  pix = nrt::PixRGB<T>(col[0],col[1],col[2]);
178 
179  return in;
180  }
181 
182 
184 
185  // ######################################################################
186  //! A pixel class to hold hue-saturation-value color components
187  template <class T>
188  struct PixHSV : public PixelBase<T, 3, PixHSV>
189  {
190  template<class Q> struct rebind { typedef PixHSV<Q> type; };
191 
192  //! Default Constructor
193  /*! All components will be uninitialized */
194  PixHSV();
195 
196  //! Copy Constructor
197  template<class T2>
198  PixHSV(PixHSV<T2> const& other);
199 
200  //! initialize with a POD type or pixel
201  template <typename T1>
202  explicit PixHSV(T1 val);
203 
204  //! Value Constructor
205  /*! All components will be initialized to the given values */
206  PixHSV(T h, T s, T v);
207 
208  //! Clamping Value Constructor
209  /*! All components will be initialized to the given values and clamped/rounded if necessary */
210  template<class hType, class sType, class vType>
211  PixHSV(hType h, sType s, vType v);
212 
213  //! Read the hue channel
214  T h() const;
215  //! Read the saturation channel
216  T s() const;
217  //! Read the value channel
218  T v() const;
219 
220  //! Set the hue channel
221  void setH(T value);
222  //! Set the saturation channel
223  void setS(T value);
224  //! Set the value channel
225  void setV(T value);
226  //! Set the hue channel and clamp/round if necessary
227  template<class T2> void setH(T2 value);
228  //! Set the saturation channel and clamp/round if necessary
229  template<class T2> void setS(T2 value);
230  //! Set the value channel and clamp/round if necessary
231  template<class T2> void setV(T2 value);
232 
233  //! Convert this color space to RGB
234  PixRGB<T> toRGB() const;
235  //! Convert to this color space from RGB
236  static PixHSV<T> fromRGB(PixRGB<T> const & other);
237  };
239 
240  //! Stream out as PixHSV(h,s,v)
241  /*! \relates PixHSV */
242  template<class T>
243  inline std::ostream& operator<< (std::ostream &out, PixHSV<T> pix)
244  {
245  out << "PixHSV" << pix.toString();
246  return out;
247  }
248 
249  // ######################################################################
250  //! A pixel class to hold a single scalar value
251  template <class T>
252  struct PixGray : public PixelBase<T, 1, PixGray>
253  {
254  template<class Q> struct rebind { typedef PixGray<Q> type; };
255 
256  //! Default Constructor
257  /*! All components will be uninitialized */
258  PixGray();
259 
260  //! Copy Constructor
261  template<class T2>
262  PixGray(PixGray<T2> const& other);
263 
264  //! initialize with a POD type or pixel, we'll let this one be no explicit
265  template <typename T1>
266  PixGray(T1 val);
267 
268  //! Read the value channel
269  T val() const;
270 
271  //! Set the hue channel
272  void set(T value);
273  //! Set the hue channel and clamp/round if necessary
274  template<class T2> void set(T2 value);
275 
276  //! Convert this color space to RGB
277  PixRGB<T> toRGB() const;
278  //! Convert to this color space from RGB
279  static PixGray<T> fromRGB(PixRGB<T> const & other);
280  };
282 
283  //! Stream out as PixGray(v)
284  /*! \relates PixGray */
285  template<class T>
286  inline std::ostream& operator<< (std::ostream &out, PixGray<T> pix)
287  {
288  out << "PixGray" << pix.toString();
289  return out;
290  }
291 
292  // ######################################################################
293  //! A pixel class to hold red-green-blue-alpha color components
294  template <class T>
295  struct PixRGBA : public PixRGB<T>, public PixelWithAlpha<T>
296  {
297 
298  template<class Q> struct rebind { typedef PixRGBA<Q> type; };
299  template<class Q, class R> struct rebind_extra { typedef PixRGBA<Q> type; };
300 
301  typedef PixRGB<T> BaseType;
302  typedef PixelWithAlpha<T> ExtraType;
303 
304  //! Default Constructor
305  /*! All components will be uninitialized */
306  PixRGBA();
307 
308  //! Copy Constructor
309  template<class T2>
310  PixRGBA(PixRGBA<T2> const& other);
311 
312  //! initialize with a POD type or pixel
313  template <typename T1>
314  explicit PixRGBA(T1 val);
315 
316  //! Value Constructor
317  /*! All components will be initialized to the given values */
318  PixRGBA(T r, T g, T b, T a);
319 
320  //! Clamping Value Constructor
321  /*! All components will be initialized to the given values and clamped/rounded if necessary */
322  template<class rType, class gType, class bType, class aType>
323  PixRGBA(rType r, gType g, bType b, aType a);
324 
325  //! Read the red channel
326  T r() const;
327  //! Read the green channel
328  T g() const;
329  //! Read the blue channel
330  T b() const;
331  //! Read the alpha channel
332  T a() const;
333 
334  //! Set the red channel
335  void setR(T value);
336  //! Set the green channel
337  void setG(T value);
338  //! Set the blue channel
339  void setB(T value);
340  //! Set the alpha channel
341  void setA(T value);
342  //! Set the red channel and clamp/round if necessary
343  template<class T2> void setR(T2 value);
344  //! Set the green channel and clamp/round if necessary
345  template<class T2> void setG(T2 value);
346  //! Set the blue channel and clamp/round if necessary
347  template<class T2> void setB(T2 value);
348  //! Set the alpha channel and clamp/round if necessary
349  template<class T2> void setA(T2 value);
350 
351  //! Convenience function to print out the values as a nicely formatted string
352  std::string toString();
353 
354  //! Convert this color space to RGB
355  PixRGB<T> toRGB() const;
356  //! Convert to this color space from RGB
357  static PixRGBA<T> fromRGB(PixRGB<T> const & other);
358 
359  //! Serialization
360  template <class Archive> void serialize(Archive & ar)
361  {
362  ar( cereal::base_class<PixRGB<T> >( this ) );
363  ar( cereal::base_class<PixelWithAlpha<T> >( this ) );
364  }
365  };
367 
368  //! Stream out as PixRGBA(r,g,b,a)
369  /*! \relates PixRGBA */
370  template<class T>
371  inline std::ostream& operator<< (std::ostream &out, PixRGBA<T> pix)
372  {
373  out << "PixRGBA" << pix.toString();
374  return out;
375  }
376 
377  //! Stream in as a PixRGBA(r,g,b,a)
378  template<class T>
379  inline typename std::enable_if<sizeof(T) != sizeof(nrt::byte), std::istream>::type &
380  operator>> (std::istream &in, PixRGBA<T> & pix)
381  {
382  std::string stringRep; in >> stringRep;
383  std::vector<std::string> splitVec = nrt::splitString(stringRep, '(');
384 
385  // check parentheses
386  if(splitVec.size() != 2 || splitVec[0].compare("PixRGBA") != 0 || *(splitVec[1].end() - 1) != ')')
388  (sformat("Could not parse PixRGBA from [%s]",stringRep.c_str()).c_str());
389 
390  // erase trailing ')'
391  splitVec[1].erase(splitVec[1].end() - 1);
392 
393  // split numbers
394  std::vector<std::string> numVec = nrt::splitString(splitVec[1], ',');
395 
396  // ensure proper sizing
397  if(numVec.size() != 4)
399  (sformat("Could Not Parse PixRGBA From [%s]: wrong number of arguments", stringRep.c_str()).c_str());
400 
401  // get numeric arguments
402  T col[4];
403  try {for(int i = 0; i < 4; i++) col[i] = boost::lexical_cast<T>(numVec[i]);}
404  catch (boost::bad_lexical_cast & e) {
406  (sformat("Could not parse numbers in PixRGBA from [%s]",stringRep.c_str()).c_str());
407  }
408  pix = nrt::PixRGBA<T>(col[0],col[1],col[2],col[3]);
409 
410  return in;
411  }
412 
413  // ######################################################################
414  //! A pixel class to hold red-green-blue-depth color components and depth information
415  template <class T_rgb, class T_d>
416  struct PixRGBD : public PixRGB<T_rgb>, public PixelWithDepth<T_d>
417  {
418  template<class Q> struct rebind { typedef PixRGBD<Q, T_d> type; };
419  template<class Q, class R> struct rebind_extra { typedef PixRGBD<Q, R> type; };
420 
421  typedef PixRGB<T_rgb> BaseType;
422  typedef PixelWithDepth<T_d> ExtraType;
423 
424  //! Default Constructor
425  /*! All components will be uninitialized */
426  PixRGBD();
427 
428  //! Copy Constructor
429  template<class T_rgb2, class T_d2>
430  PixRGBD(PixRGBD<T_rgb2, T_d2> const& other);
431 
432  //! initialize with a POD type or pixel
433  template <typename T1>
434  explicit PixRGBD(T1 val);
435 
436  //! Construct from a PixRGB and a depth
437  PixRGBD(PixRGB<T_rgb> const & rgb, T_d depth);
438 
439  //! Value Constructor
440  /*! All components will be initialized to the given values */
441  PixRGBD(T_rgb r, T_rgb g, T_rgb b, T_d d);
442 
443  //! Clamping Value Constructor
444  /*! All components will be initialized to the given values and clamped/rounded if necessary */
445  template<class rType, class gType, class bType, class dType>
446  PixRGBD(rType r, gType g, bType b, dType d);
447 
448  //! Get just the RGB component
449  PixRGB<T_rgb> & rgb();
450 
451  //! Get just the RGB component
452  PixRGB<T_rgb> const & rgb() const;
453 
454  //! Convert this color space to RGB
455  PixRGB<T_rgb> toRGB() const;
456  //! Convert to this color space from RGB
457  static PixRGBD<T_rgb, T_d> fromRGB(PixRGB<T_rgb> const & other);
458 
459  //! Serialization
460  template <class Archive> void serialize(Archive & ar)
461  {
462  ar( cereal::base_class<PixRGB<T_rgb> >( this ) );
463  ar( cereal::base_class<PixelWithDepth<T_d> >( this ) );
464  }
465  };
467 
468  //! Stream out as PixRGBD(r,g,b,d)
469  /*! \relates PixRGBD */
470  template<class T_rgb, class T_d>
471  std::ostream& operator<< (std::ostream &out, PixRGBD<T_rgb, T_d> pix);
472 
473 }
474 
475 #endif // INCLUDE_NRT_CORE_IMAGE_PIXELTYPES_H
476