agg_renderer_outline_image.h

来自「这是VCF框架的代码」· C头文件 代码 · 共 1,020 行 · 第 1/3 页

H
1,020
字号
//----------------------------------------------------------------------------// Anti-Grain Geometry - Version 2.4// Copyright (C) 2002-2005 Maxim Shemanarev (http://www.antigrain.com)//// Permission to copy, use, modify, sell and distribute this software // is granted provided this copyright notice appears in all copies. // This software is provided "as is" without express or implied// warranty, and with no claim as to its suitability for any purpose.////----------------------------------------------------------------------------// Contact: mcseem@antigrain.com//          mcseemagg@yahoo.com//          http://www.antigrain.com//----------------------------------------------------------------------------#ifndef AGG_RENDERER_OUTLINE_IMAGE_INCLUDED#define AGG_RENDERER_OUTLINE_IMAGE_INCLUDED#include "agg_math.h"#include "agg_line_aa_basics.h"#include "agg_dda_line.h"#include "agg_rendering_buffer.h"#include "agg_clip_liang_barsky.h"namespace agg{    //========================================================line_image_scale    template<class Source> class line_image_scale    {    public:        typedef typename Source::color_type color_type;        line_image_scale(const Source& src, double height) :            m_source(src),             m_height(height),            m_scale(src.height() / height)        {        }        double width()  const { return m_source.width(); }        double height() const { return m_height; }        color_type pixel(int x, int y) const         {             double src_y = (y + 0.5) * m_scale - 0.5;            int h  = m_source.height() - 1;            int y1 = ufloor(src_y);            int y2 = y1 + 1;            color_type pix1 = (y1 < 0) ? color_type::no_color() : m_source.pixel(x, y1);            color_type pix2 = (y2 > h) ? color_type::no_color() : m_source.pixel(x, y2);            return pix1.gradient(pix2, src_y - y1);        }    private:        line_image_scale(const line_image_scale<Source>&);        const line_image_scale<Source>& operator = (const line_image_scale<Source>&);        const Source& m_source;        double        m_height;        double        m_scale;    };    //======================================================line_image_pattern    template<class Filter> class line_image_pattern    {    public:        typedef Filter filter_type;        typedef typename filter_type::color_type color_type;        //--------------------------------------------------------------------        ~line_image_pattern()        {            delete [] m_data;        }        //--------------------------------------------------------------------        line_image_pattern(const Filter& filter) :            m_filter(&filter),            m_dilation(filter.dilation() + 1),            m_dilation_hr(m_dilation << line_subpixel_shift),            m_data(0),            m_width(0),            m_height(0),            m_width_hr(0),            m_half_height_hr(0),            m_offset_y_hr(0)        {        }        // Create        //--------------------------------------------------------------------        template<class Source>         line_image_pattern(const Filter& filter, const Source& src) :            m_filter(&filter),            m_dilation(filter.dilation() + 1),            m_dilation_hr(m_dilation << line_subpixel_shift),            m_data(0),            m_width(0),            m_height(0),            m_width_hr(0),            m_half_height_hr(0),            m_offset_y_hr(0)        {            create(src);        }        // Create        //--------------------------------------------------------------------        template<class Source> void create(const Source& src)        {            m_height = uceil(src.height());            m_width  = uceil(src.width());            m_width_hr = uround(src.width() * line_subpixel_scale);            m_half_height_hr = uround(src.height() * line_subpixel_scale/2);            m_offset_y_hr = m_dilation_hr + m_half_height_hr - line_subpixel_scale/2;            m_half_height_hr += line_subpixel_scale/2;            delete [] m_data;            m_data = new color_type [(m_width + m_dilation * 2) * (m_height + m_dilation * 2)];            m_buf.attach(m_data, m_width  + m_dilation * 2,                                  m_height + m_dilation * 2,                                  m_width  + m_dilation * 2);            unsigned x, y;            color_type* d1;            color_type* d2;            for(y = 0; y < m_height; y++)            {                d1 = m_buf.row_ptr(y + m_dilation) + m_dilation;                for(x = 0; x < m_width; x++)                {                    *d1++ = src.pixel(x, y);                }            }            const color_type* s1;            const color_type* s2;            for(y = 0; y < m_dilation; y++)            {                //s1 = m_buf.row_ptr(m_height + m_dilation - 1) + m_dilation;                //s2 = m_buf.row_ptr(m_dilation) + m_dilation;                d1 = m_buf.row_ptr(m_dilation + m_height + y) + m_dilation;                d2 = m_buf.row_ptr(m_dilation - y - 1) + m_dilation;                for(x = 0; x < m_width; x++)                {                    //*d1++ = color_type(*s1++, 0);                    //*d2++ = color_type(*s2++, 0);                    *d1++ = color_type::no_color();                    *d2++ = color_type::no_color();                }            }            unsigned h = m_height + m_dilation * 2;            for(y = 0; y < h; y++)            {                s1 = m_buf.row_ptr(y) + m_dilation;                s2 = m_buf.row_ptr(y) + m_dilation + m_width;                d1 = m_buf.row_ptr(y) + m_dilation + m_width;                d2 = m_buf.row_ptr(y) + m_dilation;                for(x = 0; x < m_dilation; x++)                {                    *d1++ = *s1++;                    *--d2 = *--s2;                }            }        }        //--------------------------------------------------------------------        int pattern_width() const { return m_width_hr; }        int line_width()    const { return m_half_height_hr; }        double width()      const { return m_height; }        //--------------------------------------------------------------------        void pixel(color_type* p, int x, int y) const        {            m_filter->pixel_high_res(m_buf.rows(),                                      p,                                      x % m_width_hr + m_dilation_hr,                                     y + m_offset_y_hr);        }        //--------------------------------------------------------------------        const filter_type& filter() const { return *m_filter; }    private:        line_image_pattern(const line_image_pattern<filter_type>&);        const line_image_pattern<filter_type>&             operator = (const line_image_pattern<filter_type>&);    protected:        row_ptr_cache<color_type> m_buf;        const filter_type*        m_filter;        unsigned                  m_dilation;        int                       m_dilation_hr;        color_type*               m_data;        unsigned                  m_width;        unsigned                  m_height;        int                       m_width_hr;        int                       m_half_height_hr;        int                       m_offset_y_hr;    };    //=================================================line_image_pattern_pow2    template<class Filter> class line_image_pattern_pow2 :     public line_image_pattern<Filter>    {    public:        typedef Filter filter_type;        typedef typename filter_type::color_type color_type;        typedef line_image_pattern<Filter> base_type;	        //--------------------------------------------------------------------        line_image_pattern_pow2(const Filter& filter) :            line_image_pattern<Filter>(filter), m_mask(line_subpixel_mask) {}        //--------------------------------------------------------------------        template<class Source>         line_image_pattern_pow2(const Filter& filter, const Source& src) :            line_image_pattern<Filter>(filter), m_mask(line_subpixel_mask)        {            create(src);        }                    //--------------------------------------------------------------------        template<class Source> void create(const Source& src)        {            line_image_pattern<Filter>::create(src);            m_mask = 1;            while(m_mask < base_type::m_width)             {                m_mask <<= 1;                m_mask |= 1;            }            m_mask <<= line_subpixel_shift - 1;            m_mask |=  line_subpixel_mask;            base_type::m_width_hr = m_mask + 1;        }        //--------------------------------------------------------------------        void pixel(color_type* p, int x, int y) const        {            base_type::m_filter->pixel_high_res(                    base_type::m_buf.rows(),                     p,                    (x & m_mask) + base_type::m_dilation_hr,                    y + base_type::m_offset_y_hr);        }    private:        unsigned m_mask;    };                                //===================================================distance_interpolator4    class distance_interpolator4    {    public:        //---------------------------------------------------------------------        distance_interpolator4() {}        distance_interpolator4(int x1,  int y1, int x2, int y2,                               int sx,  int sy, int ex, int ey,                                int len, double scale, int x, int y) :            m_dx(x2 - x1),            m_dy(y2 - y1),            m_dx_start(line_mr(sx) - line_mr(x1)),            m_dy_start(line_mr(sy) - line_mr(y1)),            m_dx_end(line_mr(ex) - line_mr(x2)),            m_dy_end(line_mr(ey) - line_mr(y2)),            m_dist(iround(double(x + line_subpixel_scale/2 - x2) * double(m_dy) -                           double(y + line_subpixel_scale/2 - y2) * double(m_dx))),            m_dist_start((line_mr(x + line_subpixel_scale/2) - line_mr(sx)) * m_dy_start -                          (line_mr(y + line_subpixel_scale/2) - line_mr(sy)) * m_dx_start),            m_dist_end((line_mr(x + line_subpixel_scale/2) - line_mr(ex)) * m_dy_end -                        (line_mr(y + line_subpixel_scale/2) - line_mr(ey)) * m_dx_end),            m_len(uround(len / scale))        {            double d = len * scale;            int dx = iround(((x2 - x1) << line_subpixel_shift) / d);            int dy = iround(((y2 - y1) << line_subpixel_shift) / d);            m_dx_pict   = -dy;            m_dy_pict   =  dx;            m_dist_pict =  ((x + line_subpixel_scale/2 - (x1 - dy)) * m_dy_pict -                             (y + line_subpixel_scale/2 - (y1 + dx)) * m_dx_pict) >>                            line_subpixel_shift;            m_dx       <<= line_subpixel_shift;            m_dy       <<= line_subpixel_shift;            m_dx_start <<= line_mr_subpixel_shift;            m_dy_start <<= line_mr_subpixel_shift;            m_dx_end   <<= line_mr_subpixel_shift;            m_dy_end   <<= line_mr_subpixel_shift;        }        //---------------------------------------------------------------------        void inc_x()         {             m_dist += m_dy;             m_dist_start += m_dy_start;             m_dist_pict += m_dy_pict;             m_dist_end += m_dy_end;         }        //---------------------------------------------------------------------        void dec_x()         {             m_dist -= m_dy;             m_dist_start -= m_dy_start;             m_dist_pict -= m_dy_pict;             m_dist_end -= m_dy_end;         }        //---------------------------------------------------------------------        void inc_y()         {             m_dist -= m_dx;             m_dist_start -= m_dx_start;             m_dist_pict -= m_dx_pict;             m_dist_end -= m_dx_end;         }        //---------------------------------------------------------------------        void dec_y()         {             m_dist += m_dx;             m_dist_start += m_dx_start; 

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?