Code

fixed another typo
[inkscape.git] / src / live_effects / lpe-lattice.cpp
1 #define INKSCAPE_LPE_LATTICE_CPP
2 /** \file
3  * LPE <lattice> implementation
4  
5  */
6 /*
7  * Authors:
8  *   Johan Engelen <j.b.c.engelen@utwente.nl>
9  *   Steren Giannini
10  *   NoĆ© Falzon
11  *   Victor Navez
12 *
13 * Copyright (C) 2007-2008 Authors 
14  *
15  * Released under GNU GPL, read the file 'COPYING' for more information
16  */
18 #include "live_effects/lpe-lattice.h"
20 #include "sp-shape.h"
21 #include "sp-item.h"
22 #include "sp-path.h"
23 #include "display/curve.h"
24 #include "libnr/n-art-bpath-2geom.h"
25 #include "svg/svg.h"
27 #include <2geom/sbasis.h>
28 #include <2geom/sbasis-2d.h>
29 #include <2geom/sbasis-geometric.h>
30 #include <2geom/bezier-to-sbasis.h>
31 #include <2geom/sbasis-to-bezier.h>
32 #include <2geom/d2.h>
33 #include <2geom/piecewise.h>
34 #include <2geom/transforms.h>
36 using namespace Geom;
38 namespace Inkscape {
39 namespace LivePathEffect {
41 LPELattice::LPELattice(LivePathEffectObject *lpeobject) :
42     Effect(lpeobject),
43     
44     // initialise your parameters here:
45     grid_point0(_("Control handle 0"), _("Tadah"), "gridpoint0", &wr, this),
46     grid_point1(_("Control handle 1"), _("Tadah"), "gridpoint1", &wr, this),
47     grid_point2(_("Control handle 2"), _("Tadah"), "gridpoint2", &wr, this),
48     grid_point3(_("Control handle 3"), _("Tadah"), "gridpoint3", &wr, this),
49     grid_point4(_("Control handle 4"), _("Tadah"), "gridpoint4", &wr, this),
50     grid_point5(_("Control handle 5"), _("Tadah"), "gridpoint5", &wr, this),
51     grid_point6(_("Control handle 6"), _("Tadah"), "gridpoint6", &wr, this),
52     grid_point7(_("Control handle 7"), _("Tadah"), "gridpoint7", &wr, this),
53     grid_point8(_("Control handle 8"), _("Tadah"), "gridpoint8", &wr, this),
54     grid_point9(_("Control handle 9"), _("Tadah"), "gridpoint9", &wr, this),
55     grid_point10(_("Control handle 10"), _("Tadah"), "gridpoint10", &wr, this),
56     grid_point11(_("Control handle 11"), _("Tadah"), "gridpoint11", &wr, this),
57     grid_point12(_("Control handle 12"), _("Tadah"), "gridpoint12", &wr, this),
58     grid_point13(_("Control handle 13"), _("Tadah"), "gridpoint13", &wr, this),
59     grid_point14(_("Control handle 14"), _("Tadah"), "gridpoint14", &wr, this),
60     grid_point15(_("Control handle 15"), _("Tadah"), "gridpoint15", &wr, this)
61     
62 {
63     // register all your parameters here, so Inkscape knows which parameters this effect has:
64     registerParameter( dynamic_cast<Parameter *>(&grid_point0) );
65     registerParameter( dynamic_cast<Parameter *>(&grid_point1) );
66     registerParameter( dynamic_cast<Parameter *>(&grid_point2) );
67     registerParameter( dynamic_cast<Parameter *>(&grid_point3) );
68     registerParameter( dynamic_cast<Parameter *>(&grid_point4) );
69     registerParameter( dynamic_cast<Parameter *>(&grid_point5) );
70     registerParameter( dynamic_cast<Parameter *>(&grid_point6) );
71     registerParameter( dynamic_cast<Parameter *>(&grid_point7) );
72     registerParameter( dynamic_cast<Parameter *>(&grid_point8) );
73     registerParameter( dynamic_cast<Parameter *>(&grid_point9) );
74     registerParameter( dynamic_cast<Parameter *>(&grid_point10) );
75     registerParameter( dynamic_cast<Parameter *>(&grid_point11) );
76     registerParameter( dynamic_cast<Parameter *>(&grid_point12) );
77     registerParameter( dynamic_cast<Parameter *>(&grid_point13) );
78     registerParameter( dynamic_cast<Parameter *>(&grid_point14) );
79     registerParameter( dynamic_cast<Parameter *>(&grid_point15) );
81     
82 }
84 LPELattice::~LPELattice()
85 {
87 }
90 Geom::Piecewise<Geom::D2<Geom::SBasis> >
91 LPELattice::doEffect_pwd2 (Geom::Piecewise<Geom::D2<Geom::SBasis> > const & pwd2_in)
92 {
93     D2<SBasis2d> sb2;
94     
95     //Initialisation of the sb2
96     for(unsigned dim = 0; dim < 2; dim++) {
97         sb2[dim].us = 2;
98         sb2[dim].vs = 2;
99         const int depth = sb2[dim].us*sb2[dim].vs;
100         sb2[dim].resize(depth, Linear2d(0));
101     }
103     //Grouping the point params in a convenient vector
104     std::vector<Geom::Point *> handles(16);
105     
106     handles[0] = &grid_point0;
107     handles[1] = &grid_point1;
108     handles[2] = &grid_point2;
109     handles[3] = &grid_point3;
110     handles[4] = &grid_point4;
111     handles[5] = &grid_point5;
112     handles[6] = &grid_point6;
113     handles[7] = &grid_point7;
114     handles[8] = &grid_point8;
115     handles[9] = &grid_point9;
116     handles[10] = &grid_point10;
117     handles[11] = &grid_point11;
118     handles[12] = &grid_point12;
119     handles[13] = &grid_point13;
120     handles[14] = &grid_point14;
121     handles[15] = &grid_point15;
123     Geom::Point origin = Geom::Point(boundingbox_X.min(),boundingbox_Y.min());
124       
125     double width = boundingbox_X.extent();
126     double height = boundingbox_Y.extent();
128     //numbering is based on 4 rectangles.
129     for(unsigned dim = 0; dim < 2; dim++) {
130         Geom::Point dir(0,0);
131         dir[dim] = 1;
132         for(unsigned vi = 0; vi < sb2[dim].vs; vi++) {
133             for(unsigned ui = 0; ui < sb2[dim].us; ui++) {
134                 for(unsigned iv = 0; iv < 2; iv++) {
135                     for(unsigned iu = 0; iu < 2; iu++) {
136                         unsigned corner = iu + 2*iv;
137                         unsigned i = ui + vi*sb2[dim].us;
138                         
139                         //This is the offset from the Upperleft point
140                         Geom::Point base(   (ui + iu*(3-2*ui))*width/3.,
141                                             (vi + iv*(3-2*vi))*height/3.);
142                        
143                         //Special action for corners
144                         if(vi == 0 && ui == 0) {
145                             base = Geom::Point(0,0);
146                         }
147                         
148                         // i = Upperleft corner of the considerated rectangle
149                         // corner = actual corner of the rectangle
150                         // origin = Upperleft point
151                         double dl = dot((*handles[corner+4*i] - (base + origin)), dir)/dot(dir,dir);
152                         sb2[dim][i][corner] = dl/( dim ? height : width )*pow(4.0,ui+vi);
153                     }
154                 }
155             }
156         }
157     }
158    
159     Piecewise<D2<SBasis> >  output;
160     output.push_cut(0.);
161     for(unsigned i = 0; i < pwd2_in.size(); i++) {
162         D2<SBasis> B = pwd2_in[i];
163         B -= origin;   
164         B*= 1/width;
165         //Here comes the magic
166         D2<SBasis> tB = compose_each(sb2,B);
167         tB = tB * width + origin;
169         output.push(tB,i+1);
170     }
172     return output;
175 void
176 LPELattice::doBeforeEffect (SPLPEItem *lpeitem)
178     original_bbox(lpeitem);
181 void
182 LPELattice::resetDefaults(SPItem * item)
184     original_bbox(SP_LPE_ITEM(item), false);
185     
186     // place the 16 control points
187     grid_point0[Geom::X] = boundingbox_X.min();
188     grid_point0[Geom::Y] = boundingbox_Y.min();
189     
190     grid_point1[Geom::X] = boundingbox_X.max();
191     grid_point1[Geom::Y] = boundingbox_Y.min();
192     
193     grid_point2[Geom::X] = boundingbox_X.min();
194     grid_point2[Geom::Y] = boundingbox_Y.max();
195     
196     grid_point3[Geom::X] = boundingbox_X.max();
197     grid_point3[Geom::Y] = boundingbox_Y.max();
198     
199     grid_point4[Geom::X] = 1.0/3*boundingbox_X.max()+2.0/3*boundingbox_X.min();
200     grid_point4[Geom::Y] = boundingbox_Y.min();
201     
202     grid_point5[Geom::X] = 2.0/3*boundingbox_X.max()+1.0/3*boundingbox_X.min();
203     grid_point5[Geom::Y] = boundingbox_Y.min();
204     
205     grid_point6[Geom::X] = 1.0/3*boundingbox_X.max()+2.0/3*boundingbox_X.min();
206     grid_point6[Geom::Y] = boundingbox_Y.max();
207     
208     grid_point7[Geom::X] = 2.0/3*boundingbox_X.max()+1.0/3*boundingbox_X.min();
209     grid_point7[Geom::Y] = boundingbox_Y.max();
210     
211     grid_point8[Geom::X] = boundingbox_X.min();
212     grid_point8[Geom::Y] = 1.0/3*boundingbox_Y.max()+2.0/3*boundingbox_Y.min();     
214     grid_point9[Geom::X] = boundingbox_X.max();
215     grid_point9[Geom::Y] = 1.0/3*boundingbox_Y.max()+2.0/3*boundingbox_Y.min();
216         
217     grid_point10[Geom::X] = boundingbox_X.min();
218     grid_point10[Geom::Y] = 2.0/3*boundingbox_Y.max()+1.0/3*boundingbox_Y.min();  
219     
220     grid_point11[Geom::X] = boundingbox_X.max();
221     grid_point11[Geom::Y] = 2.0/3*boundingbox_Y.max()+1.0/3*boundingbox_Y.min();  
222     
223     grid_point12[Geom::X] = 1.0/3*boundingbox_X.max()+2.0/3*boundingbox_X.min();
224     grid_point12[Geom::Y] = 1.0/3*boundingbox_Y.max()+2.0/3*boundingbox_Y.min();
225     
226     grid_point13[Geom::X] = 2.0/3*boundingbox_X.max()+1.0/3*boundingbox_X.min();
227     grid_point13[Geom::Y] = 1.0/3*boundingbox_Y.max()+2.0/3*boundingbox_Y.min();
228     
229     grid_point14[Geom::X] = 1.0/3*boundingbox_X.max()+2.0/3*boundingbox_X.min();
230     grid_point14[Geom::Y] = 2.0/3*boundingbox_Y.max()+1.0/3*boundingbox_Y.min();
231     
232     grid_point15[Geom::X] = 2.0/3*boundingbox_X.max()+1.0/3*boundingbox_X.min();
233     grid_point15[Geom::Y] = 2.0/3*boundingbox_Y.max()+1.0/3*boundingbox_Y.min();
236     
239 /* ######################## */
241 } //namespace LivePathEffect
242 } /* namespace Inkscape */
244 /*
245   Local Variables:
246   mode:c++
247   c-file-style:"stroustrup"
248   c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
249   indent-tabs-mode:nil
250   fill-column:99
251   End:
252 */
253 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4 :