void Mesh::Clip(const Plane & plane, SArray< Vec3<double> > & positivePart, SArray< Vec3<double> > & negativePart) const { const size_t nV = GetNPoints(); if (nV == 0) { return; } double d; for (size_t v = 0; v < nV; v++) { const Vec3<double> & pt = GetPoint(v); d = plane.m_a * pt[0] + plane.m_b * pt[1] + plane.m_c * pt[2] + plane.m_d; if (d > 0.0) { positivePart.PushBack(pt); } else if (d < 0.0) { negativePart.PushBack(pt); } else { positivePart.PushBack(pt); negativePart.PushBack(pt); } } }
bool PolyLine2::PtIn( const Vec2& pt ) const { int nP = GetNPoints(); if (nP < 3) return false; int nW = 0; // loop through all edges of the polygon for (int i = 0; i < nP; i++) { const Vec2& a = m_Points[i]; const Vec2& b = GetPoint( i + 1 ); if (a.y <= pt.y) { if (b.y > pt.y) { if (pt.leftof( a, b ) > 0.0f) { nW++; } } } else { if (b.y <= pt.y) { if (pt.leftof( a, b ) < 0.0f) { nW--; } } } } return (nW != 0); }
double Mesh::ComputeVolume() const { const size_t nV = GetNPoints(); const size_t nT = GetNTriangles(); if (nV == 0 || nT == 0) { return 0.0; } Vec3<double> bary(0.0, 0.0, 0.0); for (size_t v = 0; v < nV; v++) { bary += GetPoint(v); } bary /= static_cast<double>(nV); Vec3<double> ver0, ver1, ver2; double totalVolume = 0.0; for(size_t t = 0; t < nT; t++) { const Vec3<int> & tri = GetTriangle(t); ver0 = GetPoint(tri[0]); ver1 = GetPoint(tri[1]); ver2 = GetPoint(tri[2]); totalVolume += ComputeVolume4(ver0, ver1, ver2, bary); } return totalVolume/6.0; }
Vec2 PolyLine2::GetCenter() const { int nP = GetNPoints(); Vec2 res( 0.0f, 0.0f ); for (int i = 0; i < nP; i++) { res += GetPoint( i ); } res /= float( nP ); return res; }
bool PolyLine2::AddPoint( const Vec2& pt, bool bNoSelfCross ) { int nP = GetNPoints(); if (bNoSelfCross && nP > 0) { int nSeg = GetNSegments() - 2; Seg2 newSeg( pt, GetPoint( nP - 1 ) ); for (int i = 0; i < nSeg; i++) { if (newSeg.intersects( GetEdge( i ) )) return false; } } m_Points.push_back( pt ); return true; }
Frame PolyLine2::GetBound() const { int nP = GetNPoints(); if (nP == 0) return Frame::null; const Vec2& p0 = GetPoint( 0 ); Frame rect( p0.x, p0.y, p0.x, p0.y ); for (int i = 1; i < nP; i++) { const Vec2& p = GetPoint( i ); if (p.x < rect.x) rect.x = p.x; if (p.y < rect.y) rect.y = p.y; if (p.x > rect.w) rect.w = p.x; if (p.y > rect.h) rect.h = p.y; } rect.w -= rect.x; rect.h -= rect.y; return rect; }
double Mesh::ComputeDiagBB() { const size_t nPoints = GetNPoints(); if (nPoints == 0) return 0.0; Vec3< double > minBB = m_points[0]; Vec3< double > maxBB = m_points[0]; double x, y, z; for (size_t v = 1; v < nPoints; v++) { x = m_points[v][0]; y = m_points[v][1]; z = m_points[v][2]; if (x < minBB[0]) minBB[0] = x; else if (x > maxBB[0]) maxBB[0] = x; if (y < minBB[1]) minBB[1] = y; else if (y > maxBB[1]) maxBB[1] = y; if (z < minBB[2]) minBB[2] = z; else if (z > maxBB[2]) maxBB[2] = z; } return (m_diag = (maxBB - minBB).GetNorm()); }
bool Mesh::IsInside(const Vec3<double> & pt) const { const size_t nV = GetNPoints(); const size_t nT = GetNTriangles(); if (nV == 0 || nT == 0) { return false; } Vec3<double> ver0, ver1, ver2; double volume; for (size_t t = 0; t < nT; t++) { const Vec3<int> & tri = GetTriangle(t); ver0 = GetPoint(tri[0]); ver1 = GetPoint(tri[1]); ver2 = GetPoint(tri[2]); volume = ComputeVolume4(ver0, ver1, ver2, pt); if (volume < 0.0) { return false; } } return true; }
void PolyLine2::InsertPoint( int pos, const Vec2& pt ) { if (pos < 0) pos = 0; if (pos > GetNPoints()) pos = GetNPoints(); m_Points.insert( m_Points.begin() + pos, pt ); }