| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299 | //// Copyright 2005-2007 Adobe Systems Incorporated//// Distributed under the Boost Software License, Version 1.0// See accompanying file LICENSE_1_0.txt or copy at// http://www.boost.org/LICENSE_1_0.txt//#ifndef BOOST_GIL_CONCEPTS_PIXEL_HPP#define BOOST_GIL_CONCEPTS_PIXEL_HPP#include <boost/gil/concepts/basic.hpp>#include <boost/gil/concepts/channel.hpp>#include <boost/gil/concepts/color.hpp>#include <boost/gil/concepts/color_base.hpp>#include <boost/gil/concepts/concept_check.hpp>#include <boost/gil/concepts/fwd.hpp>#include <boost/gil/concepts/pixel_based.hpp>#include <boost/gil/concepts/detail/type_traits.hpp>#include <boost/gil/detail/mp11.hpp>#include <cstddef>#include <type_traits>#if defined(BOOST_CLANG)#pragma clang diagnostic push#pragma clang diagnostic ignored "-Wunknown-pragmas"#pragma clang diagnostic ignored "-Wunused-local-typedefs"#endif#if defined(BOOST_GCC) && (BOOST_GCC >= 40900)#pragma GCC diagnostic push#pragma GCC diagnostic ignored "-Wunused-local-typedefs"#endifnamespace boost { namespace gil {/// \brief Pixel concept - A color base whose elements are channels/// \ingroup PixelConcept/// \code/// concept PixelConcept<typename P> : ColorBaseConcept<P>, PixelBasedConcept<P>/// {///     where is_pixel<P>::value == true;///     // where for each K [0..size<P>::value - 1]:///     //      ChannelConcept<kth_element_type<P, K>>;//////     typename P::value_type;///         where PixelValueConcept<value_type>;///     typename P::reference;///         where PixelConcept<reference>;///     typename P::const_reference;///         where PixelConcept<const_reference>;///     static const bool P::is_mutable;//////     template <PixelConcept P2> where { PixelConcept<P, P2> }///         P::P(P2);///     template <PixelConcept P2> where { PixelConcept<P, P2> }///         bool operator==(const P&, const P2&);///     template <PixelConcept P2> where { PixelConcept<P, P2> }///         bool operator!=(const P&, const P2&);/// };/// \endcodetemplate <typename P>struct PixelConcept{    void constraints()    {        gil_function_requires<ColorBaseConcept<P>>();        gil_function_requires<PixelBasedConcept<P>>();        static_assert(is_pixel<P>::value, "");        static const bool is_mutable = P::is_mutable;        ignore_unused_variable_warning(is_mutable);        using value_type = typename P::value_type;        // TODO: Is the cyclic dependency intentional? --mloskot        // gil_function_requires<PixelValueConcept<value_type>>();        using reference = typename P::reference;        gil_function_requires<PixelConcept            <                typename detail::remove_const_and_reference<reference>::type            >>();        using const_reference = typename P::const_reference;        gil_function_requires<PixelConcept            <                typename detail::remove_const_and_reference<const_reference>::type            >>();    }};/// \brief Pixel concept that allows for changing its channels/// \ingroup PixelConcept/// \code/// concept MutablePixelConcept<PixelConcept P> : MutableColorBaseConcept<P>/// {///     where is_mutable==true;/// };/// \endcodetemplate <typename P>struct MutablePixelConcept{    void constraints()    {        gil_function_requires<PixelConcept<P>>();        static_assert(P::is_mutable, "");    }};/// \brief Homogeneous pixel concept/// \ingroup PixelConcept/// \code/// concept HomogeneousPixelConcept<PixelConcept P>///     : HomogeneousColorBaseConcept<P>, HomogeneousPixelBasedConcept<P>/// {///     P::template element_const_reference_type<P>::type operator[](P p, std::size_t i) const///     {///         return dynamic_at_c(p,i);/// }/// };/// \endcodetemplate <typename P>struct HomogeneousPixelConcept{    void constraints()    {        gil_function_requires<PixelConcept<P>>();        gil_function_requires<HomogeneousColorBaseConcept<P>>();        gil_function_requires<HomogeneousPixelBasedConcept<P>>();        p[0];    }    P p;};/// \brief Homogeneous pixel concept that allows for changing its channels/// \ingroup PixelConcept/// \code/// concept MutableHomogeneousPixelConcept<HomogeneousPixelConcept P>///     : MutableHomogeneousColorBaseConcept<P>/// {///     P::template element_reference_type<P>::type operator[](P p, std::size_t i)///     {///         return dynamic_at_c(p, i);///     }/// };/// \endcodetemplate <typename P>struct MutableHomogeneousPixelConcept{    void constraints()    {        gil_function_requires<HomogeneousPixelConcept<P>>();        gil_function_requires<MutableHomogeneousColorBaseConcept<P>>();        p[0] = v;        v = p[0];    }    typename P::template element_type<P>::type v;    P p;};/// \brief Pixel concept that is a Regular type/// \ingroup PixelConcept/// \code/// concept PixelValueConcept<PixelConcept P> : Regular<P>/// {///     where SameType<value_type,P>;/// };/// \endcodetemplate <typename P>struct PixelValueConcept{    void constraints()    {        gil_function_requires<PixelConcept<P>>();        gil_function_requires<Regular<P>>();    }};/// \brief Homogeneous pixel concept that is a Regular type/// \ingroup PixelConcept/// \code/// concept HomogeneousPixelValueConcept<HomogeneousPixelConcept P> : Regular<P>/// {///     where SameType<value_type,P>;/// };/// \endcodetemplate <typename P>struct HomogeneousPixelValueConcept{    void constraints()    {        gil_function_requires<HomogeneousPixelConcept<P>>();        gil_function_requires<Regular<P>>();        static_assert(std::is_same<P, typename P::value_type>::value, "");    }};namespace detail {template <typename P1, typename P2, int K>struct channels_are_pairwise_compatible    : mp11::mp_and    <        channels_are_pairwise_compatible<P1, P2, K - 1>,        channels_are_compatible        <            typename kth_semantic_element_reference_type<P1, K>::type,            typename kth_semantic_element_reference_type<P2, K>::type        >    >{};template <typename P1, typename P2>struct channels_are_pairwise_compatible<P1, P2, -1> : std::true_type {};} // namespace detail/// \ingroup PixelAlgorithm/// \brief Returns whether two pixels are compatible/// Pixels are compatible if their channels and color space types are compatible./// Compatible pixels can be assigned and copy constructed from one another./// \tparam P1 Models PixelConcept/// \tparam P2 Models PixelConcepttemplate <typename P1, typename P2>struct pixels_are_compatible    : mp11::mp_and        <            typename color_spaces_are_compatible            <                typename color_space_type<P1>::type,                typename color_space_type<P2>::type            >::type,            detail::channels_are_pairwise_compatible            <                P1, P2, num_channels<P1>::value - 1            >        >{};/// \ingroup PixelConcept/// \brief  Concept for pixel compatibility/// Pixels are compatible if their channels and color space types are compatible./// Compatible pixels can be assigned and copy constructed from one another./// \tparam P1 Models PixelConcept/// \tparam P2 Models PixelConcept/// \code/// concept PixelsCompatibleConcept<PixelConcept P1, PixelConcept P2>///     : ColorBasesCompatibleConcept<P1,P2> {///     // where for each K [0..size<P1>::value):///     //    ChannelsCompatibleConcept<kth_semantic_element_type<P1,K>::type, kth_semantic_element_type<P2,K>::type>;/// };/// \endcodetemplate <typename P1, typename P2>struct PixelsCompatibleConcept{    void constraints()    {        static_assert(pixels_are_compatible<P1, P2>::value, "");    }};/// \ingroup PixelConcept/// \brief Pixel convertible concept/// Convertibility is non-symmetric and implies that one pixel/// can be converted to another, approximating the color./// Conversion is explicit and sometimes lossy./// \code/// template <PixelConcept SrcPixel, MutablePixelConcept DstPixel>/// concept PixelConvertibleConcept/// {///     void color_convert(const SrcPixel&, DstPixel&);/// };/// \endcodetemplate <typename SrcP, typename DstP>struct PixelConvertibleConcept{    void constraints()    {        gil_function_requires<PixelConcept<SrcP>>();        gil_function_requires<MutablePixelConcept<DstP>>();        color_convert(src, dst);    }    SrcP src;    DstP dst;};}} // namespace boost::gil#if defined(BOOST_CLANG)#pragma clang diagnostic pop#endif#if defined(BOOST_GCC) && (BOOST_GCC >= 40900)#pragma GCC diagnostic pop#endif#endif
 |