[ VIGRA Homepage | Class Index | Function Index | File Index | Main Page ]

details vigra/rgbvalue.hxx VIGRA

00001 /************************************************************************/
00002 /*                                                                      */
00003 /*               Copyright 1998-2002 by Ullrich Koethe                  */
00004 /*       Cognitive Systems Group, University of Hamburg, Germany        */
00005 /*                                                                      */
00006 /*    This file is part of the VIGRA computer vision library.           */
00007 /*    ( Version 1.3.2, Jan 27 2005 )                                    */
00008 /*    You may use, modify, and distribute this software according       */
00009 /*    to the terms stated in the LICENSE file included in               */
00010 /*    the VIGRA distribution.                                           */
00011 /*                                                                      */
00012 /*    The VIGRA Website is                                              */
00013 /*        http://kogs-www.informatik.uni-hamburg.de/~koethe/vigra/      */
00014 /*    Please direct questions, bug reports, and contributions to        */
00015 /*        koethe@informatik.uni-hamburg.de                              */
00016 /*                                                                      */
00017 /*  THIS SOFTWARE IS PROVIDED AS IS AND WITHOUT ANY EXPRESS OR          */
00018 /*  IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED      */
00019 /*  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. */
00020 /*                                                                      */
00021 /************************************************************************/
00022 
00023 
00024 #ifndef VIGRA_RGBVALUE_HXX
00025 #define VIGRA_RGBVALUE_HXX
00026 
00027 #include <cmath>    // abs(double)
00028 #include <cstdlib>  // abs(int)
00029 #include "vigra/config.hxx"
00030 #include "vigra/numerictraits.hxx"
00031 #include "vigra/accessor.hxx"
00032 #include "vigra/tinyvector.hxx"
00033 
00034 namespace vigra {
00035 
00036 /********************************************************/
00037 /*                                                      */
00038 /*                      RGBValue                        */
00039 /*                                                      */
00040 /********************************************************/
00041 
00042 /** \brief Class for a single RGB value.
00043 
00044     This class contains three values (of the specified type) that represent
00045     red, green, and blue color channels. There are three possibilities
00046     to access these values: accessor functions (\ref red(), \ref green(),
00047     \ref blue()), index operator (operator[](dx), where 0 is red,
00048     1 is green and 2 is blue) and iterator (STL-compatible random access
00049     iterator that references the three colors in turn). The latter two
00050     methods, together with the necessary embedded typedefs, ensure
00051     compatibility of a RGBValue with a STL vector.
00052 
00053     \ref RGBValueOperators "Arithmetic operations" are defined as component-wise applications of these
00054     operations. Addition, subtraction, and multiplication of two RGBValues
00055     (+=, -=, *=, +, -, *, unary -), multiplication and division of an
00056     RGBValue with a double, and NumericTraits/PromoteTraits are defined,
00057     so that RGBValue fulfills the requirements of a \ref LinearAlgebra.
00058 
00059     A number of \ref RGBValueAccessors "accessors" are provided
00060     that support access to RGBValues as a whole, to a selected
00061     color component, or to the luminance value.
00062 
00063     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00064     Namespace: vigra
00065 */
00066 template <class VALUETYPE>
00067 class RGBValue
00068 : public TinyVector<VALUETYPE, 3>
00069 {
00070     typedef TinyVector<VALUETYPE, 3> Base;
00071   public:
00072         /** STL-compatible definition of valuetype
00073         */
00074     typedef VALUETYPE value_type;
00075         /** STL-compatible definition of iterator
00076         */
00077     typedef typename TinyVector<VALUETYPE, 3>::iterator iterator;
00078         /** STL-compatible definition of const iterator
00079         */
00080     typedef typename TinyVector<VALUETYPE, 3>::const_iterator const_iterator;
00081 
00082         /** Construct from explicit color values
00083         */
00084     RGBValue(value_type red, value_type green, value_type blue)
00085     : Base(red, green, blue)
00086     {}
00087 
00088         /** Construct gray value
00089         */
00090     RGBValue(value_type gray)
00091     : Base(gray, gray, gray)
00092     {}
00093 
00094         /** Construct from another sequence (must have length 3!)
00095         */
00096     template <class Iterator>
00097     RGBValue(Iterator i, Iterator end)
00098     : Base(i[0], i[1], i[2])
00099     {}
00100 
00101         /** Default constructor (sets all components to 0)
00102         */
00103     RGBValue()
00104     : Base(0, 0, 0)
00105     {}
00106 
00107 #if !defined(TEMPLATE_COPY_CONSTRUCTOR_BUG)
00108 
00109     RGBValue(RGBValue const & r)
00110     : Base(r)
00111     {}
00112 
00113     RGBValue & operator=(RGBValue const & r)
00114     {
00115         Base::operator=(r);
00116         return *this;
00117     }
00118 
00119 #endif // TEMPLATE_COPY_CONSTRUCTOR_BUG
00120 
00121 
00122         /** Copy constructor.
00123         */
00124     template <class U>
00125     RGBValue(RGBValue<U> const & r)
00126     : Base(r)
00127     {}
00128 
00129         /** Copy assignment.
00130         */
00131     template <class U>
00132     RGBValue & operator=(RGBValue<U> const & r)
00133     {
00134         Base::operator=(r);
00135         return *this;
00136     }
00137 
00138         /** construct from TinyVector
00139         */
00140     RGBValue(TinyVector<value_type, 3> const & r)
00141     : Base(r)
00142     {}
00143 
00144         /** assign TinyVector.
00145         */
00146     RGBValue & operator=(TinyVector<value_type, 3> const & r)
00147     {
00148         Base::operator=(r);
00149         return *this;
00150     }
00151 
00152         /** Unary negation (construct RGBValue with negative values)
00153         */
00154     RGBValue operator-() const
00155     {
00156         return RGBValue(-red(), -green(), -blue());
00157     }
00158 
00159         /** Access red component.
00160         */
00161     value_type & red() { return (*this)[0]; }
00162 
00163         /** Access green component.
00164         */
00165     value_type & green() { return (*this)[1]; }
00166 
00167         /** Access blue component.
00168         */
00169     value_type & blue() { return (*this)[2]; }
00170 
00171         /** Get red component.
00172         */
00173     value_type const & red() const { return (*this)[0]; }
00174 
00175         /** Get green component.
00176         */
00177     value_type const & green() const { return (*this)[1]; }
00178 
00179         /** Get blue component.
00180         */
00181     value_type const & blue() const { return (*this)[2]; }
00182 
00183         /** Calculate luminance.
00184         */
00185     value_type luminance() const {
00186          return detail::RequiresExplicitCast<value_type>::cast(0.3*red() + 0.59*green() + 0.11*blue()); }
00187 
00188         /** Calculate magnitude.
00189         */
00190     typename NumericTraits<VALUETYPE>::RealPromote
00191     magnitude() const {
00192          return VIGRA_CSTD::sqrt(
00193             (typename NumericTraits<VALUETYPE>::RealPromote)squaredMagnitude());
00194     }
00195 
00196         /** Calculate squared magnitude.
00197         */
00198     typename NumericTraits<VALUETYPE>::Promote
00199     squaredMagnitude() const {
00200          return red()*red() + green()*green() + blue()*blue();
00201     }
00202 
00203         /** Set red component. The type <TT>V</TT> of the passed
00204             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
00205         */
00206     template <class V>
00207     void setRed(V value) { (*this)[0] = detail::RequiresExplicitCast<value_type>::cast(value); }
00208 
00209         /** Set green component.The type <TT>V</TT> of the passed
00210             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
00211         */
00212     template <class V>
00213     void setGreen(V value) { (*this)[1] = detail::RequiresExplicitCast<value_type>::cast(value); }
00214 
00215         /** Set blue component.The type <TT>V</TT> of the passed
00216             in <TT>value</TT> is automatically converted to <TT>VALUETYPE</TT>.
00217         */
00218     template <class V>
00219     void setBlue(V value) { (*this)[2] = detail::RequiresExplicitCast<value_type>::cast(value); }
00220 
00221 
00222     template <class V>
00223     void setRGB(V r, V g, V b) 
00224     { 
00225         (*this)[0] = detail::RequiresExplicitCast<value_type>::cast(r); 
00226         (*this)[1] = detail::RequiresExplicitCast<value_type>::cast(g); 
00227         (*this)[2] = detail::RequiresExplicitCast<value_type>::cast(b); 
00228     }
00229 };
00230 
00231 /********************************************************/
00232 /*                                                      */
00233 /*                     RGBValue Comparison              */
00234 /*                                                      */
00235 /********************************************************/
00236 
00237 /** \addtogroup RGBValueOperators Functions for RGBValue
00238 
00239     \brief <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>
00240 
00241     These functions fulfill the requirements of a Linear Algebra.
00242     Return types are determined according to \ref RGBValueTraits.
00243 
00244     Namespace: vigra
00245     <p>
00246 
00247  */
00248 //@{
00249     /// component-wise equal
00250 template <class V1, class V2>
00251 inline
00252 bool
00253 operator==(RGBValue<V1> const & l, RGBValue<V2> const & r)
00254 {
00255     return (l.red() == r.red()) &&
00256        (l.green() == r.green()) &&
00257        (l.blue() == r.blue());
00258 }
00259 
00260     /// component-wise not equal
00261 template <class V1, class V2>
00262 inline
00263 bool
00264 operator!=(RGBValue<V1> const & l, RGBValue<V2> const & r)
00265 {
00266     return (l.red() != r.red()) ||
00267        (l.green() != r.green()) ||
00268        (l.blue() != r.blue());
00269 }
00270 
00271 
00272 //@}
00273 
00274 /********************************************************/
00275 /*                                                      */
00276 /*                      RGBValue-Traits                 */
00277 /*                                                      */
00278 /********************************************************/
00279 
00280 /** \page RGBValueTraits Numeric and Promote Traits of RGBValue
00281     The numeric and promote traits for RGBValues follow
00282     the general specifications for \ref NumericPromotionTraits.
00283     They are implemented in terms of the traits of the basic types by
00284     partial template specialization:
00285 
00286     \code
00287 
00288     template <class T>
00289     struct NumericTraits<RGBValue<T> >
00290     {
00291         typedef RGBValue<typename NumericTraits<T>::Promote> Promote;
00292         typedef RGBValue<typename NumericTraits<T>::RealPromote> RealPromote;
00293 
00294         typedef typename NumericTraits<T>::isIntegral isIntegral;
00295         typedef VigraFalseType isScalar;
00296 
00297         // etc.
00298     };
00299 
00300     template <class T1, class T2>
00301     struct PromoteTraits<RGBValue<T1>, RGBValue<T2> >
00302     {
00303         typedef RGBValue<typename PromoteTraits<T1, T2>::Promote> Promote;
00304     };
00305     \endcode
00306 
00307     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00308     Namespace: vigra
00309 
00310 */
00311 
00312 #if !defined(NO_PARTIAL_TEMPLATE_SPECIALIZATION)
00313 
00314 template <class T>
00315 struct NumericTraits<RGBValue<T> >
00316 {
00317     typedef RGBValue<T> Type;
00318     typedef RGBValue<typename NumericTraits<T>::Promote> Promote;
00319     typedef RGBValue<typename NumericTraits<T>::RealPromote> RealPromote;
00320     typedef RGBValue<typename NumericTraits<T>::ComplexPromote> ComplexPromote;
00321     typedef T ValueType; 
00322     
00323     typedef typename NumericTraits<T>::isIntegral isIntegral; 
00324     typedef VigraFalseType isScalar; 
00325     typedef VigraFalseType isOrdered;
00326     typedef VigraFalseType isComplex; 
00327 
00328     static RGBValue<T> zero() {
00329         return RGBValue<T>(NumericTraits<T>::zero());
00330     }
00331     static RGBValue<T> one() {
00332         return RGBValue<T>(NumericTraits<T>::one());
00333     }
00334     static RGBValue<T> nonZero() {
00335         return RGBValue<T>(NumericTraits<T>::nonZero());
00336     }
00337 
00338     static Promote toPromote(RGBValue<T> const & v) {
00339         return Promote(v);
00340     }
00341     static RealPromote toRealPromote(RGBValue<T> const & v) {
00342         return RealPromote(v);
00343     }
00344     static RGBValue<T> fromPromote(Promote const & v) {
00345         return RGBValue<T>(NumericTraits<T>::fromPromote(v.red()),
00346                            NumericTraits<T>::fromPromote(v.green()),
00347                            NumericTraits<T>::fromPromote(v.blue()));
00348     }
00349     static RGBValue<T> fromRealPromote(RealPromote const & v) {
00350         return RGBValue<T>(NumericTraits<T>::fromRealPromote(v.red()),
00351                            NumericTraits<T>::fromRealPromote(v.green()),
00352                            NumericTraits<T>::fromRealPromote(v.blue()));
00353     }
00354 };
00355 
00356 template <class T1, class T2>
00357 struct PromoteTraits<RGBValue<T1>, RGBValue<T2> >
00358 {
00359     typedef RGBValue<typename PromoteTraits<T1, T2>::Promote> Promote;
00360 };
00361 
00362 template <class T>
00363 struct PromoteTraits<RGBValue<T>, double >
00364 {
00365     typedef RGBValue<typename NumericTraits<T>::RealPromote> Promote;
00366 };
00367 
00368 template <class T>
00369 struct PromoteTraits<double, RGBValue<T> >
00370 {
00371     typedef RGBValue<typename NumericTraits<T>::RealPromote> Promote;
00372 };
00373 
00374 #else // NO_PARTIAL_TEMPLATE_SPECIALIZATION
00375 
00376 #define RGBVALUE_NUMTRAITS(T) \
00377 template<>\
00378 struct NumericTraits<RGBValue<T> >\
00379 {\
00380     typedef RGBValue<T> Type; \
00381     typedef RGBValue<NumericTraits<T>::Promote> Promote; \
00382     typedef RGBValue<NumericTraits<T>::RealPromote> RealPromote; \
00383     typedef RGBValue<NumericTraits<T>::ComplexPromote> ComplexPromote; \
00384     typedef T ValueType; \
00385     \
00386     typedef NumericTraits<T>::isIntegral isIntegral; \
00387     typedef VigraFalseType isScalar; \
00388     typedef VigraFalseType isOrdered; \
00389     typedef VigraFalseType isComplex; \
00390     \
00391     static RGBValue<T> zero() { \
00392         return RGBValue<T>(NumericTraits<T>::zero()); \
00393     }\
00394     static RGBValue<T> one() { \
00395         return RGBValue<T>(NumericTraits<T>::one()); \
00396     }\
00397     static RGBValue<T> nonZero() { \
00398         return RGBValue<T>(NumericTraits<T>::nonZero()); \
00399     }\
00400     \
00401     static Promote toPromote(RGBValue<T> const & v) { \
00402         return Promote(v); \
00403     }\
00404     static RealPromote toRealPromote(RGBValue<T> const & v) { \
00405         return RealPromote(v); \
00406     }\
00407     static RGBValue<T> fromPromote(Promote const & v) { \
00408         RGBValue<T> res;\
00409         RGBValue<T>::iterator d = res.begin();\
00410         Promote::const_iterator s = v.begin();\
00411         for(; d != res.end(); ++d, ++s)\
00412             *d = NumericTraits<T>::fromPromote(*s);\
00413         return res;\
00414     }\
00415     static RGBValue<T> fromRealPromote(RealPromote const & v) {\
00416         RGBValue<T> res;\
00417         RGBValue<T>::iterator d = res.begin();\
00418         RealPromote::const_iterator s = v.begin();\
00419         for(; d != res.end(); ++d, ++s)\
00420             *d = NumericTraits<T>::fromRealPromote(*s);\
00421         return res;\
00422     }\
00423 };
00424 
00425 #define RGBVALUE_PROMTRAITS1(type1) \
00426 template<> \
00427 struct PromoteTraits<RGBValue<type1>, RGBValue<type1> > \
00428 { \
00429     typedef RGBValue<PromoteTraits<type1, type1>::Promote> Promote; \
00430     static Promote toPromote(RGBValue<type1> const & v) { \
00431         return static_cast<Promote>(v); } \
00432 };
00433 
00434 #define RGBVALUE_PROMTRAITS2(type1, type2) \
00435 template<> \
00436 struct PromoteTraits<RGBValue<type1>, RGBValue<type2> > \
00437 { \
00438     typedef RGBValue<PromoteTraits<type1, type2>::Promote> Promote; \
00439     static Promote toPromote(RGBValue<type1> const & v) { \
00440         return static_cast<Promote>(v); } \
00441     static Promote toPromote(RGBValue<type2> const & v) { \
00442         return static_cast<Promote>(v); } \
00443 };
00444 
00445 RGBVALUE_NUMTRAITS(unsigned char)
00446 RGBVALUE_NUMTRAITS(int)
00447 RGBVALUE_NUMTRAITS(float)
00448 RGBVALUE_NUMTRAITS(double)
00449 RGBVALUE_PROMTRAITS1(unsigned char)
00450 RGBVALUE_PROMTRAITS1(int)
00451 RGBVALUE_PROMTRAITS1(float)
00452 RGBVALUE_PROMTRAITS1(double)
00453 RGBVALUE_PROMTRAITS2(float, unsigned char)
00454 RGBVALUE_PROMTRAITS2(unsigned char, float)
00455 RGBVALUE_PROMTRAITS2(int, unsigned char)
00456 RGBVALUE_PROMTRAITS2(unsigned char, int)
00457 RGBVALUE_PROMTRAITS2(int, float)
00458 RGBVALUE_PROMTRAITS2(float, int)
00459 RGBVALUE_PROMTRAITS2(double, unsigned char)
00460 RGBVALUE_PROMTRAITS2(unsigned char, double)
00461 RGBVALUE_PROMTRAITS2(int, double)
00462 RGBVALUE_PROMTRAITS2(double, int)
00463 RGBVALUE_PROMTRAITS2(double, float)
00464 RGBVALUE_PROMTRAITS2(float, double)
00465 
00466 #undef RGBVALUE_NUMTRAITS
00467 #undef RGBVALUE_PROMTRAITS1
00468 #undef RGBVALUE_PROMTRAITS2
00469 
00470 #endif // NO_PARTIAL_TEMPLATE_SPECIALIZATION
00471 
00472 
00473 /********************************************************/
00474 /*                                                      */
00475 /*                      RGBValue-Arithmetic             */
00476 /*                                                      */
00477 /********************************************************/
00478 
00479 /** \addtogroup RGBValueOperators
00480  */
00481 //@{
00482     /// componentwise add-assignment
00483 template <class V1, class V2>
00484 inline
00485 RGBValue<V1> &
00486 operator+=(RGBValue<V1> & l, RGBValue<V2> const & r)
00487 {
00488     l.red() += r.red();
00489     l.green() += r.green();
00490     l.blue() += r.blue();
00491     return l;
00492 }
00493 
00494     /// componentwise subtract-assignment
00495 template <class V1, class V2>
00496 inline
00497 RGBValue<V1> &
00498 operator-=(RGBValue<V1> & l, RGBValue<V2> const & r)
00499 {
00500     l.red() -= r.red();
00501     l.green() -= r.green();
00502     l.blue() -= r.blue();
00503     return l;
00504 }
00505 
00506     /// componentwise multiply-assignment
00507 template <class V1, class V2>
00508 inline
00509 RGBValue<V1> &
00510 operator*=(RGBValue<V1> & l, RGBValue<V2> const & r)
00511 {
00512     l.red() *= r.red();
00513     l.green() *= r.green();
00514     l.blue() *= r.blue();
00515     return l;
00516 }
00517 
00518     /// componentwise scalar multiply-assignment
00519 template <class V>
00520 inline
00521 RGBValue<V> &
00522 operator*=(RGBValue<V> & l, double r)
00523 {
00524     l.red() *= r;
00525     l.green() *= r;
00526     l.blue() *= r;
00527     return l;
00528 }
00529 
00530     /// componentwise scalar divide-assignment
00531 template <class V>
00532 inline
00533 RGBValue<V> &
00534 operator/=(RGBValue<V> & l, double r)
00535 {
00536     l.red() /= r;
00537     l.green() /= r;
00538     l.blue() /= r;
00539     return l;
00540 }
00541 
00542 using VIGRA_CSTD::abs;
00543 
00544     /// component-wise absolute value
00545 template <class T>
00546 inline
00547 RGBValue<T> abs(RGBValue<T> const & v) {
00548     return RGBValue<T>(abs(v.red()), abs(v.green()),  abs(v.blue()));
00549 }
00550 
00551 
00552 
00553     /// component-wise addition
00554 template <class V1, class V2>
00555 inline
00556 typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote
00557 operator+(RGBValue<V1> const & r1, RGBValue<V2> const & r2)
00558 {
00559     typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote res(r1);
00560 
00561     res += r2;
00562 
00563     return res;
00564 }
00565 
00566     /// component-wise subtraction
00567 template <class V1, class V2>
00568 inline
00569 typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote
00570 operator-(RGBValue<V1> const & r1, RGBValue<V2> const & r2)
00571 {
00572     typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote res(r1);
00573 
00574     res -= r2;
00575 
00576     return res;
00577 }
00578 
00579     /// component-wise multiplication
00580 template <class V1, class V2>
00581 inline
00582 typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote
00583 operator*(RGBValue<V1> const & r1, RGBValue<V2> const & r2)
00584 {
00585     typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote res(r1);
00586 
00587     res *= r2;
00588 
00589     return res;
00590 }
00591 
00592     /// component-wise left scalar multiplication
00593 template <class V>
00594 inline
00595 typename NumericTraits<RGBValue<V> >::RealPromote
00596 operator*(double v, RGBValue<V> const & r)
00597 {
00598     typename NumericTraits<RGBValue<V> >::RealPromote res(r);
00599 
00600     res *= v;
00601 
00602     return res;
00603 }
00604 
00605     /// component-wise right scalar multiplication
00606 template <class V>
00607 inline
00608 typename NumericTraits<RGBValue<V> >::RealPromote
00609 operator*(RGBValue<V> const & r, double v)
00610 {
00611     typename NumericTraits<RGBValue<V> >::RealPromote res(r);
00612 
00613     res *= v;
00614 
00615     return res;
00616 }
00617 
00618     /// component-wise scalar division
00619 template <class V>
00620 inline
00621 typename NumericTraits<RGBValue<V> >::RealPromote
00622 operator/(RGBValue<V> const & r, double v)
00623 {
00624     typename NumericTraits<RGBValue<V> >::RealPromote res(r);
00625 
00626     res /= v;
00627 
00628     return res;
00629 }
00630 
00631     /// cross product
00632 template <class V1, class V2>
00633 inline
00634 typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote
00635 cross(RGBValue<V1> const & r1, RGBValue<V2> const & r2)
00636 {
00637     typedef typename PromoteTraits<RGBValue<V1>, RGBValue<V2> >::Promote
00638             Res;
00639     return  Res(r1.green()*r2.blue() - r1.blue()*r2.green(),
00640                 r1.blue()*r2.red() - r1.red()*r2.blue(),
00641                 r1.red()*r2.green() - r1.green()*r2.red());
00642 }
00643 
00644     /// dot product
00645 template <class V1, class V2>
00646 inline
00647 typename PromoteTraits<V1, V2>::Promote
00648 dot(RGBValue<V1> const & r1, RGBValue<V2> const & r2)
00649 {
00650     return r1.red()*r2.red() + r1.green()*r2.green() + r1.blue()*r2.blue();
00651 }
00652 
00653 using VIGRA_CSTD::ceil;
00654 
00655     /** Apply ceil() function to each RGB component.
00656     */
00657 template <class V>
00658 inline
00659 RGBValue<V>
00660 ceil(RGBValue<V> const & r)
00661 {
00662     return RGBValue<V>(ceil(r.red()),
00663                        ceil(r.green()),
00664                        ceil(r.blue()));
00665 }
00666 
00667 using VIGRA_CSTD::floor;
00668 
00669     /** Apply floor() function to each RGB component.
00670     */
00671 template <class V>
00672 inline
00673 RGBValue<V>
00674 floor(RGBValue<V> const & r)
00675 {
00676     return RGBValue<V>(floor(r.red()),
00677                        floor(r.green()),
00678                        floor(r.blue()));
00679 }
00680 
00681 //@}
00682 
00683 /********************************************************/
00684 /*                                                      */
00685 /*                      RGBValue-Accessors              */
00686 /*                                                      */
00687 /********************************************************/
00688 
00689 /** \addtogroup DataAccessors
00690 */
00691 //@{
00692 /** \defgroup RGBValueAccessors Accessors for RGBValue */
00693 //@{
00694     /** Encapsulate access to rgb values.
00695 
00696     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00697     Namespace: vigra
00698     */
00699 template <class RGBVALUE>
00700 class RGBAccessor
00701 : public VectorAccessor<RGBVALUE>
00702 {
00703   public:
00704 
00705     typedef typename RGBVALUE::value_type component_type;
00706 
00707         /** Get value of the red component
00708         */
00709     template <class RGBIterator>
00710     component_type const & red(RGBIterator const & rgb) const
00711     {
00712         return (*rgb).red();
00713     }
00714 
00715     template <class V, class RGBIterator>
00716     void setRGB(V r, V g, V b, RGBIterator const & rgb) const
00717     {
00718         (*rgb).setRGB( r, g, b );
00719     }
00720 
00721     
00722         /** Set value of the red component. The type <TT>V</TT> of the passed
00723             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00724         */
00725     template <class V, class RGBIterator>
00726     void setRed(V value, RGBIterator const & rgb) const
00727     {
00728         (*rgb).setRed(value);
00729     }
00730 
00731         /** Get value of the red component at an offset
00732         */
00733     template <class RGBIterator, class DIFFERENCE>
00734     component_type const & red(RGBIterator const & rgb, DIFFERENCE diff) const
00735     {
00736         return rgb[diff].red();
00737     }
00738 
00739         /** Set value of the red component at an offset. The type <TT>V</TT> of the passed
00740             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00741         */
00742     template <class V, class RGBIterator, class DIFFERENCE>
00743     void setRed(V value, RGBIterator const & rgb, DIFFERENCE diff) const
00744     {
00745         rgb[diff].setRed(value);
00746     }
00747 
00748         /** Get value of the green component
00749         */
00750     template <class RGBIterator>
00751     component_type const & green(RGBIterator const & rgb) const
00752     {
00753         return (*rgb).green();
00754     }
00755 
00756         /** Set value of the green component. The type <TT>V</TT> of the passed
00757             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00758         */
00759     template <class V, class RGBIterator>
00760     void setGreen(V value, RGBIterator const & rgb) const
00761     {
00762         (*rgb).setGreen(value);
00763     }
00764 
00765         /** Get value of the green component at an offset
00766         */
00767     template <class RGBIterator, class DIFFERENCE>
00768     component_type const & green(RGBIterator const & rgb, DIFFERENCE d) const
00769     {
00770         return rgb[d].green();
00771     }
00772 
00773         /** Set value of the green component at an offset. The type <TT>V</TT> of the passed
00774             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00775         */
00776     template <class V, class RGBIterator, class DIFFERENCE>
00777     void setGreen(V value, RGBIterator const & rgb, DIFFERENCE d) const
00778     {
00779         rgb[d].setGreen(value);
00780     }
00781 
00782         /** Get value of the blue component
00783         */
00784     template <class RGBIterator>
00785     component_type const & blue(RGBIterator const & rgb) const
00786     {
00787         return (*rgb).blue();
00788     }
00789 
00790         /** Set value of the blue component. The type <TT>V</TT> of the passed
00791             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00792         */
00793     template <class V, class RGBIterator>
00794     void setBlue(V value, RGBIterator const & rgb) const
00795     {
00796         (*rgb).setBlue(value);
00797     }
00798 
00799         /** Get value of the blue component at an offset
00800         */
00801     template <class RGBIterator, class DIFFERENCE>
00802     component_type const & blue(RGBIterator const & rgb, DIFFERENCE d) const
00803     {
00804         return rgb[d].blue();
00805     }
00806 
00807         /** Set value of the blue component at an offset. The type <TT>V</TT> of the passed
00808             in <TT>value</TT> is automatically converted to <TT>component_type</TT>.
00809         */
00810     template <class V, class RGBIterator, class DIFFERENCE>
00811     void setBlue(V value, RGBIterator const & rgb, DIFFERENCE d) const
00812     {
00813         rgb[d].setBlue(value);
00814     }
00815 
00816 };
00817 
00818 
00819 /********************************************************/
00820 /*                                                      */
00821 /*                       RedAccessor                    */
00822 /*                                                      */
00823 /********************************************************/
00824 
00825     /** Encapsulate access to red band of an rgb value.
00826 
00827     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00828     Namespace: vigra
00829     */
00830 template <class RGBVALUE>
00831 class RedAccessor
00832 {
00833   public:
00834     typedef typename RGBVALUE::value_type value_type;
00835 
00836         /** Get value of the red component
00837         */
00838     template <class ITERATOR>
00839     value_type const & operator()(ITERATOR const & i) const {
00840         return (*i).red();
00841     }
00842 
00843         /** Get value of the red component at an offset
00844         */
00845     template <class ITERATOR, class DIFFERENCE>
00846     value_type const & operator()(ITERATOR const & i, DIFFERENCE d) const
00847     {
00848         return i[d].red();
00849     }
00850 
00851         /** Set value of the red component. The type <TT>V</TT> of the passed
00852             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00853         */
00854     template <class V, class ITERATOR>
00855     void set(V value, ITERATOR const & i) const {
00856         (*i).setRed(value);
00857     }
00858 
00859 
00860         /** Set value of the red component at an offset. The type <TT>V</TT> of the passed
00861             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00862         */
00863     template <class V, class ITERATOR, class DIFFERENCE>
00864     void set(V value, ITERATOR const & i, DIFFERENCE d) const
00865     {
00866         i[d].setRed(value);
00867     }
00868 };
00869 
00870 /********************************************************/
00871 /*                                                      */
00872 /*                     GreenAccessor                    */
00873 /*                                                      */
00874 /********************************************************/
00875 
00876     /** Encapsulate access to green band of an rgb value.
00877 
00878     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00879     Namespace: vigra
00880     */
00881 template <class RGBVALUE>
00882 class GreenAccessor
00883 {
00884   public:
00885     typedef typename RGBVALUE::value_type value_type;
00886 
00887         /** Get value of the green component
00888         */
00889     template <class ITERATOR>
00890     value_type const & operator()(ITERATOR const & i) const {
00891         return (*i).green();
00892     }
00893 
00894         /** Get value of the green component at an offset
00895         */
00896     template <class ITERATOR, class DIFFERENCE>
00897     value_type const & operator()(ITERATOR const & i, DIFFERENCE d) const
00898     {
00899         return i[d].green();
00900     }
00901 
00902         /** Set value of the green component. The type <TT>V</TT> of the passed
00903             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00904         */
00905     template <class V, class ITERATOR>
00906     void set(V value, ITERATOR const & i) const {
00907         (*i).setGreen(value);
00908     }
00909 
00910 
00911         /** Set value of the green component at an offset. The type <TT>V</TT> of the passed
00912             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00913         */
00914     template <class V, class ITERATOR, class DIFFERENCE>
00915     void set(V value, ITERATOR const & i, DIFFERENCE d) const
00916     {
00917         i[d].setGreen(value);
00918     }
00919 };
00920 
00921 /********************************************************/
00922 /*                                                      */
00923 /*                     BlueAccessor                     */
00924 /*                                                      */
00925 /********************************************************/
00926 
00927     /** Encapsulate access to blue band of an rgb value.
00928 
00929     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00930     Namespace: vigra
00931     */
00932 template <class RGBVALUE>
00933 class BlueAccessor
00934 {
00935   public:
00936     typedef typename RGBVALUE::value_type value_type;
00937 
00938         /** Get value of the blue component
00939         */
00940     template <class ITERATOR>
00941     value_type const & operator()(ITERATOR const & i) const {
00942         return (*i).blue();
00943     }
00944 
00945         /** Get value of the blue component at an offset
00946         */
00947     template <class ITERATOR, class DIFFERENCE>
00948     value_type const & operator()(ITERATOR const & i, DIFFERENCE d) const
00949     {
00950         return i[d].blue();
00951     }
00952 
00953         /** Set value of the blue component. The type <TT>V</TT> of the passed
00954             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00955         */
00956     template <class V, class ITERATOR>
00957     void set(V value, ITERATOR const & i) const {
00958         (*i).setBlue(value);
00959     }
00960 
00961 
00962         /** Set value of the blue component at an offset. The type <TT>V</TT> of the passed
00963             in <TT>value</TT> is automatically converted to <TT>value_type</TT>.
00964         */
00965     template <class V, class ITERATOR, class DIFFERENCE>
00966     void set(V value, ITERATOR const & i, DIFFERENCE d) const
00967     {
00968         i[d].setBlue(value);
00969     }
00970 };
00971 
00972 /********************************************************/
00973 /*                                                      */
00974 /*                  RGBToGrayAccessor                   */
00975 /*                                                      */
00976 /********************************************************/
00977 
00978     /** Encapsulate access to luminance of an rgb value.
00979 
00980     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
00981     Namespace: vigra
00982     */
00983 template <class RGBVALUE>
00984 class RGBToGrayAccessor
00985 {
00986   public:
00987     typedef typename RGBVALUE::value_type value_type;
00988 
00989         /** Get value of the luminance
00990         */
00991     template <class ITERATOR>
00992     value_type operator()(ITERATOR const & i) const {
00993                 return (*i).luminance(); }
00994 
00995         /** Get value of the luminance at an offset
00996         */
00997     template <class ITERATOR, class DIFFERENCE>
00998     value_type operator()(ITERATOR const & i, DIFFERENCE d) const
00999     {
01000         return i[d].luminance();
01001     }
01002 };
01003 
01004 
01005 /********************************************************/
01006 /*                                                      */
01007 /*                  GrayToRGBAccessor                   */
01008 /*                                                      */
01009 /********************************************************/
01010 
01011     /** Create an RGB view for a grayscale image by making all three channels
01012         equal.
01013 
01014     <b>\#include</b> "<a href="rgbvalue_8hxx-source.html">vigra/rgbvalue.hxx</a>"<br>
01015     Namespace: vigra
01016     */
01017 template <class VALUETYPE>
01018 class GrayToRGBAccessor
01019 {
01020    public:
01021      typedef typename vigra::RGBValue<VALUETYPE> value_type;
01022 
01023          /** Get RGB value for the given pixel.
01024          */
01025      template <class ITERATOR>
01026      value_type operator()(ITERATOR const & i) const {
01027                  return value_type(*i,*i,*i); }
01028 
01029          /** Get RGB value at an offset
01030          */
01031      template <class ITERATOR, class DIFFERENCE>
01032      value_type operator()(ITERATOR const & i, DIFFERENCE d) const
01033      {
01034          return value_type(i[d],i[d],i[d]);
01035      }
01036 };
01037 
01038 
01039 //@}
01040 //@}
01041 
01042 
01043 } // namespace vigra
01044 
01045 #endif // VIGRA_RGBVALUE_HXX

© Ullrich Köthe (koethe@informatik.uni-hamburg.de)
Cognitive Systems Group, University of Hamburg, Germany

html generated using doxygen and Python
VIGRA 1.3.2 (27 Jan 2005)