Boost GIL


planar_pixel_iterator.hpp
1//
2// Copyright 2005-2007 Adobe Systems Incorporated
3//
4// Distributed under the Boost Software License, Version 1.0
5// See accompanying file LICENSE_1_0.txt or copy at
6// http://www.boost.org/LICENSE_1_0.txt
7//
8#ifndef BOOST_GIL_PLANAR_PIXEL_ITERATOR_HPP
9#define BOOST_GIL_PLANAR_PIXEL_ITERATOR_HPP
10
11#include <boost/gil/pixel.hpp>
12#include <boost/gil/step_iterator.hpp>
13#include <boost/gil/detail/mp11.hpp>
14
15#include <boost/stl_interfaces/iterator_interface.hpp>
16
17#include <iterator>
18#include <type_traits>
19
20namespace boost { namespace gil {
21
22//forward declaration (as this file is included in planar_pixel_reference.hpp)
23template <typename ChannelReference, typename ColorSpace>
24struct planar_pixel_reference;
25
30
34
42template <typename ChannelPtr, typename ColorSpace>
44 :
45 stl_interfaces::iterator_interface<
46#if !BOOST_STL_INTERFACES_USE_DEDUCED_THIS
47 planar_pixel_iterator<ChannelPtr, ColorSpace>,
48#endif
49 std::random_access_iterator_tag,
50 pixel<typename std::iterator_traits<ChannelPtr>::value_type,layout<ColorSpace>>,
51 planar_pixel_reference<typename std::iterator_traits<ChannelPtr>::reference, ColorSpace> const
52 >,
53 detail::homogeneous_color_base
54 <
55 ChannelPtr,
56 layout<ColorSpace>,
57 mp11::mp_size<ColorSpace>::value
58 >
59{
60private:
61 using parent_t = stl_interfaces::iterator_interface<
62#if !BOOST_STL_INTERFACES_USE_DEDUCED_THIS
64#endif
65 std::random_access_iterator_tag,
68 >;
69
70 using color_base_parent_t = detail::homogeneous_color_base
71 <
72 ChannelPtr,
74 mp11::mp_size<ColorSpace>::value
75 >;
76
77 using channel_t = typename std::iterator_traits<ChannelPtr>::value_type;
78
79public:
80 using value_type = typename parent_t::value_type;
81 using reference = typename parent_t::reference;
82 using difference_type = typename parent_t::difference_type;
83 using iterator_category = typename parent_t::iterator_concept;
84
85 planar_pixel_iterator() : color_base_parent_t(0) {}
86 planar_pixel_iterator(bool) {} // constructor that does not fill with zero (for performance)
87
88 planar_pixel_iterator(const ChannelPtr& v0, const ChannelPtr& v1) : color_base_parent_t(v0,v1) {}
89 planar_pixel_iterator(const ChannelPtr& v0, const ChannelPtr& v1, const ChannelPtr& v2) : color_base_parent_t(v0,v1,v2) {}
90 planar_pixel_iterator(const ChannelPtr& v0, const ChannelPtr& v1, const ChannelPtr& v2, const ChannelPtr& v3) : color_base_parent_t(v0,v1,v2,v3) {}
91 planar_pixel_iterator(const ChannelPtr& v0, const ChannelPtr& v1, const ChannelPtr& v2, const ChannelPtr& v3, const ChannelPtr& v4) : color_base_parent_t(v0,v1,v2,v3,v4) {}
92
93 template <typename IC1,typename C1>
94 planar_pixel_iterator(const planar_pixel_iterator<IC1,C1>& ptr) : color_base_parent_t(ptr) {}
95
99 template <typename P>
100 planar_pixel_iterator(P* pix) : color_base_parent_t(pix, true) {
101 function_requires<PixelsCompatibleConcept<P,value_type> >();
102 }
103
104 struct address_of { template <typename T> T* operator()(T& t) { return &t; } };
105 template <typename P>
106 planar_pixel_iterator& operator=(P* pix) {
107 function_requires<PixelsCompatibleConcept<P,value_type> >();
108 static_transform(*pix,*this, address_of());
109
110 // PERFORMANCE_CHECK: Compare to this:
111 //this->template semantic_at_c<0>()=&pix->template semantic_at_c<0>();
112 //this->template semantic_at_c<1>()=&pix->template semantic_at_c<1>();
113 //this->template semantic_at_c<2>()=&pix->template semantic_at_c<2>();
114 return *this;
115 }
116
117 constexpr auto operator*() const noexcept -> reference { return dereference(); }
118
119 constexpr auto operator+=(difference_type d) -> planar_pixel_iterator& { advance(d); return *this; }
120
121 constexpr auto operator++() noexcept -> planar_pixel_iterator& { increment(); return *this; }
122 constexpr auto operator--() noexcept -> planar_pixel_iterator& { decrement(); return *this; }
123
124 constexpr auto operator++(int) noexcept -> planar_pixel_iterator { auto tmp = *this; increment(); return tmp; }
125 constexpr auto operator--(int) noexcept -> planar_pixel_iterator { auto tmp = *this; decrement(); return tmp; }
126
127 constexpr auto operator-(const planar_pixel_iterator& other) const noexcept { return -distance_to(other); }
128
129 constexpr bool operator==(const planar_pixel_iterator& other) const noexcept { return equal(other); }
130
131private:
132 friend struct boost::stl_interfaces::access;
133
134 void increment() { static_transform(*this,*this,detail::inc<ChannelPtr>()); }
135 void decrement() { static_transform(*this,*this,detail::dec<ChannelPtr>()); }
136 void advance(std::ptrdiff_t d){ static_transform(*this,*this,std::bind(detail::plus_asymmetric<ChannelPtr,std::ptrdiff_t>(),std::placeholders::_1,d)); }
137 reference dereference() const { return this->template deref<reference>(); }
138
139 std::ptrdiff_t distance_to(const planar_pixel_iterator& it) const { return gil::at_c<0>(it)-gil::at_c<0>(*this); }
140 bool equal(const planar_pixel_iterator& it) const { return gil::at_c<0>(*this)==gil::at_c<0>(it); }
141};
142
143namespace detail {
144template <typename I>
145struct channel_iterator_is_mutable : std::true_type {};
146
147template <typename I>
148struct channel_iterator_is_mutable<I const*> : std::false_type {};
149
150} // namespace detail
151
152template <typename IC, typename C>
153struct const_iterator_type<planar_pixel_iterator<IC,C> > {
154private:
155 using channel_t = typename std::iterator_traits<IC>::value_type;
156public:
157 using type = planar_pixel_iterator<typename channel_traits<channel_t>::const_pointer,C>;
158};
159
160// The default implementation when the iterator is a C pointer is to use the standard constness semantics
161template <typename IC, typename C>
162struct iterator_is_mutable<planar_pixel_iterator<IC,C> > : public detail::channel_iterator_is_mutable<IC> {};
163
165// ColorBasedConcept
167
168template <typename IC, typename C, int K>
169struct kth_element_type<planar_pixel_iterator<IC, C>, K>
170{
171 using type = IC;
172};
173
174template <typename IC, typename C, int K>
175struct kth_element_reference_type<planar_pixel_iterator<IC, C>, K>
176 : std::add_lvalue_reference<IC> {};
177
178template <typename IC, typename C, int K>
179struct kth_element_const_reference_type<planar_pixel_iterator<IC, C>, K>
180 : std::add_lvalue_reference<typename std::add_const<IC>::type>
181{};
182
184// HomogeneousPixelBasedConcept
186
187template <typename IC, typename C>
188struct color_space_type<planar_pixel_iterator<IC,C>>
189{
190 using type = C;
191};
192
193template <typename IC, typename C>
194struct channel_mapping_type<planar_pixel_iterator<IC, C>>
195 : channel_mapping_type<typename planar_pixel_iterator<IC,C>::value_type>
196{};
197
198template <typename IC, typename C>
199struct is_planar<planar_pixel_iterator<IC, C>> : std::true_type {};
200
201template <typename IC, typename C>
202struct channel_type<planar_pixel_iterator<IC, C>>
203{
204 using type = typename std::iterator_traits<IC>::value_type;
205};
206
208// MemoryBasedIteratorConcept
210
211template <typename IC, typename C>
212inline auto memunit_step(planar_pixel_iterator<IC,C> const&)
213 -> std::ptrdiff_t
214{
215 return sizeof(typename std::iterator_traits<IC>::value_type);
216}
217
218template <typename IC, typename C>
219inline auto memunit_distance(planar_pixel_iterator<IC,C> const& p1, planar_pixel_iterator<IC,C> const& p2)
220 -> std::ptrdiff_t
221{
222 return memunit_distance(gil::at_c<0>(p1),gil::at_c<0>(p2));
223}
224
225template <typename IC>
226struct memunit_advance_fn {
227 memunit_advance_fn(std::ptrdiff_t diff) : _diff(diff) {}
228 IC operator()(const IC& p) const { return memunit_advanced(p,_diff); }
229
230 std::ptrdiff_t _diff;
231};
232
233template <typename IC, typename C>
234inline void memunit_advance(planar_pixel_iterator<IC,C>& p, std::ptrdiff_t diff) {
235 static_transform(p, p, memunit_advance_fn<IC>(diff));
236}
237
238template <typename IC, typename C>
239inline auto memunit_advanced(planar_pixel_iterator<IC,C> const& p, std::ptrdiff_t diff)
240 -> planar_pixel_iterator<IC,C>
241{
242 planar_pixel_iterator<IC,C> ret=p;
243 memunit_advance(ret, diff);
244 return ret;
245}
246
247template <typename ChannelPtr, typename ColorSpace>
248inline auto memunit_advanced_ref(planar_pixel_iterator<ChannelPtr,ColorSpace> const& ptr, std::ptrdiff_t diff)
249 -> planar_pixel_reference<typename std::iterator_traits<ChannelPtr>::reference,ColorSpace>
250{
251 return planar_pixel_reference<typename std::iterator_traits<ChannelPtr>::reference,ColorSpace>(ptr, diff);
252}
253
255// HasDynamicXStepTypeConcept
257
258template <typename IC, typename C>
259struct dynamic_x_step_type<planar_pixel_iterator<IC,C> > {
260 using type = memory_based_step_iterator<planar_pixel_iterator<IC,C>>;
261};
262} } // namespace boost::gil
263
264#endif
defined(BOOST_NO_CXX17_HDR_MEMORY_RESOURCE)
Definition algorithm.hpp:36
Represents a color space and ordering of channels in memory.
Definition utilities.hpp:265
Represents a pixel value (a container of channels). Models: HomogeneousColorBaseValueConcept,...
Definition pixel.hpp:106
An iterator over planar pixels. Models HomogeneousColorBaseConcept, PixelIteratorConcept,...
Definition planar_pixel_iterator.hpp:59
planar_pixel_iterator(P *pix)
Definition planar_pixel_iterator.hpp:100
A reference proxy to a planar pixel.
Definition planar_pixel_reference.hpp:46