PixelBase.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_PIXELBASE_H
30 #define PT_GFX_PIXELBASE_H
31 
32 #include <Pt/Gfx/Api.h>
33 #include <Pt/Gfx/ViewBase.h>
34 #include <Pt/Gfx/Color.h>
35 #include <Pt/Types.h>
36 #include <typeinfo>
37 #include <utility>
38 
39 namespace Pt {
40 
41 namespace Gfx {
42 
43 class PixelStorage;
44 
46 // PixelBase
48 
51 class PixelBase
52 {
53  public:
54  PixelBase(const ViewBase& view, Pt::uint8_t* base, Pt::ssize_t x, Pt::ssize_t y)
55  : _view(&view)
56  , _base(base)
57  { }
58 
59  virtual ~PixelBase()
60  { }
61 
62  const ViewBase& view() const
63  { return *_view; }
64 
65  Pt::uint8_t* base()
66  { return _base; }
67 
68  const Pt::uint8_t* base() const
69  { return _base; }
70 
71  void advance()
72  {
73  _base = onAdvance();
74  }
75 
76  void advance(Pt::ssize_t n)
77  {
78  _base = onAdvance(n);
79  }
80 
81  void skipPadding()
82  {
83  _base = onSkipPadding();
84  }
85 
86  void advanceLines(Pt::ssize_t n)
87  {
88  _base = onAdvanceLines(n);
89  }
90 
91  template <typename ColorT>
92  ColorT getColor() const;
93 
94  void getColors(ColorF* colors, std::size_t length) const
95  {
96  onGetColors(colors, length);
97  }
98 
99  void getColors(Color* colors, std::size_t length) const
100  {
101  onGetColors(colors, length);
102  }
103 
104  void assign(const ColorF& color)
105  {
106  onSetColor(color);
107  }
108 
109  void assign(const Color& color)
110  {
111  onSetColor(color);
112  }
113 
114  void assign(const Color* colors, std::size_t length)
115  {
116  onAssign(colors, length);
117  }
118 
119  void assign(const ColorF* colors, std::size_t length)
120  {
121  onAssign(colors, length);
122  }
123 
124  bool assign(const PixelBase& p, std::size_t length)
125  {
126  return onAssignPixels(p, length);
127  }
128 
129  void fill(std::size_t n, const ColorF& color)
130  {
131  onFillColor(n, color);
132  }
133 
134  void fill(std::size_t n, const Color& color)
135  {
136  onFillColor(n, color);
137  }
138 
139  bool copy(PixelBase& p, std::size_t length) const
140  {
141  return onCopyPixels(p, length);
142  }
143 
144  PixelBase* clone(PixelStorage& store) const
145  {
146  return onClone(store);
147  }
148 
149  const std::type_info& getType() const
150  {
151  return onGetType();
152  }
153 
154  template <typename T>
155  T* tryCast()
156  { return getType() == typeid(T) ? static_cast<T*>(this) : nullptr; }
157 
158  template <typename T>
159  const T* tryCast() const
160  { return getType() == typeid(T) ? static_cast<const T*>(this) : nullptr; }
161 
162  protected:
163  virtual PixelBase* onClone(PixelStorage& store) const
164  { return 0; }
165 
166  virtual const std::type_info& onGetType() const = 0;
167 
168  virtual Pt::uint8_t* onAdvance() = 0;
169 
170  virtual Pt::uint8_t* onSkipPadding()
171  { return 0; }
172 
173  virtual Pt::uint8_t* onAdvance(Pt::ssize_t n) = 0;
174 
175  virtual Pt::uint8_t* onAdvanceLines(Pt::ssize_t n)
176  { return 0; }
177 
178  virtual ColorF onGetColorF() const = 0;
179 
180  virtual Color onGetColor() const = 0;
181 
182  virtual void onGetColors(ColorF* colors, std::size_t length) const = 0;
183 
184  virtual void onGetColors(Color* colors, std::size_t length) const = 0;
185 
186  virtual void onSetColor(const ColorF& color)
187  {
188  onFillColor(1, color);
189  }
190 
191  virtual void onSetColor(const Color& color)
192  {
193  onFillColor(1, color);
194  }
195 
196  virtual void onAssign(const Color* colors, std::size_t length) = 0;
197 
198  virtual void onAssign(const ColorF* colors, std::size_t length) = 0;
199 
200  virtual void onFillColor(std::size_t n, const ColorF& color) = 0;
201 
202  virtual void onFillColor(std::size_t n, const Color& color) = 0;
203 
204  virtual bool onAssignPixels(const PixelBase& p, std::size_t length)
205  { return false; }
206 
207  virtual bool onCopyPixels(PixelBase& p, std::size_t length) const
208  { return false; }
209 
210  private:
211  const ViewBase* _view;
212  Pt::uint8_t* _base;
213 };
214 
215 
216 template <typename ColorT>
217 inline ColorT PixelBase::getColor() const
218 {
219  return this->onGetColorF();
220 }
221 
222 
223 template <>
224 inline ColorF PixelBase::getColor<ColorF>() const
225 {
226  return this->onGetColorF();
227 }
228 
229 
230 template <>
231 inline Color PixelBase::getColor<Color>() const
232 {
233  return this->onGetColor();
234 }
235 
237 // PixelStorage
239 
240 class PixelStorage
241 {
242  public:
243  static const std::size_t MaxSize = sizeof(void*) * 16;
244 
245  public:
246  template <typename T, typename... Args>
247  T* create(Args&&... args)
248  {
249  static_assert(sizeof(T) <= PixelStorage::MaxSize,
250  "insufficient pixel storage");
251 
252  return new (&_data.mem) T(std::forward<Args>(args)...);
253  }
254 
255  private:
256  union Data
257  {
258  Data()
259  : ptr(0)
260  { }
261 
262  alignas(PixelBase) char mem[PixelStorage::MaxSize];
263  void* ptr;
264  void (*_align0)();
265  std::size_t _align1;
266  long double _align2;
267  } _data;
268 };
269 
270 } // namespace
271 
272 } // namespace
273 
274 #endif
Standard color type.
Definition: Color.h:46
Definition: Color.h:136
uint_type uint8_t
Unsigned 8-bit integer type.
Definition: Types.h:18
Pixel base class.
Definition: PixelBase.h:51