From: Foster B. <fos...@us...> - 2006-02-03 18:21:20
|
Update of /cvsroot/adobe-source/adobe-source/adobe/documentation/sources/gil In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv1031/adobe/documentation/sources/gil Modified Files: main.dox Added Files: design_guide.dox tutorial.dox Log Message: asl 1.0.13 Index: main.dox =================================================================== RCS file: /cvsroot/adobe-source/adobe-source/adobe/documentation/sources/gil/main.dox,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** main.dox 9 Jan 2006 19:31:34 -0000 1.2 --- main.dox 3 Feb 2006 18:20:42 -0000 1.3 *************** *** 3,59 **** \ingroup asl_home \author Lubomir Bourdev and Hailin Jin \n ! Advanced Graphics Technology \n ! Adobe Systems Inc. ! ! \section gil_toc GIL Table of Contents ! - \ref GILConcepts ! - \ref PointConcept ! - \ref ChannelConcept ! - \ref ColorSpaceTypeConcept ! - \ref PixelConcept ! - \ref IteratorConcept ! - \ref IteratorAdaptorConcept ! - \ref StepIteratorConcept ! - \ref ImageIteratorConcept ! - \ref LocatorConcept ! - \ref LocatorNDConcept ! - \ref Locator2DConcept ! - \ref XYLocatorConcept ! - \ref ImageViewConcept ! - \ref ImageViewNDConcept ! - \ref ImageView2DConcept ! - \ref GILImageViewConcept ! - \ref ImageConcept ! - \ref ImageNDConcept ! - \ref Image2DConcept ! - \ref GILImageConcept ! - \ref GILModels ! - \ref Channel ! - \ref ColorSpaces ! - \ref CMYK ! - \ref ColorConvert ! - \ref GRAY ! - \ref LAB ! - \ref RGB ! - \ref RGBA ! - \ref Pixel ! - \ref ChannelAccessor ! - \ref ColorBase ! - \ref Iterators ! - \ref PlanarPtr ! - \ref IteratorTraits ! - \ref ByteOperations ! - \ref byte_step ! - \ref byte_distance ! - \ref byte_advance ! - \ref byte_advanced ! - \ref byte_advanced_ref ! - \ref ImageView ! - \ref ImageViewConstructors ! - \ref Image ! - \ref Variant ! - \ref Metafunctions ! - \ref type_factory ! - \ref Algorithms \section IntroSec Introduction --- 3,8 ---- \ingroup asl_home \author Lubomir Bourdev and Hailin Jin \n ! Advanced Graphics Technology \n ! Adobe Systems Inc. \section IntroSec Introduction *************** *** 63,76 **** \par The library is designed with the following five goals in mind: ! - <b>Generality:</b> Abstracts image representations from algorithms on images. It allows for writing code once and have it work for any image type. ! - <b>Performance:</b> Speed has been instrumental to the design of the library. The generic algorithms provided in the library are comparable in speed to hand-coding the algorithm for a specific image type. ! - <b>Flexibility:</b> Compile-type parameter resolution results in faster code, but severely limits code flexibility. The library allows for any image parameter to be specified at run time (for a minor performance cost comparable to a virtual call overhead). ! - <b>Extensibility:</b> It is easy to extend the library with new color spaces and image types. Library extensions typically require no changes to the library core; at the same time existing image algorithms apply to new color spaces and image types. ! - <b>Compatibility:</b> The library is designed as an STL and Boost complement. Generic STL algorithms can be used for pixel manipulation, and they are especially optimized. The library works with existing raw pixel data from another image library and can even be integrated into a third-party reference counting mechanism. \section ResourcesSec Resources ! - \ref BeforeAfterExample "See the GIL difference!" Example of code before and after GIL. ! - A tutorial is nearing completion and should be released soon. ! - A detailed GIL design guide is also nearing completion and should be released soon. \section InstallationSec Installation --- 12,25 ---- \par The library is designed with the following five goals in mind: ! - <b>Generality:</b> Abstracts image representations from algorithms on images. It allows for writing code once and have it work for any image type. ! - <b>Performance:</b> Speed has been instrumental to the design of the library. The generic algorithms provided in the library are comparable in speed to hand-coding the algorithm for a specific image type. ! - <b>Flexibility:</b> Compile-type parameter resolution results in faster code, but severely limits code flexibility. The library allows for any image parameter to be specified at run time (for a minor performance cost comparable to a virtual call overhead). ! - <b>Extensibility:</b> It is easy to extend the library with new color spaces and image types. Library extensions typically require no changes to the library core; at the same time existing image algorithms apply to new color spaces and image types. ! - <b>Compatibility:</b> The library is designed as an STL and Boost complement. Generic STL algorithms can be used for pixel manipulation, and they are especially optimized. The library works with existing raw pixel data from another image library and can even be integrated into a third-party reference counting mechanism. \section ResourcesSec Resources ! - \ref BeforeAfterExample "See the GIL difference!" Example of code before and after GIL. ! - A Quick, Hands-on \ref GILTutorial "Tutorial". (In <a href="gil_tutorial.pdf">PDF</a>) ! - A Detailed \ref GILDesignGuide "Design Guide". (In <a href="gil_design_guide.pdf">PDF</a>) \section InstallationSec Installation *************** *** 80,87 **** \section AcknowledgementsSec Acknowledgements ! - <b>Jon Brandt</b>, <b>Mark Ruzon</b> and <b>Paul McJones</b> spent significant time reviewing the library and documentation and provided valuable feedback. ! - <b>Alex Stepanov</b>'s class has directly inspired this project. Alex's "start from the inside" and "bottom up" principles have been applied throughout the design. ! - <b>Sean Parent</b> and Alex Stepanov suggested splitting the image into a 'container' and 'range' classes ! - <b>Bjarne Stroustrup</b> reviewed the core library design */ --- 29,87 ---- \section AcknowledgementsSec Acknowledgements ! - <b>Jon Brandt</b>, <b>Mark Ruzon</b> and <b>Paul McJones</b> spent significant time reviewing the library and documentation and provided valuable feedback. ! - <b>Alex Stepanov</b>'s class has directly inspired this project. Alex's "start from the inside" and "bottom up" principles have been applied throughout the design. ! - <b>Sean Parent</b> and Alex Stepanov suggested splitting the image into a 'container' and 'range' classes ! - <b>Bjarne Stroustrup</b> reviewed the core library design ! ! \section gil_toc GIL Table of Contents ! - \ref GILConcepts ! - \ref PointConcept ! - \ref ChannelConcept ! - \ref ColorSpaceTypeConcept ! - \ref PixelConcept ! - \ref IteratorConcept ! - \ref IteratorAdaptorConcept ! - \ref StepIteratorConcept ! - \ref ImageIteratorConcept ! - \ref LocatorConcept ! - \ref LocatorNDConcept ! - \ref Locator2DConcept ! - \ref XYLocatorConcept ! - \ref ImageViewConcept ! - \ref ImageViewNDConcept ! - \ref ImageView2DConcept ! - \ref GILImageViewConcept ! - \ref ImageConcept ! - \ref ImageNDConcept ! - \ref Image2DConcept ! - \ref GILImageConcept ! - \ref GILModels ! - \ref Channel ! - \ref ColorSpaces ! - \ref CMYK ! - \ref ColorConvert ! - \ref GRAY ! - \ref LAB ! - \ref RGB ! - \ref RGBA ! - \ref Pixel ! - \ref ChannelAccessor ! - \ref ColorBase ! - \ref Iterators ! - \ref PlanarPtr ! - \ref IteratorTraits ! - \ref ByteOperations ! - \ref byte_step ! - \ref byte_distance ! - \ref byte_advance ! - \ref byte_advanced ! - \ref byte_advanced_ref ! - \ref ImageView ! - \ref ImageViewConstructors ! - \ref Image ! - \ref Variant ! - \ref Metafunctions ! - \ref type_factory ! - \ref Algorithms */ *************** *** 89,167 **** /// \ingroup asl_gil /// \brief GIL concept definitions, archetypes and concept checks ! /// @defgroup PointConcept Point ! /// @ingroup GILConcepts ! /// \brief Concept for N-dimensional point and refinement for 2D Ê ! /// @defgroup ChannelConcept Channel ! /// @ingroup GILConcepts ! /// \brief Concept for channel and mutable channel Ê ! /// @defgroup ColorSpaceTypeConcept Color Space ! /// @ingroup GILConcepts ! /// \brief Concept for color space type Ê ! /// @defgroup PixelConcept Pixel ! /// @ingroup GILConcepts ! /// \brief Concept for pixel and mutable pixel Ê ! /// @defgroup IteratorConcept Iterator ! /// @ingroup GILConcepts ! /// \brief Concept for iterators over pixels (fundamental, step, adaptor and image-pixel iterators over immutable/mutable pixels) ! /// @defgroup IteratorAdaptorConcept Iterator Adaptor ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator adaptor over a base iterator Ê ! /// @defgroup StepIteratorConcept Step Iterator ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator that has non-fundamental step Ê ! /// @defgroup ImageIteratorConcept Image Iterator ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator over all pixels in an image Ê ! /// @defgroup LocatorConcept Locator ! /// @ingroup GILConcepts ! /// \brief Concept for locator (generalization of iterator in N-dimensional space) ! /// @defgroup LocatorNDConcept N-Dimensional Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for an N-dimensional locator over immutable/mutable values Ê ! /// @defgroup Locator2DConcept 2-Dimensional Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for a 2-dimensional locator over immutable/mutable values Ê ! /// @defgroup XYLocatorConcept GIL's 2-Dimensional Pixel Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for GIL's 2-dimensional locator over immutable/mutable pixels Ê ! /// @defgroup ImageViewConcept Image View ! /// @ingroup GILConcepts ! /// \brief Concept for image view (N-dimensional range) ! /// @defgroup ImageViewNDConcept N-Dimensional Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for an N-dimensional range over immutable/mutable values Ê ! /// @defgroup ImageView2DConcept 2-Dimensional Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for a 2-dimensional range over immutable/mutable values Ê ! /// @defgroup GILImageViewConcept GIL's 2-Dimensional Pixel Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for GIL's 2-dimensional range over immutable/mutable pixels Ê ! /// @defgroup ImageConcept Image ! /// @ingroup GILConcepts ! /// \brief Concept for image (N-dimensional container) ! /// @defgroup ImageNDConcept N-Dimensional Image ! /// @ingroup ImageConcept ! /// \brief Concept for an N-dimensional container of immutable/mutable values Ê ! /// @defgroup Image2DConcept 2-Dimensional Image ! /// @ingroup ImageConcept ! /// \brief Concept for a 2-dimensional container of immutable/mutable values Ê ! /// @defgroup GILImageConcept GIL's 2-Dimensional Pixel Image ! /// @ingroup ImageConcept ! /// \brief Concept for GIL's 2-dimensional container of immutable/mutable pixels Ê /// @defgroup GILModels GIL Models --- 89,167 ---- /// \ingroup asl_gil /// \brief GIL concept definitions, archetypes and concept checks ! /// @defgroup PointConcept Point ! /// @ingroup GILConcepts ! /// \brief Concept for N-dimensional point and refinement for 2D Ê ! /// @defgroup ChannelConcept Channel ! /// @ingroup GILConcepts ! /// \brief Concept for channel and mutable channel Ê ! /// @defgroup ColorSpaceTypeConcept Color Space ! /// @ingroup GILConcepts ! /// \brief Concept for color space type Ê ! /// @defgroup PixelConcept Pixel ! /// @ingroup GILConcepts ! /// \brief Concept for pixel and mutable pixel Ê ! /// @defgroup IteratorConcept Iterator ! /// @ingroup GILConcepts ! /// \brief Concept for iterators over pixels (fundamental, step, adaptor and image-pixel iterators over immutable/mutable pixels) ! /// @defgroup IteratorAdaptorConcept Iterator Adaptor ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator adaptor over a base iterator Ê ! /// @defgroup StepIteratorConcept Step Iterator ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator that has non-fundamental step Ê ! /// @defgroup ImageIteratorConcept Image Iterator ! /// @ingroup IteratorConcept ! /// \brief Concept for an iterator over all pixels in an image Ê ! /// @defgroup LocatorConcept Locator ! /// @ingroup GILConcepts ! /// \brief Concept for locator (generalization of iterator in N-dimensional space) ! /// @defgroup LocatorNDConcept N-Dimensional Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for an N-dimensional locator over immutable/mutable values Ê ! /// @defgroup Locator2DConcept 2-Dimensional Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for a 2-dimensional locator over immutable/mutable values Ê ! /// @defgroup XYLocatorConcept GIL's 2-Dimensional Pixel Locator ! /// @ingroup LocatorConcept ! /// \brief Concept for GIL's 2-dimensional locator over immutable/mutable pixels Ê ! /// @defgroup ImageViewConcept Image View ! /// @ingroup GILConcepts ! /// \brief Concept for image view (N-dimensional range) ! /// @defgroup ImageViewNDConcept N-Dimensional Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for an N-dimensional range over immutable/mutable values Ê ! /// @defgroup ImageView2DConcept 2-Dimensional Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for a 2-dimensional range over immutable/mutable values Ê ! /// @defgroup GILImageViewConcept GIL's 2-Dimensional Pixel Image View ! /// @ingroup ImageViewConcept ! /// \brief Concept for GIL's 2-dimensional range over immutable/mutable pixels Ê ! /// @defgroup ImageConcept Image ! /// @ingroup GILConcepts ! /// \brief Concept for image (N-dimensional container) ! /// @defgroup ImageNDConcept N-Dimensional Image ! /// @ingroup ImageConcept ! /// \brief Concept for an N-dimensional container of immutable/mutable values Ê ! /// @defgroup Image2DConcept 2-Dimensional Image ! /// @ingroup ImageConcept ! /// \brief Concept for a 2-dimensional container of immutable/mutable values Ê ! /// @defgroup GILImageConcept GIL's 2-Dimensional Pixel Image ! /// @ingroup ImageConcept ! /// \brief Concept for GIL's 2-dimensional container of immutable/mutable pixels Ê /// @defgroup GILModels GIL Models *************** *** 169,251 **** /// \brief Standard models of GIL concepts Ê ! /// @defgroup Channel Channel ! /// @ingroup GILModels ! /// \brief Channel and channel operations Ê ! /// @defgroup ColorSpaces Color Space ! /// @ingroup GILModels ! /// \brief Color spaces and color space conversion Ê ! /// @defgroup Pixel Pixel ! /// @ingroup GILModels ! /// \brief Pixel and pixel-related functions ÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊ ! /// @defgroup ChannelAccessor Channel Accessor ! /// @ingroup Pixel ! /// \brief Classes allowing accessing a channel of a pixel Ê ! /// @defgroup ColorBase Color Bases ! /// @ingroup Pixel ! /// \brief A bundle of channel values/references/pointers of a given color space Ê ! /// @defgroup Iterators Pixel Iterators ! /// @ingroup GILModels ! /// \brief Iterators operating on pixels Ê ! /// @defgroup PlanarPtr Planar Pointers ! /// @ingroup Iterators ! /// \brief Implementations of pointers to planar pixels Ê ! /// @defgroup IteratorTraits Iterator Traits ! /// @ingroup Iterators ! /// \brief Traits for pixel iterators Ê ! /// @defgroup ByteOperations Byte-level operations ! /// @ingroup Iterators ! /// \brief Byte-level operations on pixel iterators Ê ! /// @defgroup byte_step byte_step ! /// @ingroup ByteOperations ! /// \brief returns the number of bytes from the current pixel of a pointer to the next Ê ! /// @defgroup byte_distance byte_distance ! /// @ingroup ByteOperations ! /// \brief Returns the distance in bytes from the first pixel iterator to the second Ê ! /// @defgroup byte_advance byte_advance ! /// @ingroup ByteOperations ! /// \brief Moves a pixel iterator a given distance in bytes Ê ! /// @defgroup byte_advanced byte_advanced ! /// @ingroup ByteOperations ! /// \brief Returns a pixel iterator a given byte distance away from a given pixel iterator Ê ! /// @defgroup byte_advanced_ref byte_advanced_ref ! /// @ingroup ByteOperations ! /// \brief Shortcut to advancing a pixel iterator by a given number of bytes and taking the reference in case the compiler is not smart enough Ê ! /// \defgroup ImageView Image View ! /// @ingroup GILModels ! /// \brief Image views and related operations Ê ! /// @defgroup ImageViewConstructors Image View Constructors ! /// @ingroup ImageView ! /// \brief Methods for constructing image views from raw data or other image views Ê ! /// \defgroup Image Image ! /// @ingroup GILModels ! /// \brief Images and related operations Ê ! /// @defgroup Variant Variant ! /// @ingroup GILModels ! /// \brief Support for concepts with run-time instantiation. Used in GIL to provide images and image views of run-time specified color space, channel depth, etc. Ê ! /// @defgroup Metafunctions Meta-functions ! /// @ingroup GILModels ! /// \brief Meta-functions that construct types or return type properties Ê ! /// @defgroup Algorithms Algorithms ! /// @ingroup GILModels ! /// \brief Some basic STL-style algorithms when applied to images (as opposed to ranges) Ê /// \brief namespace for functions not directly needed by the client --- 169,251 ---- /// \brief Standard models of GIL concepts Ê ! /// @defgroup Channel Channel ! /// @ingroup GILModels ! /// \brief Channel and channel operations Ê ! /// @defgroup ColorSpaces Color Space ! /// @ingroup GILModels ! /// \brief Color spaces and color space conversion Ê ! /// @defgroup Pixel Pixel ! /// @ingroup GILModels ! /// \brief Pixel and pixel-related functions ÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊÊ ! /// @defgroup ChannelAccessor Channel Accessor ! /// @ingroup Pixel ! /// \brief Classes allowing accessing a channel of a pixel Ê ! /// @defgroup ColorBase Color Bases ! /// @ingroup Pixel ! /// \brief A bundle of channel values/references/pointers of a given color space Ê ! /// @defgroup Iterators Pixel Iterators ! /// @ingroup GILModels ! /// \brief Iterators operating on pixels Ê ! /// @defgroup PlanarPtr Planar Pointers ! /// @ingroup Iterators ! /// \brief Implementations of pointers to planar pixels Ê ! /// @defgroup IteratorTraits Iterator Traits ! /// @ingroup Iterators ! /// \brief Traits for pixel iterators Ê ! /// @defgroup ByteOperations Byte-level operations ! /// @ingroup Iterators ! /// \brief Byte-level operations on pixel iterators Ê ! /// @defgroup byte_step byte_step ! /// @ingroup ByteOperations ! /// \brief returns the number of bytes from the current pixel of a pointer to the next Ê ! /// @defgroup byte_distance byte_distance ! /// @ingroup ByteOperations ! /// \brief Returns the distance in bytes from the first pixel iterator to the second Ê ! /// @defgroup byte_advance byte_advance ! /// @ingroup ByteOperations ! /// \brief Moves a pixel iterator a given distance in bytes Ê ! /// @defgroup byte_advanced byte_advanced ! /// @ingroup ByteOperations ! /// \brief Returns a pixel iterator a given byte distance away from a given pixel iterator Ê ! /// @defgroup byte_advanced_ref byte_advanced_ref ! /// @ingroup ByteOperations ! /// \brief Shortcut to advancing a pixel iterator by a given number of bytes and taking the reference in case the compiler is not smart enough Ê ! /// \defgroup ImageView Image View ! /// @ingroup GILModels ! /// \brief Image views and related operations Ê ! /// @defgroup ImageViewConstructors Image View Constructors ! /// @ingroup ImageView ! /// \brief Methods for constructing image views from raw data or other image views Ê ! /// \defgroup Image Image ! /// @ingroup GILModels ! /// \brief Images and related operations Ê ! /// @defgroup Variant Variant ! /// @ingroup GILModels ! /// \brief Support for concepts with run-time instantiation. Used in GIL to provide images and image views of run-time specified color space, channel depth, etc. Ê ! /// @defgroup Metafunctions Meta-functions ! /// @ingroup GILModels ! /// \brief Meta-functions that construct types or return type properties Ê ! /// @defgroup Algorithms Algorithms ! /// @ingroup GILModels ! /// \brief Some basic STL-style algorithms when applied to images (as opposed to ranges) Ê /// \brief namespace for functions not directly needed by the client --- NEW FILE: tutorial.dox --- //////////////////////////////////////////////////////////////////////////////////////// /// \file /// \brief Doxygen documentation /// \author Lubomir Bourdev and Hailin Jin \n /// Adobe Systems Incorporated /// /// //////////////////////////////////////////////////////////////////////////////////////// /** \page GILTutorial Generic Image Library Tutorial \author Lubomir Bourdev (lbo...@ad...) and Hailin Jin (hl...@ad...) \n Adobe Systems Incorporated \version 1.0 \date January 10, 2006 The Generic Image Library (GIL) is a C++ library that abstracts image representations from algorithms and allows writing code that can work on a variety of images with performance similar to hand-writing for a specific image type. <p>This document will give you a jump-start in using GIL. It does not discuss the underlying design of the library and does not cover all aspects of it. You can find a detailed library design document on the main GIL web page at http://opensource.adobe.com/gil - \ref InstallSec - \ref ObjectsSec - \ref UsefulTypedefs - \ref GenericObjects - \ref RelatedTypes - \ref ImageAndViewSec - \ref ImageSec - \ref ImageViewSec - \ref ImageViewFactory - \ref ManipulatingImages - \ref ContextIndepdendentPixOp - \ref GenericAndSpecialized - \ref ContextAwareOperations - \ref VariantSec - \ref ExtendingGIL - \ref CodeExamples - \ref HistogramExample - \ref SafeAreaExample - \ref GDIExample \section InstallSec Installation GIL is part of Adobe Software Library (ASL) which can be installed at http://opensource.adobe.com. GIL consists of header files only and can be used as stand-alone also. Its only dependency is boost. There is no library to link against. Including \p image_view_factory.hpp will be sufficient for most projects. \section ObjectsSec Basic Concepts <i>Pixels</i> are the fundamental building blocks of images. A pixel is a sequence of channels whose number and interpretation are defined by a color space. <i>Pixel iterators</i> are any random access iterators that operate on pixels. A built-in C pointer to a pixel is a valid pixel iterator. <i>Pixel xy locators</i> (or just pixel locators) are like iterators, but allow navigation in both x and y. <i>Image view</i> provides access to a 2D array of pixels without ownership. It is to images what a range is to STL-s containers. Most image-level algorithms operate on image views. Image views allow 1D and 2D access of the pixels and provide iterators to traverse the rows and columns. An <i>image</i> is a container of pixels. It allocates and deallocates the pixels and can provide its associated image view. \subsection UsefulTypedefs Typedefs for Concrete Types There are typedefs to refer to any concrete image, pixel iterator, pixel locator, pixel reference or pixel value. They follow this pattern: <p> \e ColorSpace + \e BitDepth + ("c") + ("_planar") + ("_step") + \e ClassType <p> Where \e ColorSpace also indicates the ordering of components. Examples are \p rgb, \p bgr, \p cmyk, \p rgba. \e BitDepth can be \p 8,\p 16,\p 32. \p c indicates object operating over immutable pixels. \p _planar indicates planar organization (as opposed to interleaved). \p _step indicates special image views, locators and iterators which traverse the data in non-trivial way (for example, backwards or every other pixel). \e ClassType is \p _image (image), \p _view (image view), \p _loc (pixel 2D locator) \p _ptr (pixel iterator), \p _ref (pixel reference), \p _pixel (pixel value). Here are examples: \code bgr8_image i; // 8-bit interleaved BGR image cmyk16_pixel; x; // 16-bit CMYK pixel value; cmyk16c_planar_ref p(x); // const reference to a 16-bit planar CMYK pixel x. rgb32_planar_step_ptr ii; // step pointer to a 32-bit planar RGB pixel. \endcode \subsection GenericObjects Generic Representation Let \p T be a channel type (\p bits8 (or \p unsigned \p char), \p bits16 (or \p unsigned \p short), \p bits32 (or \p float), etc), and \p C be a color space tag (\p rgb_tag, \p bgr_tag, \p rgba_tag, \p cmyk_tag, etc.) This is how pixel constructs are defined generically: \code pixel<T,C> v; // any pixel value pixel<T,C>& r(x); // reference to an interleaved pixel x pixel<T,C>* p; // pointer to an interleaved pixel pixel<const T,C>* p; // pointer to a constant interleaved pixel pixel<T&,C> pr(x); // reference to any planar pixel x pixel<const T&,C> cpr(x); // constant reference to any planar pixel x planar_ptr<T,C> pp; // pointer to any planar pixel // factory metafunctions (see the design guide for more) typename iterator_type<T,C,true>::type it; // equivalent to planar_ptr<T,C> ('true' means planar) typename view_type<T,C,false>::type img_view; // interleaved image view typename image_type<T,C,true>::type img; // planar image of channel type T, color space tag C typename type_from_x_iterator<X_IT>::view_type v; // image view corresponding to a given pixel iterator X_IT \endcode \subsection RelatedTypes Getting a Type Related to a Given Type As the example illustrates, planar pixels have non-standard pointers and references. You never have to worry about knowing the correct type - if you have a pointer to a pixel, you can query related types via its \p std::iterator_traits. All pixel iterators have traits that define the types related to the pixel iterator. For example, the iterator traits for a raw (interleaved) pointer to a pixel look like this: \code namespace std { template <typename T, typename C> struct iterator_traits<pixel<T,C>*> { typedef random_access_iterator_tag iterator_category; typedef pixel<T,C> value_type; typedef ptrdiff_t difference_type; typedef value_type& reference; typedef value_type* pointer; typedef T channel_type; // color channel typedef C color_space_tag; // color space identifier typedef ... const_reference; // reference to immutable pixel typedef ... const_type; // iterator over immutable pixels typedef ... dynamic_step_type; // iterator that can skip over pixels static const bool is_planar=false; // planar vs interleaved statoc const bool is_base=true; // base iterator vs adaptor over another iterator }; } \endcode Note that pixel iterators have additional types in their iterator traits, the most common of which are shown above. Locators, image views and images don't have traits classes, but provide most of the above as member typedefs. One important typedef is \p const_type. It returns the type otherwise identical to the source type, but operating over immutable pixels. Note the difference from a constant type - a constant iterator (locator, image view) does not allow modifying itself (advancing the iterator, resizing the image view) but may or may not allow modifying the underlying pixels. \p const_type returns a type that does not allow modifying the underlying pixels. \section ImageAndViewSec Images and Image Views \section ImageSec Image An image is a 2D container. It allocates memory for the pixels in its constructor, deallocates it in its destructor, and deep-copies the pixels in its copy constructor. Images can be created given width, height, and (optionally) row alignment policy: \code // 10x10 interleaved 8-bit RGB image with 4-byte alignment for rows rgb8_image my_rgb8_img(10,10, 4); // 10x10 planar 16-bit CMYK image. Dimensions can also be specified via point_type: typedef point2<ptrdiff_t> point_type; cmyk16_planar_image img(point_type(10,10)); // 10x10 generic planar image of type T and color space CS. typename image_type<T,CS,true>::type my_generic_img(10,10); \endcode \section ImageViewSec Image View Image data is accessed via image view. An image view is a lightweight delimiter of a 2D array of pixels with shallow copy constructor and assignment operator. It is similar to a range (a pair of iterators) in STL. Algorithms typically operate on image views. Images are only used to allocate and hold the pixel data. Image views can be obtained from images: \code rgb8_view v=view(my_rgb8_img); typename view_type<T,CS,true>::type v=view(my_generic_img); \endcode Constant images disallow modification of not only the image parameters but also the pixels. The views that constant images return have constant channel type: \code template <typename IMG> // Models GIL Image void my_const_test(const IMG& img) { // IMG::view_type v=view(img); // Error: can't get non-const view from const image IMG::const_view_type v=const_view(img); // OK // v(0,0)[0]=3; // Error: can't change pixels through const view } \endcode Note that \p IMG::const_view_type is the same as \p IMG::view_type::const_type but is different from <tt>const IMG::view_type</tt>. The former is a view over constant pixel data, whereas the latter is a constant view over pixels that may or may not be modifyable through the view. Image views can also be constructed as shallow views of existing pixel data. For example: \code // pointer to existing raw 8-bit BGR interleaved data unsigned char* raw_bgr=...; // 100x100 8-bit interleaved BGR image over the existing data, with 300 bytes per row: bgr8_view img_view=interleaved_view<bgr8_pixel>(100,100,raw_bgr,300); // const pointers to the red, green and blue planes of a planar 16-bit RGB image const unsigned short* r=...; const unsigned short* g=...; const unsigned short* b=...; // 100x100 16-bit constant planar RGB image view over the existing data, with 300 bytes per row: rgb16c_planar_view img=planar_rgb_view(100,100,r,g,b,300); \endcode It is also possible to construct an image from an image view and a custom allocator object. That allows for creating images that take over ownership of the data or that work with 3rd party reference counting mechanisms. \subsection ImageViewFactory Creating Image Views from Other Image Views It is possible to construct one image view from another by changing some policy of how image data is interpreted: \code // flipped upside-down, left-to-right, transposed view template <typename VIEW> VIEW flipud_view(const VIEW& src); template <typename VIEW> typename VIEW::dynamic_step_type fliplr_view(const VIEW& src); template <typename VIEW> typename VIEW::dynamic_step_type transposed_view(const VIEW& src); // rotations template <typename VIEW> typename VIEW::dynamic_step_type rotated180_view(const VIEW& src); template <typename VIEW> typename VIEW::dynamic_step_type rotated90cw_view(const VIEW& src); template <typename VIEW> typename VIEW::dynamic_step_type rotated90ccw_view(const VIEW& src); // view of an axis-aligned rectangular area within an image template <typename VIEW> VIEW subimage_view(const VIEW& src, const VIEW::point_type& top_left, const VIEW::point_type& dimensions); // subsampled view (skipping pixels in X and Y) template <typename VIEW> typename VIEW::dynamic_step_type subsampled_view(const VIEW& src, const VIEW::point_type& step); // color and bit depth converted view to match pixel type P template <typename SRC_VIEW, // Models ImageViewConcept typename DST_P> // Models PixelConcept struct color_convert_types { typedef ... x_iterator; // dereference iterator adaptor that converts SRC_VIEW::value_type to DST_P typedef ... view_type; // image view adaptor with value type DST_P, over SRC_VIEW }; template <typename VIEW, typename P> typename color_convert_types<VIEW,P>::view_type color_convert_view(const VIEW& src); // single-channel view of the N-th channel of a given view template <typename SRC_VIEW> struct nth_channel_types { typedef ... x_iterator; // iterator over a single-channel of the rows of SRC_VIEW typedef ... view_type; // its corresponding image view type }; template <typename VIEW> typename nth_channel_types<VIEW>::view_type nth_channel_view(const VIEW& view, int n); \endcode Note that views are taken as constant references. There are currently no operations that modify views. This is because views are so lightweight, that they can be constructed from scratch. The view mutability is preserved in the above methods. For example, \p flipud_view called with a mutable view will return another mutable view. Here is example of using views: \code rgb16_image img(100,100); // an RGB interleaved image // grayscale view over the green (index 1) channel of img gray16_step_view green=nth_channel_view(view(img),1); // 50x50 view of the green channel of img, upside down and taking every other pixel in X and in Y gray16_step_view ud_fud=flipud_view(subsampled_view(green,2,2)); \endcode Note that image views are fast, constant-time, shallow views over the pixel data. The above code does not copy any pixels; it operates on the pixel data allocated when \p img was created. \section ManipulatingImages Image Manipulation \subsection ContextIndepdendentPixOp Context-Independent Pixel Operations Many image operations can be applied to each pixel independently, without knowledge of its location or neighbors. Examples of such operations are assignment, equality, and computing a histogram. Similar to STL containers, image views provide a 1D navigation capability using \p begin() and \p end() call. Here is how to set all values of an 8-bit RGB interleaved image view to red: \code void make_red(const rgb8_view& img) { rgb8_pixel red(255,0,0); for (rgb8_view::iterator it=img.begin(); it!=img.end(); ++it) *it=red; } \endcode Here is a generic version of the above: \code template <typename VIEW> // Models GIL Mutable Image View void make_red(const VIEW& img) { typename VIEW::value_type red; color_convert(rgb8_pixel(255,0,0), red); // convert to red in the image color space and bit depth for (typename VIEW::iterator it=img.begin(); it!=img.end(); ++it) *it=red; } \endcode Standard STL algorithms can be used directly (also \p color_converter may be used to return destination pixel): \code template <typename VIEW> // Models GIL Mutable Image View void make_red(const VIEW& img) { gil_function_requires<MutableImageViewConcept<VIEW> >(); // optional typedef typename VIEW::value_type pixel_type; pixel_type red=color_converter<pixel_type>()(rgb8_pixel(255,0,0)); std::fill(img.begin(), img.end(), red); } \endcode Note that GIL constructs are models of GIL concepts and algorithms operate on any model of the GIL concept. Therefore you can use your own view type instead. The call to \p gil_function_requires ensures at compile-time that the template parameter \p VIEW does, in fact, satisfy the requirements of GIL image views. This code uses boost's Concept Check library. It has only compile-time penalty and is only effective in debug mode, and when \p USE_GIL_CONCEPT_CHECK is defined. Such concept checks can sometimes result in more readable compile error messages. See the GIL's Design Guide for more about GIL's concepts. There are also GIL-equivalents for some standard algorithms that take image views: \code template <typename VIEW> // Models GIL Mutable Image View void make_red(const VIEW& img) { fill_pixels(img, color_converter<typename VIEW::value_type>()(rgb8_pixel(255,0,0))); } \endcode The above code works for both planar and interleaved image views of any bit depth, color space, channel ordering or alignment policy. It also works with views constructed as shallow views of other views (upside down, subsampled, subimage, etc). It will also work for new image view types and new color spaces that can be defined in a future extension to the library. Use STL algorithms (\p std::fill) or the GIL versions (\p fill_pixels) when available, as GIL may have provided overloads optimized for performance. For example, depending on your image type, \p std::fill and \p fill_pixels may resolve to \p memset. \subsection GenericAndSpecialized Generic and Specialized Versions Suppose you want to have a generic version of the algorithm, but you want to do something slightly different for certain color spaces or pixel types. For example, you may want to provide an assembly-level optimization or GPU optimization that only works for 8-bit interleaved RGBA images. Here is how to make our \p make_red algorithm do something different for, say, planar RGB images. <p> First we need to wrap the method inside a function object, templated over the horizontal pixel iterator: \code template <typename IT> // Models GIL Mutable Pixel Iterator struct make_red_fn_obj { template <typename VIEW> // Models GIL Mutable Image View void operator()(const VIEW& img) const { fill_pixels(img, color_converter<typename VIEW::value_type>()(rgb8_pixel(255,0,0))); } }; \endcode Now we use template specialization to define the behavior when the iterator is a planar RGB pointer of any channel type \p T: \code template <typename T> struct make_red_fn_obj<planar_ptr<T,rgb_tag> > { template <typename VIEW> // Models GIL Mutable Image View void operator()(const VIEW& img) { planar_ptr<T,rgb_tag> p=img.x_at(0,0); // planar pointer to the first pixel fast_rgb8_make_red(p.r, p.g, p.b, sizeof(T)*8, img.width(), img.height(), img.row_bytes()); } }; // in bottlenecks void fast_rgb8_make_red(void* r, void* g, void* b, int depth, int width, int height, int row_bytes) { ... } \endcode Finally the \p make_red algorithm takes a view and dispatches to the right implementation: \code template <typename VIEW> // Models GIL Mutable Image View void make_red(const VIEW& img) { make_red_fn_obj<typename VIEW::x_iterator>()(img); } \endcode \subsection ContextAwareOperations Context-Aware Pixel Operations When the pixel position and the notion of rows and columns matters, use the appropriate image accessors and iterators. \p VIEW::x_iterator is a random-access pixel iterator that moves horizontally (for simple interleaved images it is just a pointer). \p VIEW::y_iterator is a random-access pixel iterator that moves vertically. Here is some sample code: \code // VIEW is an image view type (a template parameter or concrete view, like rgb8_view) VIEW img(...); typedef typename VIEW::value_type pixel_type; img(3,5)=img(7,10); // setting pixel at x=3,y=5 to the value of pixel at x=7,y=10 typename VIEW::point_type c(10,10); img(c).set_channels(0); // operator() also works on points img[11]=img[12]; // operator[] gives you 1D access (constant time, but slow!) // here is how to make the 5-th column red: pixel_type red=color_converter<pixel_type>()(rgb8_pixel(255,0,0)); for(typename VIEW::y_iterator yit=img.col_begin(5); yit!=img.col_end(5); ++yit) *yit=red; // or just std::fill(img.col_begin(5), img.col_end(5), red); // here is one way to traverse each row and column: for (size_t y=0; y<img.height(); ++y) for (typename VIEW::x_iterator xit=img.row_begin(y); xit!=img.row_end(y); ++xit) *xit=red; // here is another: for (size_t y=0; y<img.height(); ++y) { typename VIEW::x_iterator row_first=img.row_begin(y); for (size_t x=0; x<img.width(); ++x) row_first[x]=red; } \endcode Pixel XY locators are lightweight constructs that allow for 2D navigation relative to pixel coordinates: \code VIEW img_view(...); // let VIEW be a GIL Image View typedef typename VIEW::point_type point_type; typename VIEW::locator loc; loc=img_view.xy_at(10,10); // start at pixel (x=10,y=10) ++loc.x(); // move to (11,10) loc.y()+=15; // move to (11,25) loc-=point_type(1,1); // move to (10,24) *loc=(loc(-1,0)+loc(1,0))/2; // set pixel (10,24) to the average of its left and right neighbors \endcode As the example shows, the locator's \p x() and \p y() accessors return 1D random access iterators that let us change each dimension independently, but we can navigate over both dimensions simultaneously via operators \p +,\p -,\p += and \p -=. Locators are fast and lightweight objects. For example, the locator for a simple interleaved image consists of one raw pointer to the current pixel plus an integer for the row size in bytes, for a total of 8 bytes. <tt> ++loc.x() </tt> amounts to incrementing a raw pointer. That said, an operation like <tt>*loc=(loc(-1,0)+loc(1,0))/2</tt> when applied over the entire image is slower than maintaining and incrementing separate pointers to each neighbor. Locators can cache relative positions of their neighbors if they have to be accessed frequently (see the GIL Design Guide for more). Also beware that locators are not aware of the image view bounds. \section VariantSec Run-time specified images and image views Image and image view algorithms require knowing the image parameters at compile time. When image parameters are available only at run time, GIL's \p variant must be used. The name <i>variant</i> comes from \p boost::variant, which is very similar in spirit, though GIL's mechanism has a number of advantages that prevent us from using \p boost::variant. Variants are an advanced mechanism described in more detail in GIL's design guide. Briefly, they allow a non-templated instance (such as "any_image") to hold the value of run-time instantiated model (such as "rgb8_planar_image" or "my_image"). We call the set of allowable models the <i>concept space</i>. GIL provides concept spaces for standard images and image views via the \p conceptspace extension (though users may provide their own): \code // defines any_image, any_view, any_const_view #include <adobe\gil\extension\conceptspace\any_standard_image.hpp> // holder to any standard image any_image myDynImage; // Assign it an 8-bit RGB image at run time myDynImage=rgb8_image(10,10); // Replace it with a 16-bit CMYK image. move_in is like operator= but more efficient // It does not copy the data. After the call img2 will be empty (the pixels will be inside myDynImage) cmyk16_planar_image img2(100,100); myDynImage.move_in(img2); // Get the view of the dynamic image any_view myDynView=view(myDynImage); // The cast will succeed, since the view currently refers to 16-bit CMYK data cmyk16_planar_view concrete_view=myDynView._dynamic_cast<cmyk16_planar_view>(); // will throw std::bad_cast myDynView._dynamic_cast<rgb8_view>(); \endcode Variants are very efficient and by default the instantiated model is stored on the stack. Invoking a method through a variant has a performance penalty comparable to going through a single switch statement. Therefore variants of images and image views can be used for high level algorithms with practically no performance penalty. See GIL's design guide for how to make variants use your algorithms. Most GIL algorithms have versions that can take image view variants in place of templated views: \code rgb8_view v1(...); // concrete image view bgr8_view v2(...); // concrete image view compatible with v1 and of the same size any_view av(...); // run-time specified image view // Copies the pixels from v1 into v2. If the pixels are incompatible triggers compile error copy_pixels(v1,v2); // The source or destination (or both) may be run-time instantiated. // If they happen to be incompatible, throws std::bad_cast copy_pixels(v1, av); copy_pixels(av, v2); copy_pixels(av, av); \endcode Other algorithms taking variants are \p fill_pixels, \p equal_pixels, \p transform_pixels, etc. See the GIL Design Guide for more. Here is how the variant-taking \p fill_pixels looks like: \code template <typename IVCS, // Models Image View Concept Space typename VAL> // Models GIL Pixel void fill_pixels(const variant<IVCS>& img_view, const VAL& val) { img_view.apply_visitor(GIL::detail::fill_pixels_fn<VAL>(val)); } \endcode \p variant holds an object with a run-time instantiated type and \p IVCS is a template parameter specifying, among other things, the set of types the variant can take. In our case all types must be valid mutable GIL image views (i.e. models of \p MutableImageViewConcept) whose pixels are compatible with \p VAL. \p any_view (defined in GIL's conceptspace extension) is a typedef of a variant over a set of a few dozen commonly used image views, specified in the extension. There are also \p any_const_view and \p any_image typedefs: \code // inside <adobe\gil\extension\conceptspace\any_standard_image.hpp> class AnyImageViewConceptSpace { ... // defines the set of commonly used image views }; typedef variant<AnyImageViewConceptSpace> any_view; typedef variant<AnyConstImageViewConceptSpace> any_const_view; typedef variant<AnyImageConceptSpace> any_image; \endcode There is no \p any_const_image typedef (and no \p const_type typedef inside the image class), because images, being containers, propagate their constness to the pixels. To obtain an image with immutable pixels, simply use a constant reference to an image (or, for run-time specified images, a constant reference to \p any_image). \p apply_visitor takes a function object and will typically go through a switch statement to identify the currently instantiated view and invoke the function object with the specified view type. There is also a global version of \p apply_visitor taking two variants. The function object must have an application operator whose only parameter is a concrete type the variant can take. See the sample code below for an example of creating such a function object. See the GIL design guide for more on variants. GIL's I/O extension makes extensive use of run-time specified images. Here is how to make a 180-degree rotated copy of an image saved on disk, preserving its native color space and channel depth (the file formats are inferred automatically from the image extensions): \code #include <adobe\gil\extension\conceptspace\any_standard_image.hpp> #include <adobe\gil\extension\io\image_io.hpp> void save_180rot(const std::string& fileNameIn, const std::string& fileNameOut) { any_image img; load_image(img, fileNameIn); save_view(rotated180_view(view(img)), fileNameOut); } \endcode Variants should be used with caution (especially algorithms that take more than one variant) because they instantiate the algorithm for every possible model that the variant can take. This can take a toll on compile time and executable size. Despite these limitations, \p variant is a powerful technique that allows us to combine the speed of compile-time resolution with the flexibility of run-time resolution. It allows us to treat images of different parameters uniformly as a collection and store them in the same container. \section ExtendingGIL Extending the Generic Image Library GIL allows extending and replacing virtually any part of it. You can define your own channel types, color spaces, pixels, pixel iterators, locators, image views, images, and algorithms. You can make higher-dimensional images, virtual images that live on the disk, inside a jpeg file, somewhere on the internet, or even fully-synthetic images such as the Mandelbrot set. Written properly, they will work with any existing GIL code. Most such extensions require no changes to the library and can thus be supplied in another module. The GIL Design Guide contains more information on ways to extend GIL. \section CodeExamples Code Examples \subsection HistogramExample Histogram The the histogram can be computed by counting the number of pixel values that fall in each bin. The following method takes a grayscale (one-dimensional) image view, since only grayscale pixels are convertible to integers: \code template <typename GRAY_VIEW, typename R> void grayimage_histogram(const GRAY_VIEW& img, R& hist) { for (typename GRAY_VIEW::iterator it=img.begin(); it!=img.end(); ++it) ++hist[*it]; } \endcode Using \p boost::lambda and GIL's \p for_each_pixel algorithm, we can write this more compactly: \code template <typename GRAY_VIEW, typename R> void grayimage_histogram(const GRAY_VIEW& img, R& hist) { for_each_pixel(img, ++var(hist)[_1]); } \endcode Where \p for_each_pixel invokes \p std::for_each and \p var and \p _1 are \p boost::lambda constructs. To compute the luminosity histogram, we call the above method using the grayscale view of an image: \code template <typename VIEW, typename R> void luminosity_histogram(const VIEW& img, R& hist) { grayimage_histogram(color_convert_view<gray8_pixel>(img),hist); } // this is how to invoke it: unsigned char hist[255]; fill(hist,hist+255,0); luminosity_histogram(img,hist); // img is an image view \endcode If we want to view the histogram of the first channel of the image, we call: \code grayimage_histogram(nth_channel_view(img,1),hist); \endcode \subsection SafeAreaExample Creating a Copy of an Image with a Safe Buffer. Suppose we want to convolve an image with multiple kernels, the largest of which is 2K+1 x 2K+1 pixels. It may be worth creating a margin of K pixels around the image borders. Here is how to do it: \code template <typename SRC_VIEW, // Models ImageViewConcept (the source view) typename DST_IMG> // Models ImageConcept (the returned image) void create_with_margin(const SRC_VIEW& src, int k, DST_IMG& result) { gil_function_requires<ImageViewConcept<SRC_VIEW> >(); gil_function_requires<MutableImageConcept<DST_IMG> >(); result=DST_IMG(src.width()+2*k, src.height()+2*k); SRC_VIEW centerImg=subimage_view(view(result), k,k,src.width(),src.height()); std::copy(src.begin(), src.end(), centerImg.begin()); } \endcode We allocated a larger image, then we used \p subimage_view to create a shallow image of its center area of top left corner at (k,k) and of identical size as \p src, and finally we copied \p src into that center image. If the margin needs initialization, we could have done it with \p fill_pixels. Here is how to simplify this code using the \p copy_pixels algorithm: \code template <typename SRC_VIEW, typename DST_IMG> void create_with_margin(const SRC_VIEW& src, int k, DST_IMG& result) { resize_clobber_image(result, src.width()+2*k, src.height()+2*k); copy_pixels(src, subimage_view(view(result), k,k,src.width(),src.height())); } \endcode (Note also that \p resize_clobber_image is more efficient than \p operator=, as it uses \p std::swap). Not only does the above example work for planar and interleaved images of any color space and pixel depth; it is also quite fast. GIL overrides \p std::copy - when called on two identical interleaved images with no padding at the end of rows, it simply does a \p memmove. For planar images it does \p memmove for each channel. If one of the images has padding, (as in our case) it will try to do \p memmove for each row. When an image has no padding, it will use its lightweight horizontal iterator (as opposed to the more complex 1D image iterator that has to check for the end of rows). It choses the fastest method, taking into account both static and run-time parameters. \subsection GDIExample Transforming One Image Format to Another Suppose you need to display an image on the screen using Windows GDI. GDI accepts images as 8-bit BGR interleaved, upside-down with 4-byte row alignment. Converting an image from any format to any other is as simple as creating an empty image of the target format and copying the pixels: \code template <typename VIEW> void create_GDI_compatible(const VIEW& src, bgr8_image& result) { bgr8_image tmp(src.dimensions(), 4); // WinGDI wants 8-bit BGR with 4-byte row alignment copy_pixels(color_convert_view<bgr8_pixel>(flipud_view(src)), tmp); swap(result, tmp); } \endcode We can use \p copy_and_convert_pixels instead. In addition to simplifying the code, it is more efficient, as it bypasses color conversion when both the color space is already RGB (or related, like BGR) and the channel depth is already 8-bit: \code template <typename VIEW> void create_GDI_compatible(const VIEW& src, bgr8_image& result) { bgr8_image tmp(src.dimensions(), 4); // WinGDI wants 8-bit BGR with 4-byte row alignment copy_and_convert_pixels(flipud_view(src), tmp); swap(result, tmp); } \endcode Here is how to make our algorithm work for run-time specified views. First we need to wrap it into a function object whose application operator takes just the templated view: \code namespace detail { struct create_GDI_compatible_fnobj { bgr8_image& _result; create_GDI_compatible_fnobj(bgr8_image& result) : _result(result) {} typedef void result_type; // required typedef template <typename VIEW> result_type operator()(const VIEW& src) { create_GDI_compatible(src, _result); } }; } \endcode (Normally we use the return type of the application operator to return the result, which would simplify the code. However, images are expensive to return by value.) Now we need to provide an overload that takes GIL's variant, which will hold run-time instantiated view: \code template <typename IVCS> // Models Image View Concept Space void create_GDI_compatible(const variant<IVCS>& src, bgr8_image& result) { detail::create_GDI_compatible_fnobj fnobj(result); src.apply_visitor(fnobj); } \endcode Now we can use our algorithm with both compile-time specified views (like \p cmyk16_planar_view) or run-time specified views (like \p any_view). */ --- NEW FILE: design_guide.dox --- //////////////////////////////////////////////////////////////////////////////////////// /// \file /// \brief Doxygen documentation /// \author Lubomir Bourdev and Hailin Jin \n /// Adobe Systems Incorporated /// /// //////////////////////////////////////////////////////////////////////////////////////// /** \page GILDesignGuide Generic Image Library Design Guide \author Lubomir Bourdev (lbo...@ad...) and Hailin Jin (hl...@ad...) \n Adobe Systems Incorporated \version 1.0 \date January 10, 2006 <p>This document describes the design of the Generic Image Library, a C++ image-processing library that abstracts image representation from algorithms on images. [...2032 lines suppressed...] \li <b> Performance.</b> Speed has been instrumental to the design of the library. The generic algorithms provided in the library are comparable in speed to hand-coding the algorithm for a specific image type. \li <b> Flexibility.</b> Compile-type parameter resolution results in faster code, but severely limits code flexibility. The library allows for any image parameter to be specified at run time, at a minor performance cost. \li <b> Extensibility.</b> It is easy to extend the library with new color spaces and image types. Library extensions typically require no changes to the library core; at the same time existing image algorithms apply to new color spaces and image types. \li <b> Compatibility.</b> The library is designed as an STL and Boost complement. Generic STL algorithms can be used for pixel manipulation, and they are specifically targeted for optimization. The library works with existing raw pixel data from another image library and can even be integrated into a third-party reference counting mechanism. <hr> \section AcknowledgementsDG 16. Acknowledgements - <b>Jon Brandt</b>, <b>Mark Ruzon</b> and <b>Paul McJones</b> spent significant time reviewing the library and documentation and provided valuable feedback. - <b>Alex Stepanov</b>'s class has directly inspired this project. Alex's "start from the inside" and "bottom up" principles have been applied throughout the design. - <b>Sean Parent</b> and Alex Stepanov suggested splitting the image into a 'container' and 'range' classes */ |