24 #ifndef AGG_PIXFMT_GRAY_INCLUDED 25 #define AGG_PIXFMT_GRAY_INCLUDED 28 #include "agg_pixfmt_base.h" 29 #include "agg_rendering_buffer.h" 37 typedef ColorT color_type;
38 typedef typename color_type::value_type value_type;
39 typedef typename color_type::calc_type calc_type;
40 typedef typename color_type::long_type long_type;
46 static AGG_INLINE
void blend_pix(value_type* p,
47 value_type cv, value_type alpha, cover_type cover)
49 blend_pix(p, cv, color_type::mult_cover(alpha, cover));
52 static AGG_INLINE
void blend_pix(value_type* p,
53 value_type cv, value_type alpha)
55 *p = color_type::lerp(*p, cv, alpha);
63 typedef ColorT color_type;
64 typedef typename color_type::value_type value_type;
65 typedef typename color_type::calc_type calc_type;
66 typedef typename color_type::long_type long_type;
71 static AGG_INLINE
void blend_pix(value_type* p,
72 value_type cv, value_type alpha, cover_type cover)
74 blend_pix(p, color_type::mult_cover(cv, cover), color_type::mult_cover(alpha, cover));
77 static AGG_INLINE
void blend_pix(value_type* p,
78 value_type cv, value_type alpha)
80 *p = color_type::prelerp(*p, cv, alpha);
90 typedef typename ColorT::value_type value_type;
94 AGG_INLINE
void operator () (value_type* p)
100 const GammaLut& m_gamma;
109 typedef typename ColorT::value_type value_type;
113 AGG_INLINE
void operator () (value_type* p)
115 *p = m_gamma.inv(*p);
119 const GammaLut& m_gamma;
125 template<
class Blender,
class RenBuf,
unsigned Step = 1,
unsigned Offset = 0>
130 typedef RenBuf rbuf_type;
131 typedef typename rbuf_type::row_data row_data;
132 typedef Blender blender_type;
133 typedef typename blender_type::color_type color_type;
134 typedef int order_type;
135 typedef typename color_type::value_type value_type;
136 typedef typename color_type::calc_type calc_type;
140 pix_width =
sizeof(value_type) * Step,
146 value_type c[num_components];
148 void set(value_type v)
153 void set(
const color_type& color)
158 void get(value_type& v)
const 163 color_type
get()
const 165 return color_type(c[0]);
192 value_type v, value_type a,
195 blender_type::blend_pix(p->c, v, a, cover);
199 AGG_INLINE
void blend_pix(
pixel_type* p, value_type v, value_type a)
201 blender_type::blend_pix(p->c, v, a);
205 AGG_INLINE
void blend_pix(
pixel_type* p,
const color_type& c,
unsigned cover)
207 blender_type::blend_pix(p->c, c.v, c.a, cover);
211 AGG_INLINE
void blend_pix(
pixel_type* p,
const color_type& c)
213 blender_type::blend_pix(p->c, c.v, c.a);
217 AGG_INLINE
void copy_or_blend_pix(
pixel_type* p,
const color_type& c,
unsigned cover)
219 if (!c.is_transparent())
221 if (c.is_opaque() && cover == cover_mask)
227 blend_pix(p, c, cover);
233 AGG_INLINE
void copy_or_blend_pix(
pixel_type* p,
const color_type& c)
235 if (!c.is_transparent())
253 void attach(rbuf_type& rb) { m_rbuf = &rb; }
256 template<
class PixFmt>
257 bool attach(PixFmt& pixf,
int x1,
int y1,
int x2,
int y2)
260 if (r.clip(
rect_i(0, 0, pixf.width()-1, pixf.height()-1)))
262 int stride = pixf.stride();
263 m_rbuf->attach(pixf.pix_ptr(r.x1, stride < 0 ? r.y2 : r.y1),
273 AGG_INLINE
unsigned width()
const {
return m_rbuf->width(); }
274 AGG_INLINE
unsigned height()
const {
return m_rbuf->height(); }
275 AGG_INLINE
int stride()
const {
return m_rbuf->stride(); }
278 int8u* row_ptr(
int y) {
return m_rbuf->row_ptr(y); }
279 const int8u* row_ptr(
int y)
const {
return m_rbuf->row_ptr(y); }
280 row_data row(
int y)
const {
return m_rbuf->row(y); }
283 AGG_INLINE int8u* pix_ptr(
int x,
int y)
285 return m_rbuf->row_ptr(y) +
sizeof(value_type) * (x * pix_step + pix_offset);
288 AGG_INLINE
const int8u* pix_ptr(
int x,
int y)
const 290 return m_rbuf->row_ptr(y) +
sizeof(value_type) * (x * pix_step + pix_offset);
294 AGG_INLINE
pixel_type* pix_value_ptr(
int x,
int y,
unsigned len)
296 return (
pixel_type*)(m_rbuf->row_ptr(x, y, len) +
sizeof(value_type) * (x * pix_step + pix_offset));
300 AGG_INLINE
const pixel_type* pix_value_ptr(
int x,
int y)
const 302 int8u* p = m_rbuf->row_ptr(y);
303 return p ? (
pixel_type*)(p +
sizeof(value_type) * (x * pix_step + pix_offset)) : 0;
307 AGG_INLINE
static pixel_type* pix_value_ptr(
void* p)
309 return (
pixel_type*)((value_type*)p + pix_offset);
313 AGG_INLINE
static const pixel_type* pix_value_ptr(
const void* p)
315 return (
const pixel_type*)((
const value_type*)p + pix_offset);
319 AGG_INLINE
static void write_plain_color(
void* p, color_type c)
323 pix_value_ptr(p)->set(c);
327 AGG_INLINE
static color_type read_plain_color(
const void* p)
329 return pix_value_ptr(p)->get();
333 AGG_INLINE
static void make_pix(int8u* p,
const color_type& c)
339 AGG_INLINE color_type pixel(
int x,
int y)
const 341 if (
const pixel_type* p = pix_value_ptr(x, y))
345 return color_type::no_color();
349 AGG_INLINE
void copy_pixel(
int x,
int y,
const color_type& c)
351 pix_value_ptr(x, y, 1)->set(c);
355 AGG_INLINE
void blend_pixel(
int x,
int y,
const color_type& c, int8u cover)
357 copy_or_blend_pix(pix_value_ptr(x, y, 1), c, cover);
361 AGG_INLINE
void copy_hline(
int x,
int y,
376 AGG_INLINE
void copy_vline(
int x,
int y,
382 pix_value_ptr(x, y++, 1)->set(c);
389 void blend_hline(
int x,
int y,
394 if (!c.is_transparent())
398 if (c.is_opaque() && cover == cover_mask)
411 blend_pix(p, c, cover);
421 void blend_vline(
int x,
int y,
426 if (!c.is_transparent())
428 if (c.is_opaque() && cover == cover_mask)
432 pix_value_ptr(x, y++, 1)->set(c);
440 blend_pix(pix_value_ptr(x, y++, 1), c, cover);
449 void blend_solid_hspan(
int x,
int y,
454 if (!c.is_transparent())
460 if (c.is_opaque() && *covers == cover_mask)
466 blend_pix(p, c, *covers);
477 void blend_solid_vspan(
int x,
int y,
482 if (!c.is_transparent())
488 if (c.is_opaque() && *covers == cover_mask)
494 blend_pix(p, c, *covers);
504 void copy_color_hspan(
int x,
int y,
506 const color_type* colors)
520 void copy_color_vspan(
int x,
int y,
522 const color_type* colors)
526 pix_value_ptr(x, y++, 1)->set(*colors++);
533 void blend_color_hspan(
int x,
int y,
535 const color_type* colors,
545 copy_or_blend_pix(p, *colors++, *covers++);
552 if (cover == cover_mask)
556 copy_or_blend_pix(p, *colors++);
565 copy_or_blend_pix(p, *colors++, cover);
575 void blend_color_vspan(
int x,
int y,
577 const color_type* colors,
585 copy_or_blend_pix(pix_value_ptr(x, y++, 1), *colors++, *covers++);
591 if (cover == cover_mask)
595 copy_or_blend_pix(pix_value_ptr(x, y++, 1), *colors++);
603 copy_or_blend_pix(pix_value_ptr(x, y++, 1), *colors++, cover);
611 template<
class Function>
void for_each_pixel(Function f)
614 for (y = 0; y < height(); ++y)
616 row_data r = m_rbuf->row(y);
619 unsigned len = r.x2 - r.x1 + 1;
632 template<
class GammaLut>
void apply_gamma_dir(
const GammaLut& g)
638 template<
class GammaLut>
void apply_gamma_inv(
const GammaLut& g)
644 template<
class RenBuf2>
645 void copy_from(
const RenBuf2& from,
650 if (
const int8u* p = from.row_ptr(ysrc))
652 std::memmove(m_rbuf->row_ptr(xdst, ydst, len) + xdst * pix_width,
653 p + xsrc * pix_width,
660 template<
class SrcPixelFormatRenderer>
661 void blend_from_color(
const SrcPixelFormatRenderer& from,
662 const color_type& color,
668 typedef typename SrcPixelFormatRenderer::pixel_type src_pixel_type;
669 typedef typename SrcPixelFormatRenderer::color_type src_color_type;
671 if (
const src_pixel_type* psrc = from.pix_value_ptr(xsrc, ysrc))
673 pixel_type* pdst = pix_value_ptr(xdst, ydst, len);
677 copy_or_blend_pix(pdst, color, src_color_type::scale_cover(cover, psrc->c[0]));
688 template<
class SrcPixelFormatRenderer>
689 void blend_from_lut(
const SrcPixelFormatRenderer& from,
690 const color_type* color_lut,
696 typedef typename SrcPixelFormatRenderer::pixel_type src_pixel_type;
698 if (
const src_pixel_type* psrc = from.pix_value_ptr(xsrc, ysrc))
700 pixel_type* pdst = pix_value_ptr(xdst, ydst, len);
704 copy_or_blend_pix(pdst, color_lut[psrc->c[0]], cover);