DGtal  0.9.2
EuclideanShapesDecorator.h
1 
17 #pragma once
18 
30 #if defined(EuclideanShapesDecorator_RECURSES)
31 #error Recursive header files inclusion detected in EuclideanShapesDecorator.h
32 #else // defined(EuclideanShapesDecorator_RECURSES)
33 
34 #define EuclideanShapesDecorator_RECURSES
35 
36 #if !defined EuclideanShapesDecorator_h
37 
38 #define EuclideanShapesDecorator_h
39 
41 // Inclusions
42 #include <iostream>
43 #include "DGtal/base/Common.h"
44 #include "DGtal/base/ConstAlias.h"
45 
46 #include "DGtal/shapes/CEuclideanBoundedShape.h"
47 #include "DGtal/shapes/CEuclideanOrientedShape.h"
49 
50 namespace DGtal
51 {
52 
54  // template class EuclideanShapesCSG
66  template <typename ShapeA, typename ShapeB>
68  {
69  protected:
71  {
75  };
76 
77  public:
80 
81  typedef typename ShapeA::Space Space;
82  typedef typename ShapeA::RealPoint RealPoint;
83 
89  : bIsValid(false)
90  {}
91 
98  : myShapeA(other.myShapeA), v_shapes(other.v_shapes),
100  bIsValid(other.bIsValid)
101  {}
102 
109  : myShapeA( a )
110  {
111  myLowerBound = myShapeA->getLowerBound();
112  myUpperBound = myShapeA->getUpperBound();
113 
114  bIsValid = true;
115  }
116 
125  {
126  myShapeA = other.myShapeA;
127  v_shapes = other.v_shapes;
128 
129  myLowerBound = other.myLowerBound;
130  myUpperBound = other.myUpperBound;
131 
132  bIsValid = other.bIsValid;
133 
134  return *this;
135  }
136 
143  {
144  myShapeA = a;
145 
146  myLowerBound = myShapeA->getLowerBound();
147  myUpperBound = myShapeA->getUpperBound();
148 
149  bIsValid = true;
150  }
151 
159  {
162 
163  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
164 
165  std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_plus, b );
166 
167  for(Dimension i =0; i < Space::dimension; ++i)
168  {
169  myLowerBound[i] = std::min(myLowerBound[i], b->getLowerBound()[i]);
170  myUpperBound[i] = std::max(myUpperBound[i], b->getUpperBound()[i]);
171  }
172 
173  v_shapes.push_back(shape);
174  }
175 
183  {
186 
187  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
188 
189  std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_intersection, b );
190 
191  for(Dimension i=0; i < Space::dimension; ++i)
192  {
193  myLowerBound[i] = std::max(myLowerBound[i], b->getLowerBound()[i]);
194  myUpperBound[i] = std::min(myUpperBound[i], b->getUpperBound()[i]);
195  }
196 
197  v_shapes.push_back(shape);
198  }
199 
207  {
210 
211  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
212 
213  std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_minus, b );
214 
215  v_shapes.push_back(shape);
216  }
217 
222  RealPoint getLowerBound() const
223  {
224  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
225 
226  return myLowerBound;
227  }
228 
233  RealPoint getUpperBound() const
234  {
235  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
236 
237  return myUpperBound;
238  }
239 
248  Orientation orientation( const RealPoint & p ) const
249  {
250  FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
251 
252  Orientation orient = myShapeA->orientation( p );
253 
254  for(unsigned int i = 0; i < v_shapes.size(); ++i)
255  {
256  if( v_shapes[i].first == e_minus )
257  {
258  if (( v_shapes[i].second->orientation( p ) == INSIDE ) || ( v_shapes[i].second->orientation( p ) == ON ))
259  {
260  orient = OUTSIDE;
261  }
262  }
263  else if( v_shapes[i].first == e_intersection )
264  {
265  if (( orient == ON ) && ( v_shapes[i].second->orientation( p ) != OUTSIDE ))
266  {
267  orient = ON;
268  }
269  else if (( v_shapes[i].second->orientation( p ) == ON ) && ( orient != OUTSIDE ))
270  {
271  orient = ON;
272  }
273  else if (( orient == INSIDE ) && ( v_shapes[i].second->orientation( p ) == INSIDE ))
274  {
275  orient = INSIDE;
276  }
277  else
278  {
279  orient = OUTSIDE;
280  }
281  }
282  else
283  {
284  if (( orient == INSIDE ) || ( v_shapes[i].second->orientation( p ) == INSIDE ))
285  {
286  orient = INSIDE;
287  }
288  else if (( orient == ON ) || ( v_shapes[i].second->orientation( p ) == ON ))
289  {
290  orient = ON;
291  }
292  else
293  {
294  orient = OUTSIDE;
295  }
296  }
297  }
298 
299  return orient;
300  }
301 
302  public:
303 
308  void selfDisplay ( std::ostream & out ) const;
309 
314  bool isValid() const
315  {
316  return bIsValid;
317  }
318 
319  // ------------------------- Internals ------------------------------------
320  private:
321 
324 
326  std::vector< std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > > v_shapes;
327 
329  RealPoint myLowerBound;
330 
332  RealPoint myUpperBound;
333 
335  bool bIsValid;
336 
337  };
338 
339 namespace deprecated
340 {
342 // template class EuclideanShapesDecorator
351  template <typename ShapeA, typename ShapeB>
353  {
354  // ----------------------- Standard services ------------------------------
355  public:
360 
361  typedef typename ShapeA::Space Space;
362  typedef typename ShapeA::RealPoint RealPoint;
363 
371  : myShapeA( a ),
372  myShapeB( b )
373  {
374  RealPoint shapeALowerBoundary = myShapeA.getLowerBound();
375  RealPoint shapeBLowerBoundary = myShapeB.getLowerBound();
376  RealPoint shapeAUpperBoundary = myShapeA.getUpperBound();
377  RealPoint shapeBUpperBoundary = myShapeB.getUpperBound();
378  for ( unsigned int i = 0; i < myLowerBound.size(); ++i )
379  {
380  myLowerBound[ i ] = std::min( shapeALowerBoundary[ i ], shapeBLowerBoundary[ i ] );
381  myUpperBound[ i ] = std::max( shapeAUpperBoundary[ i ], shapeBUpperBoundary[ i ] );
382  }
383  }
384 
389  RealPoint getLowerBound() const
390  {
391  return myLowerBound;
392  }
393 
398  RealPoint getUpperBound() const
399  {
400  return myUpperBound;
401  }
402 
410  Orientation orientation( const RealPoint & p ) const
411  {
412  if (( myShapeA.orientation( p ) == INSIDE ) || ( myShapeB.orientation( p ) == INSIDE ))
413  {
414  return INSIDE;
415  }
416  else if (( myShapeA.orientation( p ) == ON ) || ( myShapeB.orientation( p ) == ON ))
417  {
418  return ON;
419  }
420  return OUTSIDE;
421  }
422 
427 
428  // ----------------------- Interface --------------------------------------
429  public:
430 
435  void selfDisplay ( std::ostream & out ) const;
436 
441  bool isValid() const;
442 
443  // ------------------------- Hidden services ------------------------------
444  protected:
445 
451 
452  private:
453 
459  EuclideanShapesUnion ( const EuclideanShapesUnion & other );
460 
468 
469  // ------------------------- Internals ------------------------------------
470  private:
471  const ShapeA & myShapeA;
472  const ShapeB & myShapeB;
473 
474  RealPoint myLowerBound;
475  RealPoint myUpperBound;
476 
477  }; // end of class EuclideanShapesUnion
478 
480  // template class EuclideanShapesIntersection
488  template <typename ShapeA, typename ShapeB>
490  {
491  // ----------------------- Standard services ------------------------------
492  public:
497 
498  typedef typename ShapeA::Space Space;
499  typedef typename ShapeA::RealPoint RealPoint;
500 
508  : myShapeA( a ),
509  myShapeB( b )
510  {
511  RealPoint shapeALowerBoundary = myShapeA.getLowerBound();
512  RealPoint shapeBLowerBoundary = myShapeB.getLowerBound();
513  RealPoint shapeAUpperBoundary = myShapeA.getUpperBound();
514  RealPoint shapeBUpperBoundary = myShapeB.getUpperBound();
515  for ( unsigned int i = 0; i < myLowerBound.size(); ++i )
516  {
517  myLowerBound[ i ] = std::min( shapeALowerBoundary[ i ], shapeBLowerBoundary[ i ] );
518  myUpperBound[ i ] = std::max( shapeAUpperBoundary[ i ], shapeBUpperBoundary[ i ] );
519  }
520  }
521 
522 
527  RealPoint getLowerBound() const
528  {
529  return myLowerBound;
530  }
531 
536  RealPoint getUpperBound() const
537  {
538  return myUpperBound;
539  }
540 
548  Orientation orientation( const RealPoint & p ) const
549  {
550  if (( myShapeA.orientation( p ) == ON ) && ( myShapeB.orientation( p ) != OUTSIDE ))
551  {
552  return ON;
553  }
554  else if (( myShapeB.orientation( p ) == ON ) && ( myShapeA.orientation( p ) != OUTSIDE ))
555  {
556  return ON;
557  }
558  else if (( myShapeA.orientation( p ) == INSIDE ) && ( myShapeB.orientation( p ) == INSIDE ))
559  {
560  return INSIDE;
561  }
562 
563  return OUTSIDE;
564  }
565 
566 
571 
572  // ----------------------- Interface --------------------------------------
573  public:
574 
579  void selfDisplay ( std::ostream & out ) const;
580 
585  bool isValid() const;
586 
587  // ------------------------- Hidden services ------------------------------
588  protected:
589 
595 
596  private:
597 
604 
612 
613  // ------------------------- Internals ------------------------------------
614  private:
615  const ShapeA & myShapeA;
616  const ShapeB & myShapeB;
617 
618  RealPoint myLowerBound;
619  RealPoint myUpperBound;
620 
621  }; // end of class EuclideanShapesIntersection
622 
624  // template class EuclideanShapesMinus
632  template <typename ShapeA, typename ShapeB>
634  {
635  // ----------------------- Standard services ------------------------------
636  public:
641 
642  typedef typename ShapeA::Space Space;
643  typedef typename ShapeA::RealPoint RealPoint;
644 
652  : myShapeA( a ),
653  myShapeB( b )
654  {
655  RealPoint shapeALowerBoundary = myShapeA.getLowerBound();
656  RealPoint shapeBLowerBoundary = myShapeB.getLowerBound();
657  RealPoint shapeAUpperBoundary = myShapeA.getUpperBound();
658  RealPoint shapeBUpperBoundary = myShapeB.getUpperBound();
659  for ( unsigned int i = 0; i < myLowerBound.size(); ++i )
660  {
661  myLowerBound[ i ] = std::min( shapeALowerBoundary[ i ], shapeBLowerBoundary[ i ] );
662  myUpperBound[ i ] = std::max( shapeAUpperBoundary[ i ], shapeBUpperBoundary[ i ] );
663  }
664  }
665 
670  RealPoint getLowerBound() const
671  {
672  return myLowerBound;
673  }
674 
679  RealPoint getUpperBound() const
680  {
681  return myUpperBound;
682  }
683 
691  Orientation orientation( const RealPoint & p ) const
692  {
693  if (( myShapeB.orientation( p ) == INSIDE ) || ( myShapeB.orientation( p ) == ON ))
694  {
695  return OUTSIDE;
696  }
697  return myShapeA.orientation( p );
698  }
699 
700 
705 
706  // ----------------------- Interface --------------------------------------
707  public:
708 
713  void selfDisplay ( std::ostream & out ) const;
714 
719  bool isValid() const;
720 
721  // ------------------------- Hidden services ------------------------------
722  protected:
723 
729 
730  private:
731 
737  EuclideanShapesMinus ( const EuclideanShapesMinus & other );
738 
746 
747  // ------------------------- Internals ------------------------------------
748  private:
749  const ShapeA & myShapeA;
750  const ShapeB & myShapeB;
751 
752  RealPoint myLowerBound;
753  RealPoint myUpperBound;
754 
755  }; // end of class EuclideanShapesMinus
756 
757 
758  }
759 
760 
767  template <typename ShapeA, typename ShapeB>
768  std::ostream&
769  operator<< ( std::ostream & out, const deprecated::EuclideanShapesUnion<ShapeA, ShapeB> & object );
770 
771  template <typename ShapeA, typename ShapeB>
772  std::ostream&
773  operator<< ( std::ostream & out, const deprecated::EuclideanShapesIntersection<ShapeA, ShapeB> & object );
774 
775  template <typename ShapeA, typename ShapeB>
776  std::ostream&
777  operator<< ( std::ostream & out, const deprecated::EuclideanShapesMinus<ShapeA, ShapeB> & object );
778 
779 } // namespace DGtal
780 
781 
782 // //
784 
785 #endif // !defined EuclideanShapesDecorator_h
786 
787 #undef EuclideanShapesDecorator_RECURSES
788 #endif // else defined(EuclideanShapesDecorator_RECURSES)
void selfDisplay(std::ostream &out) const
RealPoint myLowerBound
Domain lower bound.
static const Dimension dimension
static constants to store the dimension.
Definition: SpaceND.h:132
BOOST_CONCEPT_ASSERT((concepts::CEuclideanBoundedShape< ShapeA >))
EuclideanShapesIntersection & operator=(const EuclideanShapesIntersection &other)
EuclideanShapesMinus & operator=(const EuclideanShapesMinus &other)
EuclideanShapesMinus(ConstAlias< ShapeA > a, ConstAlias< ShapeB > b)
Aim: This class encapsulates its parameter class so that to indicate to the user that the object/poin...
Definition: ConstAlias.h:186
EuclideanShapesUnion(ConstAlias< ShapeA > a, ConstAlias< ShapeB > b)
DGtal::uint32_t Dimension
Definition: Common.h:113
EuclideanShapesIntersection(ConstAlias< ShapeA > a, ConstAlias< ShapeB > b)
CountedConstPtrOrConstPtr< ShapeA > myShapeA
Base Shape.
Aim: Intersection between two models of CEuclideanBoundedShape and CEuclideanOrientedShape.
void selfDisplay(std::ostream &out) const
Aim: Minus between two models of CEuclideanBoundedShape and CEuclideanOrientedShape.
EuclideanShapesUnion & operator=(const EuclideanShapesUnion &other)
Orientation
Definition: Common.h:118
void setParams(ConstAlias< ShapeA > a)
BOOST_CONCEPT_ASSERT((concepts::CEuclideanBoundedShape< ShapeA >))
EuclideanShapesCSG(const EuclideanShapesCSG &other)
void plus(ConstAlias< ShapeB > b)
Aim: Constructive Solid Geometry (CSG) between models of CEuclideanBoundedShape and CEuclideanOriente...
EuclideanShapesCSG & operator=(const EuclideanShapesCSG &other)
RealPoint myUpperBound
Domain upper bound.
Orientation orientation(const RealPoint &p) const
BOOST_CONCEPT_ASSERT((concepts::CEuclideanBoundedShape< ShapeA >))
void selfDisplay(std::ostream &out) const
Aim: characterizes models of digital oriented shapes. For example, models should provide an orientati...
DGtal is the top-level namespace which contains all DGtal functions and types.
BOOST_CONCEPT_ASSERT((concepts::CEuclideanBoundedShape< ShapeA >))
std::vector< std::pair< e_operator, CountedConstPtrOrConstPtr< ShapeB > > > v_shapes
Vector of all operations (ordered) of ShapeB.
bool bIsValid
if the CSG is valid.
Orientation orientation(const RealPoint &p) const
void selfDisplay(std::ostream &out) const
Aim: Union between two models of CEuclideanBoundedShape and CEuclideanOrientedShape.
void minus(ConstAlias< ShapeB > b)
Orientation orientation(const RealPoint &p) const
Orientation orientation(const RealPoint &p) const
void intersection(ConstAlias< ShapeB > b)
EuclideanShapesCSG(ConstAlias< ShapeA > a)