Merged changes in the trunk up to revision 28600.
[blender.git] / source / blender / freestyle / intern / stroke / ChainingIterators.h
1 //
2 //  Filename         : ChainingIterators
3 //  Author           : Stephane Grabli
4 //  Purpose          : Chaining iterators
5 //  Date of creation : 01/07/2003
6 //
7 ///////////////////////////////////////////////////////////////////////////////
8
9 //
10 //  Copyright (C) : Please refer to the COPYRIGHT file distributed 
11 //   with this source distribution. 
12 //
13 //  This program is free software; you can redistribute it and/or
14 //  modify it under the terms of the GNU General Public License
15 //  as published by the Free Software Foundation; either version 2
16 //  of the License, or (at your option) any later version.
17 //
18 //  This program is distributed in the hope that it will be useful,
19 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
20 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21 //  GNU General Public License for more details.
22 //
23 //  You should have received a copy of the GNU General Public License
24 //  along with this program; if not, write to the Free Software
25 //  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
26 //
27 ///////////////////////////////////////////////////////////////////////////////
28 #ifndef  CHAININGITERATORS_H
29 # define CHAININGITERATORS_H
30
31 # include "../view_map/ViewMap.h"
32 # include "../view_map/ViewMapIterators.h"
33 # include "../view_map/ViewMapAdvancedIterators.h"
34 # include <iostream>
35 # include "Predicates1D.h"
36
37 #include "../system/Iterator.h" //soc 
38
39 # include  "../python/Director.h"
40
41 //using namespace ViewEdgeInternal;
42
43 //
44 // Adjacency iterator used in the chaining process
45 //
46 ///////////////////////////////////////////////////////////
47 class LIB_STROKE_EXPORT AdjacencyIterator : public Iterator {
48 protected:
49   ViewVertexInternal::orientedViewEdgeIterator _internalIterator;
50   bool _restrictToSelection;
51   bool _restrictToUnvisited;
52 public:
53   AdjacencyIterator(){
54     _restrictToSelection = true;
55     _restrictToUnvisited = true;
56   }
57   AdjacencyIterator(ViewVertex *iVertex, bool iRestrictToSelection = true, bool iRestrictToUnvisited = true){
58     _restrictToSelection = iRestrictToSelection;
59     _restrictToUnvisited = iRestrictToUnvisited;
60     _internalIterator = iVertex->edgesBegin();
61     while((!_internalIterator.isEnd()) && (!isValid((*_internalIterator).first)))
62       ++_internalIterator;
63   }
64   AdjacencyIterator(const AdjacencyIterator& iBrother){
65     _internalIterator = iBrother._internalIterator;
66     _restrictToSelection = iBrother._restrictToSelection;
67     _restrictToUnvisited = iBrother._restrictToUnvisited;
68   }
69   AdjacencyIterator& operator=(const AdjacencyIterator& iBrother) {  
70     _internalIterator = iBrother._internalIterator;
71     _restrictToSelection = iBrother._restrictToSelection;
72     _restrictToUnvisited = iBrother._restrictToUnvisited;  
73     return *this;
74   } 
75   virtual ~AdjacencyIterator(){
76   }
77   
78   virtual string getExactTypeName() const {
79     return "AdjacencyIterator";
80   }
81
82   virtual inline bool isEnd() const {
83     return _internalIterator.isEnd();
84   }
85   virtual inline bool isBegin() const {
86     return _internalIterator.isBegin();
87   }
88   /*! Returns true if the current ViewEdge is is coming
89    *  towards the iteration vertex. False otherwise.
90    */
91   bool isIncoming() const ;
92
93   /*! Returns a *pointer* to the pointed ViewEdge. */
94   virtual ViewEdge* operator*() ;
95   virtual ViewEdge* operator->() {return operator*();}
96   virtual AdjacencyIterator& operator++() {
97     increment();
98     return *this;
99   }
100   virtual AdjacencyIterator operator++(int) {
101     AdjacencyIterator tmp(*this);
102     increment();
103     return tmp;
104   }
105   virtual int increment();
106
107   virtual int decrement(){
108     cerr << "Warning: method decrement() not implemented" << endl;
109         return 0;
110   }
111
112 protected:
113   bool isValid(ViewEdge* edge);
114 };
115
116 //
117 // Base class for Chaining Iterators
118 //
119 ///////////////////////////////////////////////////////////
120
121 /*! Base class for chaining iterators.
122  *  This class is designed to be overloaded
123  *  in order to describe chaining rules.
124  *  It makes the works of chaining rules description 
125  *  easier.
126  *  The two main methods that need to overloaded are 
127  *  traverse() and init(). 
128  *  traverse() tells which ViewEdge to follow, among the adjacent ones.
129  *  If you specify restriction rules (such as "Chain only 
130  *  ViewEdges of the selection"), they will be included 
131  *  in the adjacency iterator. (i.e, the adjacent iterator 
132  *  will only stop on "valid" edges).
133  */
134 class LIB_STROKE_EXPORT ChainingIterator : public ViewEdgeInternal::ViewEdgeIterator{
135 protected:
136   bool _restrictToSelection;
137   bool _restrictToUnvisited;
138   bool _increment; //true if we're currently incrementing, false when decrementing
139   
140 public:
141         
142         ViewEdge *result;
143         PyObject *py_c_it;
144         
145   /*! Builds a Chaining Iterator from the first ViewEdge used for iteration
146    *  and its orientation.
147    *  \param iRestrictToSelection
148    *    Indicates whether to force the chaining to stay within
149    *    the set of selected ViewEdges or not.
150    *  \param iRestrictToUnvisited
151    *    Indicates whether a ViewEdge that has already been chained
152    *    must be ignored ot not.
153    *  \param begin
154    *    The ViewEdge from which to start the chain.
155    *  \param orientation
156    *    The direction to follow to explore the graph. If true,
157    *    the direction indicated by the first ViewEdge is used.
158    */
159   ChainingIterator(bool iRestrictToSelection = true, bool iRestrictToUnvisited = true, ViewEdge* begin = 0, bool orientation = true)
160     : ViewEdgeIterator(begin, orientation) {
161     _restrictToSelection = iRestrictToSelection;
162     _restrictToUnvisited = iRestrictToUnvisited;
163     _increment = true;
164         py_c_it = 0;
165   }
166
167   /*! Copy constructor */
168   ChainingIterator(const ChainingIterator& brother)
169     : ViewEdgeIterator(brother) {
170     _restrictToSelection = brother._restrictToSelection;
171     _restrictToUnvisited = brother._restrictToUnvisited;
172     _increment = brother._increment;
173         py_c_it = brother.py_c_it;
174   }
175
176   /*! Returns the string "ChainingIterator" */
177   virtual string getExactTypeName() const {
178     return "ChainingIterator";
179   }
180
181   /*! Inits the iterator context.
182    *  This method is called each time 
183    *  a new chain is started.
184    *  It can be used to reset some 
185    *  history information that you 
186    *  might want to keep.  
187    */
188   virtual int init() {
189         return Director_BPy_ChainingIterator_init( this );
190   }
191   
192   /*! This method iterates over the potential next 
193    *  ViewEdges and returns the one that will be 
194    *  followed next.
195    *  returns the next ViewEdge to follow or 
196    *  0 when the end of the chain is reached.
197    *  \param it
198    *    The iterator over the ViewEdges adjacent to 
199    *    the end vertex of the current ViewEdge.
200    *    The Adjacency iterator reflects the restriction 
201    *    rules by only iterating over the valid ViewEdges.
202    */
203   virtual int traverse(const AdjacencyIterator &it){
204         return Director_BPy_ChainingIterator_traverse( this, const_cast<AdjacencyIterator &>(it) );
205   }
206
207   /* accessors */
208   /*! Returns true if the orientation of the current ViewEdge 
209    *  corresponds to its natural orientation
210    */
211   //inline bool getOrientation() const {}
212   /*! Returns the vertex which is the next crossing */
213   inline ViewVertex * getVertex() {
214     if(_increment){
215       if(_orientation){
216         return _edge->B();
217       }else{
218         return _edge->A();
219       }  
220     }else{
221       if(_orientation){
222         return _edge->A();
223       }else{
224         return _edge->B();
225       }
226     }
227   }
228
229   /*! Returns true if the current iteration is an incrementation */
230   inline bool isIncrementing() const{
231     return _increment;
232   }
233   
234   /* increments.*/
235   virtual int increment() ;
236   virtual int decrement() ;
237 };
238
239 //
240 // Chaining iterators definitions
241 //
242 ///////////////////////////////////////////////////////////
243
244 /*! A ViewEdge Iterator used to follow ViewEdges the most naturally.
245  *  For example, it will follow visible ViewEdges of same nature.
246  *  As soon, as the nature or the visibility changes, the iteration
247  *  stops (by setting the pointed ViewEdge to 0).
248  *  In the case of an iteration over a set of ViewEdge that are both
249  *  Silhouette and Crease, there will be a precedence of the silhouette
250  *  over the crease criterion.
251  */
252 class LIB_STROKE_EXPORT ChainSilhouetteIterator : public ChainingIterator
253 {
254 public:
255   /*! Builds a ChainSilhouetteIterator from the first ViewEdge used for iteration
256    *  and its orientation.
257    *  \param iRestrictToSelection
258    *    Indicates whether to force the chaining to stay within
259    *    the set of selected ViewEdges or not.
260    *  \param begin
261    *    The ViewEdge from where to start the iteration.
262    *  \param orientation
263    *    If true, we'll look for the next ViewEdge among the
264    *    ViewEdges that surround the ending ViewVertex of begin.
265    *    If false, we'll search over the ViewEdges surrounding
266    *    the ending ViewVertex of begin.
267    */
268   ChainSilhouetteIterator(bool iRestrictToSelection = true, ViewEdge* begin = NULL, bool orientation = true)
269     : ChainingIterator(iRestrictToSelection, true, begin, orientation) {}
270
271   /*! Copy constructor */
272   ChainSilhouetteIterator(const ChainSilhouetteIterator& brother)
273     : ChainingIterator(brother) {}
274
275   /*! Returns the string "ChainSilhouetteIterator" */
276   virtual string getExactTypeName() const {
277     return "ChainSilhouetteIterator";
278   }
279
280   /*! This method iterates over the potential next 
281    *  ViewEdges and returns the one that will be 
282    *  followed next.
283    *  When reaching the end of a chain, 0 is returned.
284    */
285   virtual int traverse(const AdjacencyIterator& it);
286
287         /*! Inits the iterator context */ 
288   virtual int init() {
289     return 0;
290   }
291 };
292
293 //
294 // ChainPredicateIterator
295 //
296 ///////////////////////////////////////////////////////////
297
298 /*! A "generic" user-controlled ViewEdge iterator. This iterator
299  *  is in particular built from a unary predicate and a binary predicate.
300  *  First, the unary predicate is evaluated for all potential next ViewEdges
301  *  in order to only keep the ones respecting a certain constraint.
302  *  Then, the binary predicate is evaluated on the current ViewEdge
303  *  together with each ViewEdge of the previous selection. The first
304  *  ViewEdge respecting both the unary predicate and the binary predicate
305  *  is kept as the next one. If none of the potential next ViewEdge respects
306  *  these 2 predicates, 0 is returned.
307  */
308 class LIB_STROKE_EXPORT ChainPredicateIterator : public ChainingIterator
309 {
310 protected:
311   BinaryPredicate1D *_binary_predicate; // the caller is responsible for the deletion of this object
312   UnaryPredicate1D  *_unary_predicate;  // the caller is responsible for the deletion of this object
313 public:
314
315   /*! Builds a ChainPredicateIterator from a starting ViewEdge and its orientation.
316    *  \param iRestrictToSelection
317    *    Indicates whether to force the chaining to stay within
318    *    the set of selected ViewEdges or not.
319    *  \param iRestrictToUnvisited
320    *    Indicates whether a ViewEdge that has already been chained
321    *    must be ignored ot not.
322    *  \param begin
323    *    The ViewEdge from where to start the iteration.
324    *  \param orientation
325    *    If true, we'll look for the next ViewEdge among the
326    *    ViewEdges that surround the ending ViewVertex of begin.
327    *    If false, we'll search over the ViewEdges surrounding
328    *    the ending ViewVertex of begin.
329    */
330   ChainPredicateIterator(bool iRestrictToSelection = true, bool iRestrictToUnvisited = true, ViewEdge* begin = NULL, bool orientation = true)
331     : ChainingIterator(iRestrictToSelection, iRestrictToUnvisited, begin, orientation) {
332     _binary_predicate = 0;
333     _unary_predicate = 0;
334   }
335
336   /*! Builds a ChainPredicateIterator from a unary predicate, a binary predicate, a starting ViewEdge and its orientation.
337    *  \param iRestrictToSelection
338    *    Indicates whether to force the chaining to stay within
339    *    the set of selected ViewEdges or not.
340    *  \param iRestrictToUnvisited
341    *    Indicates whether a ViewEdge that has already been chained
342    *    must be ignored ot not.
343    *  \param upred
344    *    The unary predicate that the next ViewEdge must satisfy.
345    *  \param bpred
346    *    The binary predicate that the next ViewEdge must satisfy
347    *    together with the actual pointed ViewEdge. 
348    *  \param begin
349    *    The ViewEdge from where to start the iteration.
350    *  \param orientation
351    *    If true, we'll look for the next ViewEdge among the
352    *    ViewEdges that surround the ending ViewVertex of begin.
353    *    If false, we'll search over the ViewEdges surrounding
354    *    the ending ViewVertex of begin.
355    */
356   ChainPredicateIterator(UnaryPredicate1D& upred, BinaryPredicate1D& bpred, bool iRestrictToSelection = true, bool iRestrictToUnvisited = true, ViewEdge* begin = NULL, bool orientation = true)
357     : ChainingIterator(iRestrictToSelection, iRestrictToUnvisited, begin, orientation) {
358     _unary_predicate = &upred;
359     _binary_predicate = &bpred;
360   }
361
362   /*! Copy constructor */
363   ChainPredicateIterator(const ChainPredicateIterator& brother)
364     : ChainingIterator(brother){
365     _unary_predicate = brother._unary_predicate;
366     _binary_predicate = brother._binary_predicate;
367   }
368
369   /*! Destructor. */
370   virtual ~ChainPredicateIterator(){
371     _unary_predicate = 0;
372     _binary_predicate = 0;
373   }
374
375   /*! Returns the string "ChainPredicateIterator" */
376   virtual string getExactTypeName() const {
377     return "ChainPredicateIterator";
378   }
379
380   /*! This method iterates over the potential next 
381    *  ViewEdges and returns the one that will be 
382    *  followed next.
383    *  When reaching the end of a chain, 0 is returned.
384    */
385   virtual int traverse(const AdjacencyIterator &it);
386
387         /*! Inits the iterator context */ 
388   virtual int init() {
389         return 0;
390   }
391  
392 };
393
394 #endif // CHAININGITERATORS_H