code cleanup: spelling
[blender.git] / source / blender / freestyle / intern / stroke / Curve.h
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * ***** END GPL LICENSE BLOCK *****
19  */
20
21 #ifndef __FREESTYLE_CURVE_H__
22 #define __FREESTYLE_CURVE_H__
23
24 /** \file blender/freestyle/intern/stroke/Curve.h
25  *  \ingroup freestyle
26  *  \brief Class to define a container for curves
27  *  \author Stephane Grabli
28  *  \date 11/01/2003
29  */
30
31 #include <deque>
32
33 #include "../geometry/Geom.h"
34
35 //#include "../scene_graph/FrsMaterial.h"
36
37 #include "../view_map/Interface0D.h"
38 #include "../view_map/Interface1D.h"
39 #include "../view_map/Silhouette.h"
40 #include "../view_map/SilhouetteGeomEngine.h"
41
42 #include "../system/BaseIterator.h"
43
44 #ifdef WITH_CXX_GUARDEDALLOC
45 #include "MEM_guardedalloc.h"
46 #endif
47
48 using namespace std;
49
50 namespace Freestyle {
51
52 using namespace Geometry;
53
54 /**********************************/
55 /*                                */
56 /*                                */
57 /*             CurvePoint         */
58 /*                                */
59 /*                                */
60 /**********************************/
61
62 /*! Class to represent a point of a curve.
63  *  A CurvePoint can be any point of a 1D curve (it doesn't have to be a vertex of the curve).
64  *  Any Interface1D is built upon ViewEdges, themselves built upon FEdges. Therefore, a curve is basically
65  *  a polyline made of a list SVertex.
66  *  Thus, a CurvePoint is built by lineraly interpolating two SVertex.
67  *  CurvePoint can be used as virtual points while querying 0D information along a curve at a given resolution.
68  */
69 class LIB_STROKE_EXPORT CurvePoint : public Interface0D
70 {
71 public: // Implementation of Interface0D
72         /*! Returns the string "CurvePoint"*/
73         virtual string getExactTypeName() const
74         {
75                 return "CurvePoint";
76         }
77
78         // Data access methods
79         /*! Returns the 3D X coordinate of the point */
80         virtual real getX() const
81         {
82                 return _Point3d.x();
83         }
84
85         /*! Returns the 3D Y coordinate of the point */
86         virtual real getY() const
87         {
88                 return _Point3d.y();
89         }
90
91         /*! Returns the 3D Z coordinate of the point */
92         virtual real getZ() const
93         {
94                 return _Point3d.z();
95         }
96
97         /*!  Returns the 3D point. */ 
98         virtual Vec3f getPoint3D() const
99         {
100                 return _Point3d;
101         }
102
103         /*! Returns the projected 3D X coordinate of the point */
104         virtual real getProjectedX() const
105         {
106                 return _Point2d.x();
107         }
108
109         /*! Returns the projected 3D Y coordinate of the point */
110         virtual real getProjectedY() const
111         {
112                 return _Point2d.y();
113         }
114
115         /*! Returns the projected 3D Z coordinate of the point */
116         virtual real getProjectedZ() const
117         {
118                 return _Point2d.z();
119         }
120
121         /*!  Returns the 2D point. */ 
122         virtual Vec2f getPoint2D() const
123         {
124                 return Vec2f((float)_Point2d.x(), (float)_Point2d.y());
125         }
126
127         virtual FEdge *getFEdge(Interface0D& inter);
128
129         /*! Returns the CurvePoint's Id */
130         virtual Id getId() const
131         {
132                 Id id;
133                 if (_t2d == 0)
134                         return __A->getId();
135                 else if (_t2d == 1)
136                         return __B->getId();
137                 return id;
138         }
139
140         /*! Returns the CurvePoint's Nature */
141         virtual Nature::VertexNature getNature() const
142         {
143                 Nature::VertexNature nature = Nature::POINT;
144                 if (_t2d == 0)
145                         nature |= __A->getNature();
146                 else if (_t2d == 1)
147                         nature |= __B->getNature();
148                 return nature;
149         }
150
151         /*! Cast the Interface0D in SVertex if it can be. */
152         virtual SVertex *castToSVertex()
153         {
154                 if (_t2d == 0)
155                         return __A;
156                 else if (_t2d == 1)
157                         return __B;
158                 return Interface0D::castToSVertex();
159         }
160
161         /*! Cast the Interface0D in ViewVertex if it can be. */
162         virtual ViewVertex *castToViewVertex()
163         {
164                 if (_t2d == 0)
165                         return __A->castToViewVertex();
166                 else if (_t2d == 1)
167                         return __B->castToViewVertex();
168                 return Interface0D::castToViewVertex();
169         }
170
171         /*! Cast the Interface0D in NonTVertex if it can be. */
172         virtual NonTVertex *castToNonTVertex()
173         {
174                 if (_t2d == 0)
175                         return __A->castToNonTVertex();
176                 else if (_t2d == 1)
177                         return __B->castToNonTVertex();
178                 return Interface0D::castToNonTVertex();
179         }
180
181         /*! Cast the Interface0D in TVertex if it can be. */
182         virtual TVertex *castToTVertex()
183         {
184                 if (_t2d == 0)
185                         return __A->castToTVertex();
186                 else if (_t2d == 1)
187                         return __B->castToTVertex();
188                 return Interface0D::castToTVertex();
189         }
190
191 public:
192         typedef SVertex vertex_type;
193
194 protected:
195         SVertex *__A;
196         SVertex *__B;
197         float _t2d;
198         //float _t3d;
199         Vec3r _Point2d;
200         Vec3r _Point3d;
201
202 public:
203         /*! Defult Constructor. */
204         CurvePoint();
205
206         /*! Builds a CurvePoint from two SVertex and an interpolation parameter.
207          *  \param iA
208          *    The first SVertex
209          *  \param iB
210          *    The second SVertex
211          *  \param t2d
212          *    A 2D interpolation parameter used to linearly interpolate \a iA and \a iB
213          */
214         CurvePoint(SVertex *iA, SVertex *iB, float t2d);
215
216         /*! Builds a CurvePoint from two CurvePoint and an interpolation parameter.
217          *  \param iA
218          *    The first CurvePoint
219          *  \param iB
220          *    The second CurvePoint
221          *  \param t2d
222          *    The 2D interpolation parameter used to linearly interpolate \a iA and \a iB.
223          */
224         CurvePoint(CurvePoint *iA, CurvePoint *iB, float t2d);
225
226         //CurvePoint(SVertex *iA, SVertex *iB, float t2d, float t3d);
227
228         /*! Copy Constructor. */
229         CurvePoint(const CurvePoint& iBrother);
230
231         /*! Operator = */
232         CurvePoint& operator=(const CurvePoint& iBrother);
233
234         /*! Destructor */
235         virtual ~CurvePoint() {}
236
237         /*! Operator == */
238         bool operator==(const CurvePoint& b)
239         {
240                 return ((__A == b.__A) && (__B == b.__B) && (_t2d == b._t2d));
241         }
242
243         /* accessors */
244         /*! Returns the first SVertex upon which the CurvePoint is built. */
245         inline SVertex *A()
246         {
247                 return __A;
248         }
249
250         /*! Returns the second SVertex upon which the CurvePoint is built. */
251         inline SVertex *B()
252         {
253                 return __B;
254         }
255
256         /*! Returns the interpolation parameter. */
257         inline float t2d() const
258         {
259                 return _t2d;
260         }
261
262 #if 0
263         inline const float t3d() const
264         {
265                 return _t3d;
266         }
267 #endif
268
269         /* modifiers */
270         /*! Sets the first SVertex upon which to build the CurvePoint. */
271         inline void setA(SVertex *iA)
272         {
273                 __A = iA;
274         }
275
276         /*! Sets the second SVertex upon which to build the CurvePoint. */
277         inline void setB(SVertex *iB)
278         {
279                 __B = iB;
280         }
281
282         /*! Sets the 2D interpolation parameter to use. */
283         inline void setT2d(float t)
284         {
285                 _t2d = t;
286         }
287
288 #if 0
289         inline void SetT3d(float t)
290         {
291                 _t3d = t;
292         }
293 #endif
294
295         /* Information access interface */
296
297         FEdge *fedge();
298
299         inline const Vec3r& point2d() const
300         {
301                 return _Point2d;
302         }
303
304         inline const Vec3r& point3d() const
305         {
306                 return _Point3d;
307         }
308
309         Vec3r normal() const;
310         //FrsMaterial material() const;
311         //Id shape_id() const;
312         const SShape *shape() const;
313         //float shape_importance() const;
314
315         //const unsigned qi() const;
316         occluder_container::const_iterator occluders_begin() const;
317         occluder_container::const_iterator occluders_end() const;
318         bool occluders_empty() const;
319         int occluders_size() const;
320         const Polygon3r& occludee() const;
321         const SShape *occluded_shape() const;
322         const bool occludee_empty() const;
323         real z_discontinuity() const;
324 #if 0
325         float local_average_depth() const;
326         float local_depth_variance() const;
327         real local_average_density(float sigma = 2.3f) const;
328         Vec3r shaded_color() const;
329         Vec3r orientation2d() const;
330         Vec3r orientation3d() const;
331
332         real curvature2d() const
333         {
334                 return viewedge()->curvature2d((_VertexA->point2d() + _VertexB->point2d()) / 2.0);
335         }
336
337         Vec3r curvature2d_as_vector() const;
338         /*! angle in radians */
339         real curvature2d_as_angle() const;
340 #endif
341
342         real curvatureFredo() const;
343         Vec2d directionFredo() const;
344 };
345
346
347 /**********************************/
348 /*                                */
349 /*                                */
350 /*             Curve              */
351 /*                                */
352 /*                                */
353 /**********************************/
354
355 namespace CurveInternal {
356
357 class CurvePoint_const_traits;
358 class CurvePoint_nonconst_traits;
359 template<class Traits> class __point_iterator;
360 class CurvePointIterator;
361
362 } // end of namespace CurveInternal
363
364 /*! Base class for curves made of CurvePoints.
365  *  SVertex is the type of the initial curve vertices.
366  *  A Chain is a specialization of a Curve.
367  */
368 class LIB_STROKE_EXPORT Curve : public Interface1D
369 {
370 public:
371         typedef CurvePoint Vertex;
372         typedef CurvePoint Point;
373         typedef Point point_type;
374         typedef Vertex vertex_type;
375         typedef deque<Vertex*> vertex_container;
376
377         /* Iterator to iterate over a vertex edges */
378
379         typedef CurveInternal::__point_iterator<CurveInternal::CurvePoint_nonconst_traits > point_iterator;
380         typedef CurveInternal::__point_iterator<CurveInternal::CurvePoint_const_traits > const_point_iterator;
381         typedef point_iterator vertex_iterator ;
382         typedef const_point_iterator const_vertex_iterator ;
383
384 protected:
385         vertex_container _Vertices;
386         double _Length;
387         Id _Id;
388         unsigned _nSegments; // number of segments
389
390 public:
391         /*! Default Constructor. */
392         Curve()
393         {
394                 _Length = 0;
395                 _Id = 0;
396                 _nSegments = 0;
397         }
398
399         /*! Builds a Curve from its id */
400         Curve(const Id& id)
401         {
402                 _Length = 0;
403                 _Id = id;
404                 _nSegments = 0;
405         }
406
407         /*! Copy Constructor. */
408         Curve(const Curve& iBrother)
409         {
410                 _Length = iBrother._Length;
411                 _Vertices = iBrother._Vertices;
412                 _Id = iBrother._Id;
413                 _nSegments = 0;
414         }
415
416         /*! Destructor. */
417         virtual ~Curve();
418
419         /*! Returns the string "Curve" */
420         virtual string getExactTypeName() const
421         {
422                 return "Curve";
423         }
424
425         /* fredo's curvature storage */
426         void computeCurvatureAndOrientation();
427
428         /*! Adds a single vertex (CurvePoint) at the end of the Curve */
429         inline void push_vertex_back(Vertex *iVertex)
430         {
431                 if (!_Vertices.empty()) {
432                         Vec3r vec_tmp(iVertex->point2d() - _Vertices.back()->point2d());
433                         _Length += vec_tmp.norm();
434                         ++_nSegments;
435                 }
436                 Vertex *new_vertex = new Vertex(*iVertex);
437                 _Vertices.push_back(new_vertex);
438         }
439
440         /*! Adds a single vertex (SVertex) at the end of the Curve */
441         inline void push_vertex_back(SVertex *iVertex) 
442         {
443                 if (!_Vertices.empty()) {
444                         Vec3r vec_tmp(iVertex->point2d() - _Vertices.back()->point2d());
445                         _Length += vec_tmp.norm();
446                         ++_nSegments;
447                 }
448                 Vertex *new_vertex = new Vertex(iVertex, 0, 0);
449                 _Vertices.push_back(new_vertex);
450         }
451
452         /*! Adds a single vertex (CurvePoint) at the front of the Curve */
453         inline void push_vertex_front(Vertex *iVertex) 
454         {
455                 if (!_Vertices.empty()) {
456                         Vec3r vec_tmp(iVertex->point2d() - _Vertices.front()->point2d());
457                         _Length += vec_tmp.norm();
458                         ++_nSegments;
459                 }
460                 Vertex *new_vertex = new Vertex(*iVertex);
461                 _Vertices.push_front(new_vertex);
462         }
463
464         /*! Adds a single vertex (SVertex) at the front of the Curve */
465         inline void push_vertex_front(SVertex *iVertex) 
466         {
467                 if (!_Vertices.empty()) {
468                         Vec3r vec_tmp(iVertex->point2d() - _Vertices.front()->point2d());
469                         _Length += vec_tmp.norm();
470                         ++_nSegments;
471                 }
472                 Vertex *new_vertex = new Vertex(iVertex, 0, 0);
473                 _Vertices.push_front(new_vertex);
474         }
475
476         /*! Returns true is the Curve doesn't have any Vertex yet. */
477         inline bool empty() const
478         {
479                 return _Vertices.empty();
480         }
481
482         /*! Returns the 2D length of the Curve. */
483         inline real getLength2D() const
484         {
485                 return _Length;
486         }
487
488         /*! Returns the Id of the 1D element. */
489         virtual Id getId() const
490         {
491                 return _Id;
492         }
493
494         /*! Returns the number of segments in the polyline constituting the Curve. */
495         inline unsigned int nSegments() const
496         {
497                 return _nSegments;
498         }
499
500         inline void setId(const Id& id)
501         {
502                 _Id = id;
503         }
504
505         /* Information access interface */
506
507 #if 0
508         inline Vec3r shaded_color(int iCombination = 0) const;
509         inline Vec3r orientation2d(point_iterator it) const;
510         Vec3r orientation2d(int iCombination = 0) const;
511         Vec3r orientation3d(point_iterator it) const;
512         Vec3r orientation3d(int iCombination = 0) const;
513
514         real curvature2d(point_iterator it) const
515         {
516                 return (*it)->curvature2d();
517         }
518
519         real curvature2d(int iCombination = 0) const;
520         FrsMaterial material() const;
521         int qi() const;
522         occluder_container::const_iterator occluders_begin() const;
523         occluder_container::const_iterator occluders_end() const;
524         int occluders_size() const;
525         bool occluders_empty() const;
526
527         const Polygon3r& occludee() const
528         {
529                 return *(_FEdgeA->aFace());
530         }
531
532         const SShape *occluded_shape() const;
533         const bool occludee_empty() const;
534         real z_discontinuity(int iCombination = 0) const;
535         int shape_id() const;
536         const SShape *shape() const;
537         float shape_importance(int iCombination = 0) const;
538         float local_average_depth(int iCombination = 0) const;
539         float local_depth_variance(int iCombination = 0) const;
540         real local_average_density(float sigma = 2.3f, int iCombination = 0) const;
541         Vec3r curvature2d_as_vector(int iCombination = 0) const;
542         /*! angle in radians */
543         real curvature2d_as_angle(int iCombination = 0) const;
544 #endif
545
546         /* advanced iterators access */
547         point_iterator points_begin(float step = 0);
548         const_point_iterator points_begin(float step = 0) const;
549         point_iterator points_end(float step = 0);
550         const_point_iterator points_end(float step = 0) const;
551
552         /* methods given for convenience */
553         point_iterator vertices_begin();
554         const_point_iterator vertices_begin() const;
555         point_iterator vertices_end();
556         const_point_iterator vertices_end() const;
557
558         // specialized iterators access
559         CurveInternal::CurvePointIterator curvePointsBegin(float t = 0.0f);
560         CurveInternal::CurvePointIterator curvePointsEnd(float t = 0.0f);
561
562         CurveInternal::CurvePointIterator curveVerticesBegin();
563         CurveInternal::CurvePointIterator curveVerticesEnd();
564
565         // Iterators access
566         /*! Returns an Interface0DIterator pointing onto the first vertex of the Curve and that can iterate
567          *  over the \a vertices of the Curve.
568          */
569         virtual Interface0DIterator verticesBegin();
570
571         /*! Returns an Interface0DIterator pointing after the last vertex of the Curve and that can iterate
572          *  over the \a vertices of the Curve.
573          */
574         virtual Interface0DIterator verticesEnd();
575
576         /*! Returns an Interface0DIterator pointing onto the first point of the Curve and that can iterate
577          *  over the \a points of the Curve at any resolution.
578          *  At each iteration a virtual temporary CurvePoint is created.
579          */
580         virtual Interface0DIterator pointsBegin(float t = 0.0f);
581
582         /*! Returns an Interface0DIterator pointing after the last point of the Curve and that can iterate
583          *  over the \a points of the Curve at any resolution.
584          *  At each iteration a virtual temporary CurvePoint is created.
585          */
586         virtual Interface0DIterator pointsEnd(float t = 0.0f);
587 };
588
589 } /* namespace Freestyle */
590
591 #endif  // __FREESTYLE_CURVE_H__