37 if(!loops[0]->is_ccw())
39 m_loops.push_back(loops[0]);
40 for(
size_t i=1; i<loops.size();i++ )
43 if( loops[i]->is_ccw() )
46 m_loops.push_back(loops[i]);
79 GISMO_ASSERT(u.cols() == 1,
"Waiting for a single point");
82 std::vector<T> tmp = m_loops[0]->lineIntersections(direction, u(direction,0) );
94 m_loops[0]->curve(0).eval_into( xx, e );
99 for(
index_t i=0; i!=e.cols(); i++)
101 if( (e( !direction, i )> u(!direction,0)) )
104 if ( (count % 2) == 0 )
107 for(
index_t v = 1; v<this->numLoops(); v++)
111 tmp= m_loops[v]->lineIntersections( direction, u(direction,0) );
115 gsAsMatrix<T> Ev(tmp);
116 m_loops[v]->curve(0).eval_into( Ev, e );
118 for(
index_t i=0; i!=e.cols(); i++)
121 if( e(!direction,i) > u(!direction,0) )
126 if( (count % 2) != 0 )
135 bool gsPlanarDomain<T>::onBoundary(gsMatrix<T>
const & u)
137 for(
index_t v=0; v< this->numLoops();v++)
141 if( m_loops[v]->isOn(u, parValue,1e-5 ) )
153 os <<
"Outer boundary: " << *m_loops[0];
154 if ( m_loops.size()>1 )
157 for (
typename std::vector<
gsCurveLoop<T> *>::const_iterator it =
158 m_loops.begin()+1; it != m_loops.end(); ++it)
161 os <<
"Bounding box: ["<< m_bbox.col(0).transpose()<<
", "
162 << m_bbox.col(1).transpose() <<
"]";
171 assert( (loopID>=0) && (loopID < numLoops()) );
174 switch (numEndPoints)
190 u.resize(2, (m_loops[loopID]->curves()).size() * np);
192 typename std::vector< gsCurve<T> *>::const_iterator it;
198 if (numEndPoints==0) {firstInd=1;secondInd=npoints-2;}
200 for ( it= (m_loops[loopID]->curves()).begin(); it!= (m_loops[loopID]->curves()).end(); ++it )
205 for (
int ii=firstInd;ii<=secondInd;ii++) pts(0,ii-firstInd)= (T)(ii)/(T)(npoints-1);
207 (*it)->eval_into( pts, uCols );
208 u.middleCols( i * np,np ) = uCols;
210 (*it)->eval_into( pts, uCols );
211 u.middleCols( i * np,np ) = uCols;
224 T dist=sqrt((x2-x1)*(x2-x1)+(y2-y1)*(y2-y1)+(z2-z1)*(z2-z1));
229 void gsPlanarDomain<T>::sampleCurve_into(
int loopID,
int curveID,
int npoints, gsMatrix<T> & u )
231 assert( (loopID>=0) && (loopID < numLoops()) );
232 assert( (curveID>=0) && (curveID < loop(loopID).size() ) );
234 typename std::vector< gsCurve<T> *>::const_iterator it;
235 for ( it= (m_loops[loopID]->curves()).begin()+curveID; it!= (m_loops[loopID]->curves()).begin()+curveID+1 ; ++it )
239 gsMatrix<T> pts(1,npoints);
240 for (
int ii=0;ii<=npoints-1;ii++)
241 { pts(0,ii)= (T)(ii)/(T)(npoints-1); };
242 (*it)->eval_into( pts, u );
250 typename gsMesh<T>::uPtr m(
new gsMesh<T>());
256 GISMO_ASSERT(npoints > 0,
"Number of points must be positive.");
259 T h_x = (m_bbox(0,1) - m_bbox(0,0) ) / (npoints-1) ,
260 h_y = (m_bbox(1,1) - m_bbox(1,0) ) / (npoints-1) ;
263 VertexList x_seg_begin;
264 VertexList x_seg_end;
267 std::vector<T> tmp = m_loops[0]->lineIntersections(0, xi );
268 gsDebug<<
"----- INTs: "<<tmp.size()<<
"( "<<xi<<
") \n";
271 m_loops[0]->curve(0).eval_into(xxi, xev );
273 std::sort( x_seg.data(), x_seg.data()+x_seg.size() );
275 for (
index_t j= 0; j!= x_seg.size(); j+=2 )
277 VertexHandle v = m->addVertex( xi, x_seg[j] );
278 if ( x_seg[j] < x_seg[j+1] )
280 x_seg_begin.push_back( v );
281 v = m->addVertex( xi, x_seg[j+1] );
282 x_seg_end.push_back ( v );
286 x_seg_end.push_back( v );
287 v = m->addVertex( xi, x_seg[j+1] );
288 x_seg_begin.push_back ( v );
293 for (
int i = 0; i!= npoints-1; ++i )
295 tmp = m_loops[0]->lineIntersections(0, xi );
296 gsDebug<<
"----- INTs: "<<tmp.size()<<
"( "<<xi<<
") \n";
299 m_loops[0]->curve(0).eval_into(xxi, xev );
301 std::sort( x_seg.data(), x_seg.data()+x_seg.size() );
303 for (
index_t j= 0; j!= x_seg.size(); j+=2 )
305 VertexHandle v = m->addVertex( xi, x_seg[j] );
306 if ( x_seg[j] < x_seg[j+1] )
308 x_seg_begin.push_back( v );
309 v = m->addVertex( xi, x_seg[j+1] );
310 x_seg_end.push_back ( v );
314 x_seg_end.push_back( v );
315 v = m->addVertex( xi, x_seg[j+1] );
316 x_seg_begin.push_back ( v );
323 std::sort( x_seg_begin.begin(), x_seg_begin.end(), Yless<T> );
324 std::sort( x_seg_end.begin() , x_seg_end.end() , Yless<T> );
326 gsDebug<<
"x-segments: "<<x_seg_begin.size()<<
", "<<x_seg_end.size()<<
"\n";
329 bool SegStart(
false), SegEnd(
false);
332 VertexListIter ss = x_seg_begin.begin(),
333 es = x_seg_end.begin();
337 for (
int i = 0; i!= npoints; ++i )
339 tmp = m_loops[0]->lineIntersections(1, yi );
344 gsDebug<<
"--- Intersection event "<<i<<
"( "<<yi<<
" )\n";
349 m_loops[0]->curve(0).eval_into(yyi, yev );
351 std::sort( y_seg.data(), y_seg.data()+y_seg.size() );
356 while( es != x_seg_end.end() && (*es)->y() < yi )
361 for ( VertexListIter it= line0.begin(); it!= line0.end(); ++it )
362 if ( (*it)->x() == (*es)->x() )
364 gsDebug<<
"SegEnd: removed "<< **it ;
372 for ( VertexListIter it= line0.begin(); it!= line0.end(); ++it )
374 v = m->addVertex( (*it)->x(), yi );
379 while( ss != x_seg_begin.end() && (*ss)->y() < yi )
382 gsDebug<<
"SegStart: added "<< (*ss)->x() <<
".\n";
383 line0.push_back(*(ss) );
384 v = m->addVertex( (*ss)->x(), yi );
389 std::sort( line0.begin(), line0.end(), Xless<T> );
390 std::sort( line1.begin(), line1.end(), Xless<T> );
392 gsDebug<<
"line0 has "<< line0.size() <<
" points\n";
393 gsDebug<<
"line1 has "<< line1.size() <<
" points\n";
396 if ( ! line1.empty() && line1.size() == line0.size() )
398 gsDebug<<
"Tiling row "<<i<<
".\n";
399 VertexListIter it0=line0.begin();
400 for ( VertexListIter it1= line1.begin(); it1!= line1.end()-1; ++it1, ++it0 )
401 m->addFace( *it0, *it1, *(it1+1), *(it0+1) );
406 VertexListIter it0=line0.begin();
407 for ( VertexListIter it1= line1.begin(); it1!= line1.end(); ++it1, ++it0 )
408 gsDebug<< (*it0)->x() <<
" - "<< (*it1)->x() <<
" \n";
409 while ( it0 != line0.end() )
410 gsDebug<< (*it0++)->x() <<
" - * " <<
" \n";
414 gsDebug<<
"Connecting endpoints.\n";
418 Yseg.push_back( m->addVertex( y_seg[0] , yi ) );
419 Yseg.push_back( m->addVertex( y_seg[y_seg.size()-1], yi ) );
426 m->addFace( Yprev[0], line0.front(), line0[1] );
427 m->addFace( Yprev[1], line0.back() , line0[line0.size()-2] );
430 m->addFace( Yseg[0], line1.front(), line0.front() );
431 m->addFace( Yseg[1], line1.back(), line0.back() );
433 else if ( Yprev.size() )
436 m->addFace( line1.front(), line0.front(), Yprev[0], Yseg[0] );
437 m->addFace( line1.back() , line0.back() , Yprev[1], Yseg[1] );
442 SegStart=SegEnd=
false;
458 T bbox_length_y =m_bbox(1,1)-m_bbox(1,0);
459 int yPoints = cast<T,int>( (T)(npoints)*bbox_length_y) ;
461 if(yPoints<lb_yPoints)
464 npoints *= lb_yPoints / yPoints;
466 npoints *= lb_yPoints / 2;
468 yPoints = lb_yPoints;
473 gsMatrix<T> y_samples = gsPointGrid<T>( m_bbox(1,0), m_bbox(1,1), yPoints);
481 std::vector<std::vector< VertexHandle > >samples;
482 std::vector<std::vector< VertexHandle > >intersections;
490 for (
int i = 0; i!= yPoints; ++i )
492 std::vector<T> x_all;
494 for (
size_t j=0;j<m_loops.size();j++)
496 std::vector<T> x = m_loops[j]->lineIntersections(1, y_samples(0,i) );
504 gsWarn<<
"lineIntersection yielded a tangent"<<
'\n';
506 else if (x.size()%2==1)
509 gsWarn<<
"lineIntersection yielded a tangent and more intersections, try another number of points"<<
'\n';
514 for (
size_t k=0;k<x.size();k++)
516 x_all.push_back(e(0,k));
520 std::sort(x_all.begin(), x_all.end() );
523 for (
typename std::vector<T>::const_iterator it = x_all.begin();
524 it < x_all.end(); it += 2 )
525 numPoints[k++] = cast<T,int>( (*(it+1) - *it)* (T)(npoints) );
527 std::vector<VertexHandle> x_line;
528 std::vector<VertexHandle> intersection_vec;
529 for(
index_t j=0;j<numPoints.size();j++)
531 x_line.push_back(m->addVertex(x_all[j*2],y_samples(0,i)));
532 intersection_vec.push_back(m->addVertex(x_all[j*2],y_samples(0,i)));
534 for(k=0; k<numPoints[j]; k++)
536 x_line.push_back(m->addVertex(x_all[j*2]*(T)(numPoints[j]-k)/(T)(numPoints[j]+1)+x_all[j*2+1]*(T)(k+1)/(T)(numPoints[j]+1),y_samples(0,i)));
538 x_line.push_back(m->addVertex(x_all[j*2+1],y_samples(0,i)));
539 intersection_vec.push_back(m->addVertex(x_all[j*2+1],y_samples(0,i)));
541 samples.push_back(x_line);
542 intersections.push_back(intersection_vec);
544 T checkDist=(y_samples(0,1)-y_samples(0,0))*(T)(5);
545 for(
size_t i=0;i<intersections.size()-1;i++)
552 if(samples[i].size()>0&&samples[i+1].size()>0)
554 while (currentTop!=samples[i].size()-1||currentBot!=samples[i+1].size()-1)
556 if(currentTop==samples[i].size()-1)
558 VertexHandle v1=samples[i][currentTop];
559 VertexHandle v2=samples[i+1][currentBot];
560 VertexHandle v3=samples[i+1][currentBot+1];
561 if(getDistance(v1,v2)<checkDist&&getDistance(v1,v3)<checkDist&&getDistance(v2,v3)<checkDist)
562 m->addFace(v1,v2,v3);
565 else if(currentBot==samples[i+1].size()-1)
567 VertexHandle v1=samples[i][currentTop];
568 VertexHandle v2=samples[i+1][currentBot];
569 VertexHandle v3=samples[i][currentTop+1];
570 if(getDistance(v1,v2)<checkDist&&getDistance(v1,v3)<checkDist&&getDistance(v2,v3)<checkDist)
571 m->addFace(v1,v2,v3);
576 topToBotDist=getDistance(samples[i][currentTop],samples[i+1][currentBot+1]);
577 botToTopDist=getDistance(samples[i][currentTop+1],samples[i+1][currentBot]);
578 if (topToBotDist<botToTopDist)
580 VertexHandle v1=samples[i][currentTop];
581 VertexHandle v2=samples[i+1][currentBot];
582 VertexHandle v3=samples[i+1][currentBot+1];
583 if(getDistance(v1,v2)<checkDist&&getDistance(v1,v3)<checkDist&&getDistance(v2,v3)<checkDist)
584 m->addFace(v1,v2,v3);
589 VertexHandle v1=samples[i][currentTop];
590 VertexHandle v2=samples[i+1][currentBot];
591 VertexHandle v3=samples[i][currentTop+1];
592 if(getDistance(v1,v2)<checkDist&&getDistance(v1,v3)<checkDist&&getDistance(v2,v3)<checkDist)
593 m->addFace(v1,v2,v3);
Knot vector for B-splines.
Provides definition of gsTemplate class.
void sampleLoop_into(int loopID, int npoints, int numEndPoints, gsMatrix< T > &u)
linearly discriti
Definition: gsPlanarDomain.hpp:169
Creates a mapped object or data pointer to a matrix without copying data.
Definition: gsLinearAlgebra.h:126
#define gsDebug
Definition: gsDebug.h:61
memory::unique_ptr< gsMesh< T > > toMesh(int npoints=50) const
Return a triangulation of the planar domain.
Definition: gsPlanarDomain.hpp:248
Provides declaration of ConstantFunction class.
gsMatrix< T > eval(const gsMatrix< T > &u) const
Evaluate the function,.
Definition: gsFunctionSet.hpp:120
#define index_t
Definition: gsConfig.h:32
#define GISMO_ASSERT(cond, message)
Definition: gsDebug.h:89
Class Representing a triangle mesh with 3D vertices.
Definition: gsMesh.h:31
#define gsWarn
Definition: gsDebug.h:50
GISMO_DEPRECATED index_t direction(index_t s)
Returns the parametric direction that corresponds to side s.
Definition: gsBoundary.h:1048
gsPlanarDomain()
Default empty constructor.
Definition: gsPlanarDomain.h:51
T x() const
Definition: gsVertex.h:108
Provides declaration of the Mesh class.
Represents a B-spline curve/function with one parameter.
Class representing a Planar domain with an outer boundary and a number of holes.
Definition: gsPlanarDomain.h:43
T y() const
Definition: gsVertex.h:110
memory::unique_ptr< gsCurve > uPtr
Unique pointer for gsCurve.
Definition: gsCurve.h:38
This is the main header file that collects wrappers of Eigen for linear algebra.
Provides declaration of Curve abstract interface.
A closed loop given by a collection of curves.
Definition: gsCurveLoop.h:36
Provides declaration of the NurbsCreator struct.
T z() const
Definition: gsVertex.h:112
gsVertex class that represents a 3D vertex for a gsMesh.
Definition: gsVertex.h:26
std::ostream & print(std::ostream &os) const
Prints the object as a string.
Definition: gsPlanarDomain.hpp:151
Provides functions for finding the preimage of a curve via a map.