1226584Sdim//---------------------------------------------------------------------------- 2226584Sdim// Anti-Grain Geometry - Version 2.4 3226584Sdim// Copyright (C) 2002-2005 Maxim Shemanarev (http://www.antigrain.com) 4226584Sdim// 5226584Sdim// Permission to copy, use, modify, sell and distribute this software 6226584Sdim// is granted provided this copyright notice appears in all copies. 7226584Sdim// This software is provided "as is" without express or implied 8226584Sdim// warranty, and with no claim as to its suitability for any purpose. 9226584Sdim// 10226584Sdim//---------------------------------------------------------------------------- 11226584Sdim// Contact: mcseem@antigrain.com 12226584Sdim// mcseemagg@yahoo.com 13226584Sdim// http://www.antigrain.com 14226584Sdim//---------------------------------------------------------------------------- 15226584Sdim 16226584Sdim#ifndef AGG_SPAN_INTERPOLATOR_LINEAR_INCLUDED 17226584Sdim#define AGG_SPAN_INTERPOLATOR_LINEAR_INCLUDED 18226584Sdim 19226584Sdim#include "agg_basics.h" 20226584Sdim#include "agg_dda_line.h" 21226584Sdim#include "agg_trans_affine.h" 22226584Sdim 23226584Sdimnamespace agg 24249423Sdim{ 25226584Sdim 26226584Sdim //================================================span_interpolator_linear 27226584Sdim template<class Transformer = trans_affine, unsigned SubpixelShift = 8> 28226584Sdim class span_interpolator_linear 29226584Sdim { 30226584Sdim public: 31226584Sdim typedef Transformer trans_type; 32226584Sdim 33226584Sdim enum subpixel_scale_e 34226584Sdim { 35226584Sdim subpixel_shift = SubpixelShift, 36226584Sdim subpixel_scale = 1 << subpixel_shift 37226584Sdim }; 38226584Sdim 39226584Sdim //-------------------------------------------------------------------- 40226584Sdim span_interpolator_linear() {} 41226584Sdim span_interpolator_linear(const trans_type& trans) : m_trans(&trans) {} 42226584Sdim span_interpolator_linear(const trans_type& trans, 43226584Sdim double x, double y, unsigned len) : 44226584Sdim m_trans(&trans) 45226584Sdim { 46226584Sdim begin(x, y, len); 47226584Sdim } 48226584Sdim 49226584Sdim //---------------------------------------------------------------- 50226584Sdim const trans_type& transformer() const { return *m_trans; } 51226584Sdim void transformer(const trans_type& trans) { m_trans = &trans; } 52226584Sdim 53226584Sdim //---------------------------------------------------------------- 54226584Sdim void begin(double x, double y, unsigned len) 55226584Sdim { 56226584Sdim double tx; 57226584Sdim double ty; 58226584Sdim 59226584Sdim tx = x; 60226584Sdim ty = y; 61226584Sdim m_trans->transform(&tx, &ty); 62226584Sdim int x1 = iround(tx * subpixel_scale); 63226584Sdim int y1 = iround(ty * subpixel_scale); 64226584Sdim 65226584Sdim tx = x + len; 66226584Sdim ty = y; 67226584Sdim m_trans->transform(&tx, &ty); 68226584Sdim int x2 = iround(tx * subpixel_scale); 69226584Sdim int y2 = iround(ty * subpixel_scale); 70226584Sdim 71226584Sdim m_li_x = dda2_line_interpolator(x1, x2, len); 72226584Sdim m_li_y = dda2_line_interpolator(y1, y2, len); 73226584Sdim } 74226584Sdim 75226584Sdim //---------------------------------------------------------------- 76226584Sdim void resynchronize(double xe, double ye, unsigned len) 77226584Sdim { 78226584Sdim m_trans->transform(&xe, &ye); 79226584Sdim m_li_x = dda2_line_interpolator(m_li_x.y(), iround(xe * subpixel_scale), len); 80226584Sdim m_li_y = dda2_line_interpolator(m_li_y.y(), iround(ye * subpixel_scale), len); 81226584Sdim } 82226584Sdim 83226584Sdim //---------------------------------------------------------------- 84226584Sdim void operator++() 85226584Sdim { 86226584Sdim ++m_li_x; 87226584Sdim ++m_li_y; 88226584Sdim } 89226584Sdim 90226584Sdim //---------------------------------------------------------------- 91226584Sdim void coordinates(int* x, int* y) const 92226584Sdim { 93226584Sdim *x = m_li_x.y(); 94226584Sdim *y = m_li_y.y(); 95226584Sdim } 96226584Sdim 97226584Sdim private: 98226584Sdim const trans_type* m_trans; 99226584Sdim dda2_line_interpolator m_li_x; 100226584Sdim dda2_line_interpolator m_li_y; 101226584Sdim }; 102226584Sdim 103226584Sdim 104226584Sdim 105226584Sdim 106226584Sdim 107226584Sdim 108226584Sdim //=====================================span_interpolator_linear_subdiv 109226584Sdim template<class Transformer = trans_affine, unsigned SubpixelShift = 8> 110226584Sdim class span_interpolator_linear_subdiv 111226584Sdim { 112226584Sdim public: 113226584Sdim typedef Transformer trans_type; 114226584Sdim 115226584Sdim enum subpixel_scale_e 116226584Sdim { 117226584Sdim subpixel_shift = SubpixelShift, 118226584Sdim subpixel_scale = 1 << subpixel_shift 119226584Sdim }; 120226584Sdim 121226584Sdim 122226584Sdim //---------------------------------------------------------------- 123226584Sdim span_interpolator_linear_subdiv() : 124226584Sdim m_subdiv_shift(4), 125226584Sdim m_subdiv_size(1 << m_subdiv_shift), 126226584Sdim m_subdiv_mask(m_subdiv_size - 1) {} 127226584Sdim 128226584Sdim span_interpolator_linear_subdiv(const trans_type& trans, 129226584Sdim unsigned subdiv_shift = 4) : 130226584Sdim m_subdiv_shift(subdiv_shift), 131226584Sdim m_subdiv_size(1 << m_subdiv_shift), 132226584Sdim m_subdiv_mask(m_subdiv_size - 1), 133226584Sdim m_trans(&trans) {} 134226584Sdim 135226584Sdim span_interpolator_linear_subdiv(const trans_type& trans, 136226584Sdim double x, double y, unsigned len, 137226584Sdim unsigned subdiv_shift = 4) : 138226584Sdim m_subdiv_shift(subdiv_shift), 139226584Sdim m_subdiv_size(1 << m_subdiv_shift), 140226584Sdim m_subdiv_mask(m_subdiv_size - 1), 141226584Sdim m_trans(&trans) 142226584Sdim { 143226584Sdim begin(x, y, len); 144226584Sdim } 145226584Sdim 146226584Sdim //---------------------------------------------------------------- 147226584Sdim const trans_type& transformer() const { return *m_trans; } 148226584Sdim void transformer(const trans_type& trans) { m_trans = &trans; } 149226584Sdim 150226584Sdim //---------------------------------------------------------------- 151226584Sdim unsigned subdiv_shift() const { return m_subdiv_shift; } 152226584Sdim void subdiv_shift(unsigned shift) 153226584Sdim { 154226584Sdim m_subdiv_shift = shift; 155226584Sdim m_subdiv_size = 1 << m_subdiv_shift; 156234353Sdim m_subdiv_mask = m_subdiv_size - 1; 157226584Sdim } 158226584Sdim 159226584Sdim //---------------------------------------------------------------- 160226584Sdim void begin(double x, double y, unsigned len) 161239462Sdim { 162226584Sdim double tx; 163226584Sdim double ty; 164226584Sdim m_pos = 1; 165226584Sdim m_src_x = iround(x * subpixel_scale) + subpixel_scale; 166226584Sdim m_src_y = y; 167226584Sdim m_len = len; 168226584Sdim 169226584Sdim if(len > m_subdiv_size) len = m_subdiv_size; 170226584Sdim tx = x; 171226584Sdim ty = y; 172226584Sdim m_trans->transform(&tx, &ty); 173226584Sdim int x1 = iround(tx * subpixel_scale); 174226584Sdim int y1 = iround(ty * subpixel_scale); 175226584Sdim 176226584Sdim tx = x + len; 177226584Sdim ty = y; 178226584Sdim m_trans->transform(&tx, &ty); 179226584Sdim 180226584Sdim m_li_x = dda2_line_interpolator(x1, iround(tx * subpixel_scale), len); 181226584Sdim m_li_y = dda2_line_interpolator(y1, iround(ty * subpixel_scale), len); 182226584Sdim } 183226584Sdim 184226584Sdim //---------------------------------------------------------------- 185226584Sdim void operator++() 186226584Sdim { 187226584Sdim ++m_li_x; 188226584Sdim ++m_li_y; 189226584Sdim if(m_pos >= m_subdiv_size) 190226584Sdim { 191226584Sdim unsigned len = m_len; 192226584Sdim if(len > m_subdiv_size) len = m_subdiv_size; 193226584Sdim double tx = double(m_src_x) / double(subpixel_scale) + len; 194226584Sdim double ty = m_src_y; 195226584Sdim m_trans->transform(&tx, &ty); 196226584Sdim m_li_x = dda2_line_interpolator(m_li_x.y(), iround(tx * subpixel_scale), len); 197226584Sdim m_li_y = dda2_line_interpolator(m_li_y.y(), iround(ty * subpixel_scale), len); 198226584Sdim m_pos = 0; 199226584Sdim } 200226584Sdim m_src_x += subpixel_scale; 201226584Sdim ++m_pos; 202226584Sdim --m_len; 203226584Sdim } 204226584Sdim 205226584Sdim //---------------------------------------------------------------- 206226584Sdim void coordinates(int* x, int* y) const 207226584Sdim { 208226584Sdim *x = m_li_x.y(); 209226584Sdim *y = m_li_y.y(); 210226584Sdim } 211226584Sdim 212234353Sdim private: 213226584Sdim unsigned m_subdiv_shift; 214226584Sdim unsigned m_subdiv_size; 215226584Sdim unsigned m_subdiv_mask; 216226584Sdim const trans_type* m_trans; 217226584Sdim dda2_line_interpolator m_li_x; 218226584Sdim dda2_line_interpolator m_li_y; 219226584Sdim int m_src_x; 220226584Sdim double m_src_y; 221226584Sdim unsigned m_pos; 222226584Sdim unsigned m_len; 223226584Sdim }; 224226584Sdim 225226584Sdim 226226584Sdim} 227226584Sdim 228249423Sdim 229226584Sdim 230226584Sdim#endif 231226584Sdim 232226584Sdim 233226584Sdim