Loading [MathJax]/extensions/TeX/AMSsymbols.js
DGtal 2.0.0
DigitalShapesDecorator.h
1
16
17#pragma once
18
29
30#if defined(DigitalShapesDecorator_RECURSES)
31#error Recursive header files inclusion detected in DigitalShapesDecorator.h
32#else // defined(DigitalShapesDecorator_RECURSES)
34#define DigitalShapesDecorator_RECURSES
35
36#if !defined DigitalShapesDecorator_h
38#define DigitalShapesDecorator_h
39
41// Inclusions
42#include <iostream>
43#include "DGtal/base/Common.h"
44#include "DGtal/base/ConstAlias.h"
45
46#include "DGtal/shapes/CDigitalBoundedShape.h"
47#include "DGtal/shapes/CDigitalOrientedShape.h"
49
50namespace DGtal
51{
52
54 // template class DigitalShapesCSG
66 template <typename ShapeA, typename ShapeB>
68 {
69 protected:
76
77 public:
80
81 typedef typename ShapeA::Space Space;
82 typedef typename ShapeA::Point Point;
83
89 : bIsValid(false)
90 {}
91
98 : myShapeA(other.myShapeA), v_shapes(other.v_shapes),
100 bIsValid(other.bIsValid)
101 {}
102
103
110 : myShapeA( a )
111 {
112 myLowerBound = myShapeA->getLowerBound();
113 myUpperBound = myShapeA->getUpperBound();
114
115 bIsValid = true;
116 }
117
126 {
127 myShapeA = other.myShapeA;
128 v_shapes = other.v_shapes;
129
132
133 bIsValid = other.bIsValid;
134
135 return *this;
136 }
137
144 {
145 myShapeA = a;
146
147 myLowerBound = myShapeA->getLowerBound();
148 myUpperBound = myShapeA->getUpperBound();
149
150 bIsValid = true;
151 }
152
160 {
163
164 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
165
166 std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_plus, b );
167
168 for(Dimension i =0; i < Space::dimension; ++i)
169 {
170 myLowerBound[i] = std::min(myLowerBound[i], b->getLowerBound()[i]);
171 myUpperBound[i] = std::max(myUpperBound[i], b->getUpperBound()[i]);
172 }
173
174 v_shapes.push_back(shape);
175 }
176
184 {
187
188 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
189
190 std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_intersection, b );
191
192 for(Dimension i=0; i < Space::dimension; ++i)
193 {
194 myLowerBound[i] = std::max(myLowerBound[i], b->getLowerBound()[i]);
195 myUpperBound[i] = std::min(myUpperBound[i], b->getUpperBound()[i]);
196 }
197
198 v_shapes.push_back(shape);
199 }
200
208 {
211
212 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
213
214 std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > shape( e_minus, b );
215
216 v_shapes.push_back(shape);
217
218 }
219
225 {
226 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
227
228 return myLowerBound;
229 }
230
236 {
237 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
238
239 return myUpperBound;
240 }
241
250 Orientation orientation( const Point & p ) const
251 {
252 FATAL_ERROR_MSG( isValid(), "Operation invalid. Maybe you don't set a ShapeA object." );
253
254 Orientation orient = myShapeA->orientation( p );
255
256 for(unsigned int i = 0; i < v_shapes.size(); ++i)
257 {
258 if( v_shapes[i].first == e_minus )
259 {
260 if (( v_shapes[i].second->orientation( p ) == INSIDE ) || ( v_shapes[i].second->orientation( p ) == ON ))
261 {
262 orient = OUTSIDE;
263 }
264 }
265 else if( v_shapes[i].first == e_intersection )
266 {
267 if (( orient == ON ) && ( v_shapes[i].second->orientation( p ) != OUTSIDE ))
268 {
269 orient = ON;
270 }
271 else if (( v_shapes[i].second->orientation( p ) == ON ) && ( orient != OUTSIDE ))
272 {
273 orient = ON;
274 }
275 else if (( orient == INSIDE ) && ( v_shapes[i].second->orientation( p ) == INSIDE ))
276 {
277 orient = INSIDE;
278 }
279 else
280 {
281 orient = OUTSIDE;
282 }
283 }
284 else
285 {
286 if (( orient == INSIDE ) || ( v_shapes[i].second->orientation( p ) == INSIDE ))
287 {
288 orient = INSIDE;
289 }
290 else if (( orient == ON ) || ( v_shapes[i].second->orientation( p ) == ON ))
291 {
292 orient = ON;
293 }
294 else
295 {
296 orient = OUTSIDE;
297 }
298 }
299 }
300
301 return orient;
302 }
303
304 public:
305
310 void selfDisplay ( std::ostream & out ) const;
311
316 bool isValid() const
317 {
318 return bIsValid;
319 }
320
321 // ------------------------- Internals ------------------------------------
322 private:
323
326
328 std::vector< std::pair<e_operator, CountedConstPtrOrConstPtr< ShapeB > > > v_shapes;
329
332
335
338
339 };
340} // namespace DGtal
341
342
343
344#endif // !defined DigitalShapesDecorator_h
345
346#undef DigitalShapesDecorator_RECURSES
347#endif // else defined(DigitalShapesDecorator_RECURSES)
Aim: This class encapsulates its parameter class so that to indicate to the user that the object/poin...
Definition ConstAlias.h:187
void plus(ConstAlias< ShapeB > b)
DigitalShapesCSG & operator=(const DigitalShapesCSG &other)
std::vector< std::pair< e_operator, CountedConstPtrOrConstPtr< ShapeB > > > v_shapes
Vector of all operations (ordered) of ShapeB.
CountedConstPtrOrConstPtr< ShapeA > myShapeA
Base Shape.
void selfDisplay(std::ostream &out) const
DigitalShapesCSG(ConstAlias< ShapeA > a)
Point myUpperBound
Domain upper bound.
BOOST_CONCEPT_ASSERT((concepts::CDigitalOrientedShape< ShapeA >))
Orientation orientation(const Point &p) const
Point myLowerBound
Domain lower bound.
DigitalShapesCSG(const DigitalShapesCSG &other)
void minus(ConstAlias< ShapeB > b)
void intersection(ConstAlias< ShapeB > b)
void setParams(ConstAlias< ShapeA > a)
bool bIsValid
if the CSG is valid.
BOOST_CONCEPT_ASSERT((concepts::CDigitalBoundedShape< ShapeA >))
static const Dimension dimension
Definition SpaceND.h:132
DGtal is the top-level namespace which contains all DGtal functions and types.
DGtal::uint32_t Dimension
Definition Common.h:119
Orientation
Definition Common.h:124
@ INSIDE
Definition Common.h:124
@ OUTSIDE
Definition Common.h:124
@ ON
Definition Common.h:124
Aim: designs the concept of bounded shapes in DGtal (shape for which upper and lower bounding bounds ...
Aim: characterizes models of digital oriented shapes. For example, models should provide an orientati...