LineView.h
1 /* Copyright (C) 2015 Marc Boris Duerner
2 
3  This library is free software; you can redistribute it and/or
4  modify it under the terms of the GNU Lesser General Public
5  License as published by the Free Software Foundation; either
6  version 2.1 of the License, or (at your option) any later version.
7 
8  As a special exception, you may use this file as part of a free
9  software library without restriction. Specifically, if other files
10  instantiate templates or use macros or inline functions from this
11  file, or you compile this file and link it with other files to
12  produce an executable, this file does not by itself cause the
13  resulting executable to be covered by the GNU General Public
14  License. This exception does not however invalidate any other
15  reasons why the executable file might be covered by the GNU Library
16  General Public License.
17 
18  This library is distributed in the hope that it will be useful,
19  but WITHOUT ANY WARRANTY; without even the implied warranty of
20  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21  Lesser General Public License for more details.
22 
23  You should have received a copy of the GNU Lesser General Public
24  License along with this library; if not, write to the Free Software
25  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
26  MA 02110-1301 USA
27 */
28 
29 #ifndef PT_GFX_LINE_VIEW_H
30 #define PT_GFX_LINE_VIEW_H
31 
32 #include <Pt/Gfx/Api.h>
33 #include <Pt/Gfx/View.h>
34 #include <Pt/Gfx/Span.h>
35 #include <Pt/Types.h>
36 
37 #include <cstddef>
38 #include <cassert>
39 
40 namespace Pt {
41 
42 namespace Gfx {
43 
44 template <typename FormatT, typename TraitsT>
45 class LineIterator;
46 
47 template <typename FormatT, typename TraitsT>
48 class ConstLineIterator;
49 
50 
51 template <typename FormatT, typename TraitsT>
52 class LineIterator
53 {
54  public:
55  typedef FormatT Format;
56  typedef TraitsT Traits;
57 
58  public:
59  using value_type = Span<Format, Traits>;
60  using difference_type = std::ptrdiff_t;
61  using pointer = value_type*;
62  using reference = value_type&;
63  using iterator_category = std::forward_iterator_tag;
64 
65  public:
66  LineIterator(BasicView<Format, Traits>& view, Pt::ssize_t x, Pt::ssize_t y)
67  : _span(view, x, y, view.width())
68  { }
69 
70  reference operator*()
71  { return _span; }
72 
73  const reference operator*() const
74  { return _span; }
75 
76  pointer operator->()
77  { return &_span; }
78 
79  const value_type* operator->() const
80  { return &_span; }
81 
82  LineIterator& operator++() noexcept
83  {
84  _span.advanceLines(1);
85  return *this;
86  }
87 
88  LineIterator operator++(int) noexcept
89  {
90  LineIterator it(*this);
91  ++*this;
92  return it;
93  }
94 
95  LineIterator& operator+=(Pt::ssize_t n)
96  {
97  _span.advanceLines(n);
98  return *this;
99  }
100 
101  bool operator==(const LineIterator& other) const noexcept
102  {
103  return _span.front().equals( other->front() );
104  }
105 
106  bool operator!=(const LineIterator& other) const noexcept
107  {
108  return ! (*this == other);
109  }
110 
111  private:
112  Span<Format, Traits> _span;
113 };
114 
115 
116 template <typename FormatT, typename TraitsT>
117 class ConstLineIterator
118 {
119  public:
120  typedef FormatT Format;
121  typedef TraitsT Traits;
122 
123  public:
124  using value_type = ConstSpan<Format, Traits>;
125  using difference_type = std::ptrdiff_t;
126  using pointer = const value_type*;
127  using reference = const value_type&;
128  using iterator_category = std::forward_iterator_tag;
129 
130  public:
131  ConstLineIterator(const BasicConstView<Format, Traits>& view, Pt::ssize_t x, Pt::ssize_t y)
132  : _span(view, x, y, view.width())
133  { }
134 
135  const reference operator*() const
136  { return _span; }
137 
138  const pointer operator->() const
139  { return &_span; }
140 
141  ConstLineIterator& operator++() noexcept
142  {
143  _span.advanceLines(1);
144  return *this;
145  }
146 
147  ConstLineIterator operator++(int) noexcept
148  {
149  ConstLineIterator it(*this);
150  ++*this;
151  return it;
152  }
153 
154  ConstLineIterator& operator+=(Pt::ssize_t n)
155  {
156  _span.advanceLines(n);
157  return *this;
158  }
159 
160  bool operator==(const ConstLineIterator& other) const noexcept
161  {
162  return _span.front().equals( other->front() );
163  }
164 
165  bool operator!=(const ConstLineIterator& other) const noexcept
166  {
167  return ! (*this == other);
168  }
169 
170  private:
171  ConstSpan<Format, Traits> _span;
172 };
173 
174 
175 template <typename FormatT, typename TraitsT>
176 class BasicLineView
177 {
178  public:
179  typedef FormatT Format;
180  typedef TraitsT Traits;
181 
182  typedef LineIterator<Format, Traits> Iterator;
183 
184  public:
185  explicit BasicLineView( const Format& format = FormatT::get() );
186 
187  BasicLineView(Pt::uint8_t* data, Pt::ssize_t width, Pt::ssize_t height,
188  Pt::ssize_t padding, const Format& format = FormatT::get());
189 
190  template <typename T>
191  explicit BasicLineView(T& source);
192 
193  template <typename T>
194  BasicLineView(T& source, Int x, Int y, Int w, Int h);
195 
196  BasicLineView& operator=(const BasicLineView&) = default;
197 
198  Pt::uint8_t* data()
199  { return _view.data(); }
200 
201  const Pt::uint8_t* data() const
202  { return _view.data(); }
203 
204  Pt::ssize_t width() const
205  { return _view.width(); }
206 
207  Pt::ssize_t height() const
208  { return _view.height(); }
209 
210  Pt::ssize_t stride() const
211  { return _view.stride(); }
212 
213  const Format& format() const
214  { return _view.format(); }
215 
216  Pt::ssize_t pixelStride() const
217  { return _view.pixelStride(); }
218 
219  Pt::ssize_t padding() const
220  { return _view.padding(); }
221 
222  Iterator line(Pt::ssize_t y)
223  { return Iterator(_view, 0, y); }
224 
225  Iterator begin()
226  { return Iterator(_view, 0, 0); }
227 
228  Iterator end()
229  { return Iterator(_view, 0, _view.height()); }
230 
231  private:
232  BasicView<Format, Traits> _view;
233 };
234 
235 
236 template <typename FormatT, typename TraitsT>
237 class BasicConstLineView
238 {
239  public:
240  typedef FormatT Format;
241  typedef TraitsT Traits;
242 
243  typedef ConstLineIterator<Format, Traits> Iterator;
244 
245  public:
246  explicit BasicConstLineView( const Format& format = FormatT::get() );
247 
248  BasicConstLineView(const Pt::uint8_t* data, Pt::ssize_t width, Pt::ssize_t height,
249  Pt::ssize_t padding, const Format& format = FormatT::get());
250 
251  template <typename T>
252  explicit BasicConstLineView(const T& source);
253 
254  template <typename T>
255  BasicConstLineView(const T& source, Int x, Int y, Int w, Int h);
256 
257  BasicConstLineView& operator=(const BasicConstLineView&) = default;
258 
259  const Pt::uint8_t* data() const
260  { return _view.data(); }
261 
262  Pt::ssize_t width() const
263  { return _view.width(); }
264 
265  Pt::ssize_t height() const
266  { return _view.height(); }
267 
268  Pt::ssize_t stride() const
269  { return _view.stride(); }
270 
271  const Format& format() const
272  { return _view.format(); }
273 
274  Pt::ssize_t pixelStride() const
275  { return _view.pixelStride(); }
276 
277  Pt::ssize_t padding() const
278  { return _view.padding(); }
279 
280  Iterator line(Pt::ssize_t y) const
281  { return Iterator(_view, 0, y); }
282 
283  Iterator begin() const
284  { return Iterator(_view, 0, 0); }
285 
286  Iterator end() const
287  { return Iterator(_view, 0, _view.height()); }
288 
289  private:
290  BasicConstView<Format, Traits> _view;
291 };
292 
293 
294 template <typename T>
295 BasicLineView<typename T::Format,
296  typename T::Traits> lineView(T& source)
297 {
298  return BasicLineView<typename T::Format, typename T::Traits>(source);
299 }
300 
301 
302 template <typename T>
303 BasicConstLineView<typename T::Format,
304  typename T::Traits> lineView(const T& source)
305 {
306  return BasicConstLineView<typename T::Format, typename T::Traits>(source);
307 }
308 
309 
310 template <typename T>
311 BasicLineView<typename T::Format,
312  typename T::Traits> lineView(T& source, Int x, Int y, Int w, Int h)
313 {
314  return BasicLineView<typename T::Format, typename T::Traits>(source, x, y, w, h);
315 }
316 
317 
318 template <typename T>
319 BasicConstLineView<typename T::Format,
320  typename T::Traits> lineView(const T& source, Int x, Int y, Int w, Int h)
321 {
322  return BasicConstLineView<typename T::Format, typename T::Traits>(source, x, y, w, h);
323 }
324 
325 
326 template <typename FormatT, typename TraitsT = ImageTraits<FormatT> >
327 BasicLineView<FormatT,
328  TraitsT> lineView(Pt::uint8_t* data, Pt::ssize_t width,
329  Pt::ssize_t height, Pt::ssize_t padding = 0)
330 {
331  return BasicLineView<FormatT, TraitsT>(data, width, height, padding, FormatT::get());
332 }
333 
334 
335 template <typename FormatT, typename TraitsT = ImageTraits<FormatT> >
336 BasicConstLineView<FormatT,
337  TraitsT> lineView(const Pt::uint8_t* data, Pt::ssize_t width,
338  Pt::ssize_t height, Pt::ssize_t padding = 0)
339 {
340  return BasicConstLineView<FormatT, TraitsT>(data, width, height, padding, FormatT::get());
341 }
342 
343 
344 template <typename T>
345 BasicLineView<typename T::Format,
346  ImageTraitsF> lineViewF(T& source)
347 {
348  return BasicLineView<typename T::Format, ImageTraitsF>(source);
349 }
350 
351 
352 template <typename T>
353 BasicConstLineView<typename T::Format,
354  ImageTraitsF> lineViewF(const T& source)
355 {
356  return BasicConstLineView<typename T::Format, ImageTraitsF>(source);
357 }
358 
359 
360 template <typename T>
361 BasicLineView<typename T::Format,
362  ImageTraitsF> lineViewF(T& source, Int x, Int y, Int w, Int h)
363 {
364  return BasicLineView<typename T::Format, ImageTraitsF>(source, x, y, w, h);
365 }
366 
367 
368 template <typename T>
369 BasicConstLineView<typename T::Format,
370  ImageTraitsF> lineViewF(const T& source, Int x, Int y, Int w, Int h)
371 {
372  return BasicConstLineView<typename T::Format, ImageTraitsF>(source, x, y, w, h);
373 }
374 
375 
376 inline LineViewF lineViewF(Pt::uint8_t* data, Pt::ssize_t width,
377  Pt::ssize_t height, Pt::ssize_t padding,
378  const ImageFormat& format)
379 {
380  return LineViewF(data, width, height, padding, format);
381 }
382 
383 
384 inline ConstLineViewF lineViewF(const Pt::uint8_t* data, Pt::ssize_t width,
385  Pt::ssize_t height, Pt::ssize_t padding,
386  const ImageFormat& format)
387 {
388  return ConstLineViewF(data, width, height, padding, format);
389 }
390 
391 } // namespace
392 
393 } // namespace
394 
395 #endif
396 
397 #include <Pt/Gfx/LineView.hpp>
uint_type uint8_t
Unsigned 8-bit integer type.
Definition: Types.h:18