1
0
mirror of https://git.dev.opencascade.org/repos/occt.git synced 2025-08-09 13:22:24 +03:00

Compare commits

...

4 Commits

Author SHA1 Message Date
kgv
1bb4f7a819 0032285: Coding Rules - get rid of generic methods in GCPnts_TangentialDeflection 2021-04-06 16:02:25 +03:00
kgv
12a38ea066 0032260: Draw Harness, IVtkDraw - add command ivtkwritevtp dumping actor into VTP file 2021-04-01 10:43:09 +03:00
kgv
a8690dc621 0025845: VIS - Surface normals to be associated with polygonal source
IVtk_IShapeData::InsertCoordinate() has been replaced by IVtk_IShapeData::InsertPoint()
defining vertex position with surface normal.
IVtkVTK_ShapeData now allocates normals array within vtkPolyData.
IVtkOCC_ShapeMesher now fills in vertex positions with surfcae normals.
IVtkTools_SubPolyDataFilter has been corrected to optionally copy normals.

ivtksetboundingdraw command has been merged into "ivtksetdispmode -faceBoundaryDraw".
2021-04-01 10:43:06 +03:00
kgv
9e572b462b 0032247: VIS, IVtkOCC_ShapeMesher - allow disabling auto-triangulation behavior
IVtkOCC_Shape now stores Prs3d_Drawer object used by IVtkOCC_ShapeMesher and IVtkOCC_SelectableObject.
IVtkOCC_ShapeMesher::internalBuild() made more consistent to AIS_Shape::Compute() in cleaning/triangulating shape.

Added command ivtkdefaults similar to vdefaults managing triangulation default parameters.
2021-03-30 09:49:25 +03:00
33 changed files with 2014 additions and 1634 deletions

View File

@@ -10,7 +10,6 @@ GCPnts_QuasiUniformDeflection.cxx
GCPnts_QuasiUniformDeflection.pxx
GCPnts_QuasiUniformDeflection.hxx
GCPnts_TangentialDeflection.cxx
GCPnts_TangentialDeflection.pxx
GCPnts_TangentialDeflection.hxx
GCPnts_UniformAbscissa.cxx
GCPnts_UniformAbscissa.pxx

File diff suppressed because it is too large Load Diff

View File

@@ -26,16 +26,13 @@
#include <Adaptor3d_Curve.hxx>
#include <Adaptor2d_Curve2d.hxx>
class Standard_ConstructionError;
class Standard_OutOfRange;
//! Computes a set of points on a curve from package
//! Adaptor3d such as between two successive points
//! P1(u1)and P2(u2) :
//!
//! @code
//! . ||P1P3^P3P2||/||P1P3||*||P3P2||<AngularDeflection
//! . ||P1P2^P1P3||/||P1P2||<CurvatureDeflection
//!
//! @endcode
//! where P3 is the point of abscissa ((u1+u2)/2), with
//! u1 the abscissa of the point P1 and u2 the abscissa
//! of the point P2.
@@ -47,107 +44,204 @@ class Standard_OutOfRange;
//! and CurvatureDeflection > gp::Resolution() must be
//! satisfied at the construction time.
//!
//! A minimum number of points can be fixed for a
//! linear or circular element.
//! A minimum number of points can be fixed for a linear or circular element.
//! Example:
//! Handle(Geom_BezierCurve) C = new Geom_BezierCurve (Poles);
//! GeomAdaptor_Curve Curve (C);
//! Real CDeflect = 0.01; //Curvature deflection
//! Real ADeflect = 0.09; //Angular deflection
//! @code
//! Handle(Geom_BezierCurve) aCurve = new Geom_BezierCurve (thePoles);
//! GeomAdaptor_Curve aCurveAdaptor (aCurve);
//! double aCDeflect = 0.01; // Curvature deflection
//! double anADeflect = 0.09; // Angular deflection
//!
//! GCPnts_TangentialDeflection PointsOnCurve;
//! PointsOnCurve.Initialize (Curve, ADeflect, CDeflect);
//!
//! Real U;
//! gp_Pnt P;
//! for (Integer i=1; i<=PointsOnCurve.NbPoints();i++) {
//! U = PointsOnCurve.Parameter (i);
//! P = PointsOnCurve.Value (i);
//! GCPnts_TangentialDeflection aPointsOnCurve;
//! aPointsOnCurve.Initialize (aCurveAdaptor, anADeflect, aCDeflect);
//! for (int i = 1; i <= aPointsOnCurve.NbPoints(); ++i)
//! {
//! double aU = aPointsOnCurve.Parameter (i);
//! gp_Pnt aPnt = aPointsOnCurve.Value (i);
//! }
//! @endcode
class GCPnts_TangentialDeflection
{
public:
//
DEFINE_STANDARD_ALLOC
//! Empty constructor.
//! @sa Initialize()
Standard_EXPORT GCPnts_TangentialDeflection();
Standard_EXPORT GCPnts_TangentialDeflection(const Adaptor3d_Curve& C, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT GCPnts_TangentialDeflection(const Adaptor3d_Curve& C, const Standard_Real FirstParameter, const Standard_Real LastParameter, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT GCPnts_TangentialDeflection(const Adaptor2d_Curve2d& C, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT GCPnts_TangentialDeflection(const Adaptor2d_Curve2d& C, const Standard_Real FirstParameter, const Standard_Real LastParameter, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT void Initialize (const Adaptor3d_Curve& C, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT void Initialize (const Adaptor3d_Curve& C, const Standard_Real FirstParameter, const Standard_Real LastParameter, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT void Initialize (const Adaptor2d_Curve2d& C, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
Standard_EXPORT void Initialize (const Adaptor2d_Curve2d& C, const Standard_Real FirstParameter, const Standard_Real LastParameter, const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection, const Standard_Integer MinimumOfPoints = 2, const Standard_Real UTol = 1.0e-9, const Standard_Real theMinLen = 1.0e-7);
//! Constructor for 3D curve.
//! @param theC [in] 3d curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT GCPnts_TangentialDeflection (const Adaptor3d_Curve& theC,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Constructor for 3D curve with restricted range.
//! @param theC [in] 3d curve
//! @param theFirstParameter [in] first parameter on curve
//! @param theLastParameter [in] last parameter on curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTo l [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT GCPnts_TangentialDeflection (const Adaptor3d_Curve& theC, const Standard_Real theFirstParameter, const Standard_Real theLastParameter,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Constructor for 2D curve.
//! @param theC [in] 2d curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT GCPnts_TangentialDeflection (const Adaptor2d_Curve2d& theC,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Constructor for 2D curve with restricted range.
//! @param theC [in] 2d curve
//! @param theFirstParameter [in] first parameter on curve
//! @param theLastParameter [in] last parameter on curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT GCPnts_TangentialDeflection (const Adaptor2d_Curve2d& theC, const Standard_Real theFirstParameter, const Standard_Real theLastParameter,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Initialize algorithm for 3D curve.
//! @param theC [in] 3d curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT void Initialize (const Adaptor3d_Curve& theC,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Initialize algorithm for 3D curve with restricted range.
//! @param theC [in] 3d curve
//! @param theFirstParameter [in] first parameter on curve
//! @param theLastParameter [in] last parameter on curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT void Initialize (const Adaptor3d_Curve& theC, const Standard_Real theFirstParameter, const Standard_Real theLastParameter,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Initialize algorithm for 2D curve.
//! @param theC [in] 2d curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT void Initialize (const Adaptor2d_Curve2d& theC,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Initialize algorithm for 2D curve with restricted range.
//! @param theC [in] 2d curve
//! @param theFirstParameter [in] first parameter on curve
//! @param theLastParameter [in] last parameter on curve
//! @param theAngularDeflection [in] angular deflection in radians
//! @param theCurvatureDeflection [in] linear deflection
//! @param theMinimumOfPoints [in] minimum number of points
//! @param theUTol [in] tolerance in curve parametric scope
//! @param theMinLen [in] minimal length
Standard_EXPORT void Initialize (const Adaptor2d_Curve2d& theC, const Standard_Real theFirstParameter, const Standard_Real theLastParameter,
const Standard_Real theAngularDeflection, const Standard_Real theCurvatureDeflection,
const Standard_Integer theMinimumOfPoints = 2,
const Standard_Real theUTol = 1.0e-9,
const Standard_Real theMinLen = 1.0e-7);
//! Add point to already calculated points (or replace existing)
//! Returns index of new added point
//! or founded with parametric tolerance (replaced if theIsReplace is true)
Standard_EXPORT Standard_Integer AddPoint (const gp_Pnt& thePnt, const Standard_Real theParam, const Standard_Boolean theIsReplace = Standard_True);
Standard_Integer NbPoints () const
{
return parameters.Length ();
return myParameters.Length ();
}
Standard_Real Parameter (const Standard_Integer I) const
{
return parameters.Value (I);
return myParameters.Value (I);
}
gp_Pnt Value (const Standard_Integer I) const
{
return points.Value (I);
return myPoints.Value (I);
}
//! Computes angular step for the arc using the given parameters.
Standard_EXPORT static Standard_Real ArcAngularStep (const Standard_Real theRadius, const Standard_Real theLinearDeflection, const Standard_Real theAngularDeflection, const Standard_Real theMinLength);
private:
Standard_EXPORT void PerformLinear (const Adaptor3d_Curve& C);
Standard_EXPORT void PerformLinear (const Adaptor2d_Curve2d& C);
Standard_EXPORT void PerformCircular (const Adaptor3d_Curve& C);
Standard_EXPORT void PerformCircular (const Adaptor2d_Curve2d& C);
Standard_EXPORT void PerformCurve (const Adaptor3d_Curve& C);
Standard_EXPORT void PerformCurve (const Adaptor2d_Curve2d& C);
Standard_EXPORT void EvaluateDu (const Adaptor3d_Curve& C, const Standard_Real U, gp_Pnt& P, Standard_Real& Du, Standard_Boolean& NotDone) const;
Standard_EXPORT void EvaluateDu (const Adaptor2d_Curve2d& C, const Standard_Real U, gp_Pnt& P, Standard_Real& Du, Standard_Boolean& NotDone) const;
Standard_EXPORT void EstimDefl (const Adaptor3d_Curve& C, const Standard_Real U1, const Standard_Real U2,
Standard_Real& MaxDefl, Standard_Real& UMax);
Standard_EXPORT void EstimDefl (const Adaptor2d_Curve2d& C, const Standard_Real U1, const Standard_Real U2,
Standard_Real& MaxDefl, Standard_Real& UMax);
template<class TheCurve>
void initialize (const TheCurve& C, const Standard_Real FirstParameter, const Standard_Real LastParameter,
const Standard_Real AngularDeflection, const Standard_Real CurvatureDeflection,
const Standard_Integer MinimumOfPoints,
const Standard_Real UTol,
const Standard_Real theMinLen);
template<class TheCurve>
void PerformLinear (const TheCurve& theC);
template<class TheCurve>
void PerformCircular (const TheCurve& theC);
//! On respecte ll'angle et la fleche, on peut imposer un nombre minimum de points sur un element lineaire.
template<class TheCurve>
void PerformCurve (const TheCurve& C);
template<class TheCurve>
void EvaluateDu (const TheCurve& C, const Standard_Real U, gp_Pnt& P, Standard_Real& Du, Standard_Boolean& NotDone) const;
//! Estimation of maximal deflection for interval [U1, U2]
template<class TheCurve>
void EstimDefl (const TheCurve& C, const Standard_Real U1, const Standard_Real U2,
Standard_Real& MaxDefl, Standard_Real& UMax);
private:
Standard_Real angularDeflection;
Standard_Real curvatureDeflection;
Standard_Real uTol;
Standard_Integer minNbPnts;
Standard_Real myAngularDeflection;
Standard_Real myCurvatureDeflection;
Standard_Real myUTol;
Standard_Integer myMinNbPnts;
Standard_Real myMinLen;
Standard_Real lastu;
Standard_Real firstu;
TColgp_SequenceOfPnt points;
TColStd_SequenceOfReal parameters;
Standard_Real myLastU;
Standard_Real myFirstu;
TColgp_SequenceOfPnt myPoints;
TColStd_SequenceOfReal myParameters;
};
#endif // _GCPnts_TangentialDeflection_HeaderFile

View File

@@ -1,687 +0,0 @@
// Created on: 1996-11-08
// Created by: Jean Claude VAUTHIER
// Copyright (c) 1996-1999 Matra Datavision
// Copyright (c) 1999-2014 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <GCPnts_DeflectionType.hxx>
#include <Standard_ConstructionError.hxx>
#include <Precision.hxx>
#include <gp_XYZ.hxx>
#include <gp_Pnt.hxx>
#include <gp_Vec.hxx>
#include <gp.hxx>
#include <NCollection_List.hxx>
#include <math_PSO.hxx>
#include <math_BrentMinimum.hxx>
#define Us3 0.3333333333333333333333333333
void GCPnts_TangentialDeflection::EvaluateDu (
const TheCurve& C,
const Standard_Real U,
gp_Pnt& P,
Standard_Real& Du,
Standard_Boolean& NotDone) const {
gp_Vec T, N;
D2 (C, U, P, T, N);
Standard_Real Lt = T.Magnitude ();
Standard_Real LTol = Precision::Confusion ();
if (Lt > LTol && N.Magnitude () > LTol) {
Standard_Real Lc = N.CrossMagnitude (T);
Standard_Real Ln = Lc/Lt;
if (Ln > LTol) {
Du = sqrt (8.0 * Max(curvatureDeflection, myMinLen) / Ln);
NotDone = Standard_False;
}
}
}
//=======================================================================
//function : GCPnts_TangentialDeflection
//purpose :
//=======================================================================
GCPnts_TangentialDeflection::GCPnts_TangentialDeflection (
const TheCurve& C,
const Standard_Real AngularDeflection,
const Standard_Real CurvatureDeflection,
const Standard_Integer MinimumOfPoints,
const Standard_Real UTol,
const Standard_Real theMinLen)
{
Initialize (C,AngularDeflection,CurvatureDeflection,MinimumOfPoints,UTol,theMinLen);
}
//=======================================================================
//function : GCPnts_TangentialDeflection
//purpose :
//=======================================================================
GCPnts_TangentialDeflection::GCPnts_TangentialDeflection (
const TheCurve& C,
const Standard_Real FirstParameter,
const Standard_Real LastParameter,
const Standard_Real AngularDeflection,
const Standard_Real CurvatureDeflection,
const Standard_Integer MinimumOfPoints,
const Standard_Real UTol,
const Standard_Real theMinLen)
{
Initialize (C,
FirstParameter,
LastParameter,
AngularDeflection,
CurvatureDeflection,
MinimumOfPoints,
UTol, theMinLen);
}
//=======================================================================
//function : Initialize
//purpose :
//=======================================================================
void GCPnts_TangentialDeflection::Initialize (
const TheCurve& C,
const Standard_Real AngularDeflection,
const Standard_Real CurvatureDeflection,
const Standard_Integer MinimumOfPoints,
const Standard_Real UTol,
const Standard_Real theMinLen)
{
Initialize (C,
C.FirstParameter (),
C.LastParameter (),
AngularDeflection,
CurvatureDeflection,
MinimumOfPoints,
UTol, theMinLen);
}
//=======================================================================
//function : Initialize
//purpose :
//=======================================================================
void GCPnts_TangentialDeflection::Initialize (
const TheCurve& C,
const Standard_Real FirstParameter,
const Standard_Real LastParameter,
const Standard_Real AngularDeflection,
const Standard_Real CurvatureDeflection,
const Standard_Integer MinimumOfPoints,
const Standard_Real UTol,
const Standard_Real theMinLen)
{
Standard_ConstructionError_Raise_if (CurvatureDeflection < Precision::Confusion () ||
AngularDeflection < Precision::Angular (),
"GCPnts_TangentialDeflection::Initialize - Zero Deflection")
parameters.Clear ();
points .Clear ();
if (FirstParameter < LastParameter) {
firstu = FirstParameter;
lastu = LastParameter;
}
else {
lastu = FirstParameter;
firstu = LastParameter;
}
uTol = UTol;
angularDeflection = AngularDeflection;
curvatureDeflection = CurvatureDeflection;
minNbPnts = Max (MinimumOfPoints, 2);
myMinLen = Max(theMinLen, Precision::Confusion());
switch (C.GetType()) {
case GeomAbs_Line:
PerformLinear (C);
break;
case GeomAbs_Circle:
PerformCircular (C);
break;
case GeomAbs_BSplineCurve:
{
Handle_TheBSplineCurve BS = C.BSpline() ;
if (BS->NbPoles() == 2 ) PerformLinear (C);
else PerformCurve (C);
break;
}
case GeomAbs_BezierCurve:
{
Handle_TheBezierCurve BZ = C.Bezier();
if (BZ->NbPoles() == 2) PerformLinear (C);
else PerformCurve (C);
break;
}
default: PerformCurve (C);
}
}
//=======================================================================
//function : PerformLinear
//purpose :
//=======================================================================
void GCPnts_TangentialDeflection::PerformLinear (const TheCurve& C) {
gp_Pnt P;
D0 (C, firstu, P);
parameters.Append (firstu);
points .Append (P);
if (minNbPnts > 2)
{
Standard_Real Du = (lastu - firstu) / minNbPnts;
Standard_Real U = firstu + Du;
for (Standard_Integer i = 2; i < minNbPnts; i++)
{
D0 (C, U, P);
parameters.Append (U);
points .Append (P);
U += Du;
}
}
D0 (C, lastu, P);
parameters.Append (lastu);
points .Append (P);
}
//=======================================================================
//function : PerformCircular
//purpose :
//=======================================================================
void GCPnts_TangentialDeflection::PerformCircular (const TheCurve& C)
{
// akm 8/01/02 : check the radius before divide by it
Standard_Real dfR = C.Circle().Radius();
Standard_Real Du = GCPnts_TangentialDeflection::ArcAngularStep(
dfR, curvatureDeflection, angularDeflection, myMinLen);
const Standard_Real aDiff = lastu - firstu;
// Round up number of points to satisfy curvatureDeflection more precisely
Standard_Integer NbPoints = (Standard_Integer)Min(Ceiling(aDiff / Du), 1.0e+6);
NbPoints = Max(NbPoints, minNbPnts - 1);
Du = aDiff / NbPoints;
gp_Pnt P;
Standard_Real U = firstu;
for (Standard_Integer i = 1; i <= NbPoints; i++)
{
D0 (C, U, P);
parameters.Append (U);
points .Append (P);
U += Du;
}
D0 (C, lastu, P);
parameters.Append (lastu);
points .Append (P);
}
//=======================================================================
//function : PerformCurve
//purpose : On respecte ll'angle et la fleche, on peut imposer un nombre
// minimum de points sur un element lineaire
//=======================================================================
void GCPnts_TangentialDeflection::PerformCurve (const TheCurve& C)
{
Standard_Integer i, j;
gp_XYZ V1, V2;
gp_Pnt MiddlePoint, CurrentPoint, LastPoint;
Standard_Real Du, Dusave, MiddleU, L1, L2;
Standard_Real U1 = firstu;
Standard_Real LTol = Precision::Confusion (); //protection longueur nulle
Standard_Real ATol = 1.e-2 * angularDeflection;
if(ATol > 1.e-2)
ATol = 1.e-2;
else if(ATol < 1.e-7)
ATol = 1.e-7;
D0 (C, lastu, LastPoint);
//Initialization du calcul
Standard_Boolean NotDone = Standard_True;
Dusave = (lastu - firstu)*Us3;
Du = Dusave;
EvaluateDu (C, U1, CurrentPoint, Du, NotDone);
parameters.Append (U1);
points .Append (CurrentPoint);
// Used to detect "isLine" current bspline and in Du computation in general handling.
Standard_Integer NbInterv = C.NbIntervals(GeomAbs_CN);
TColStd_Array1OfReal Intervs(1, NbInterv+1);
C.Intervals(Intervs, GeomAbs_CN);
if (NotDone || Du > 5. * Dusave) {
//C'est soit une droite, soit une singularite :
V1 = (LastPoint.XYZ() - CurrentPoint.XYZ());
L1 = V1.Modulus ();
if (L1 > LTol)
{
//Si c'est une droite on verifie en calculant minNbPoints :
Standard_Boolean IsLine = Standard_True;
Standard_Integer NbPoints = (minNbPnts > 3) ? minNbPnts : 3;
switch (C.GetType()) {
case GeomAbs_BSplineCurve:
{
Handle_TheBSplineCurve BS = C.BSpline() ;
NbPoints = Max(BS->Degree() + 1, NbPoints);
break;
}
case GeomAbs_BezierCurve:
{
Handle_TheBezierCurve BZ = C.Bezier();
NbPoints = Max(BZ->Degree() + 1, NbPoints);
break;
}
default:
;}
////
Standard_Real param = 0.;
for (i = 1; i <= NbInterv && IsLine; ++i)
{
// Avoid usage intervals out of [firstu, lastu].
if ((Intervs(i+1) < firstu) ||
(Intervs(i) > lastu))
{
continue;
}
// Fix border points in applicable intervals, to avoid be out of target interval.
if ((Intervs(i) < firstu) &&
(Intervs(i+1) > firstu))
{
Intervs(i) = firstu;
}
if ((Intervs(i) < lastu) &&
(Intervs(i+1) > lastu))
{
Intervs(i + 1) = lastu;
}
Standard_Real delta = (Intervs(i+1) - Intervs(i))/NbPoints;
for (j = 1; j <= NbPoints && IsLine; ++j)
{
param = Intervs(i) + j*delta;
D0 (C, param, MiddlePoint);
V2 = (MiddlePoint.XYZ() - CurrentPoint.XYZ());
L2 = V2.Modulus ();
if (L2 > LTol)
{
const Standard_Real aAngle = V2.CrossMagnitude(V1)/(L1*L2);
IsLine = (aAngle < ATol);
}
}
}
if (IsLine)
{
parameters.Clear();
points .Clear();
PerformLinear(C);
return;
}
else
{
//c'etait une singularite on continue :
//Du = Dusave;
EvaluateDu (C, param, MiddlePoint, Du, NotDone);
}
}
else
{
Du = (lastu-firstu)/2.1;
MiddleU = firstu + Du;
D0 (C, MiddleU, MiddlePoint);
V1 = (MiddlePoint.XYZ() - CurrentPoint.XYZ());
L1 = V1.Modulus ();
if (L1 < LTol)
{
// L1 < LTol C'est une courbe de longueur nulle, calcul termine :
// on renvoi un segment de 2 points (protection)
parameters.Append (lastu);
points .Append (LastPoint);
return;
}
}
}
if (Du > Dusave) Du = Dusave;
else Dusave = Du;
if (Du < uTol) {
Du = lastu - firstu;
if (Du < uTol) {
parameters.Append (lastu);
points .Append (LastPoint);
return;
}
}
//Traitement normal pour une courbe
Standard_Boolean MorePoints = Standard_True;
Standard_Real U2 = firstu;
Standard_Real AngleMax = angularDeflection * 0.5; //car on prend le point milieu
Standard_Integer aIdx[2] = {Intervs.Lower(), Intervs.Lower()}; // Indexes of intervals of U1 and U2, used to handle non-uniform case.
Standard_Boolean isNeedToCheck = Standard_False;
gp_Pnt aPrevPoint = points.Last();
while (MorePoints) {
aIdx[0] = getIntervalIdx(U1, Intervs, aIdx[0]);
U2 += Du;
if (U2 >= lastu) { //Bout de courbe
U2 = lastu;
CurrentPoint = LastPoint;
Du = U2-U1;
Dusave = Du;
}
else D0 (C, U2, CurrentPoint); //Point suivant
Standard_Real Coef = 0.0, ACoef = 0., FCoef = 0.;
Standard_Boolean Correction, TooLarge, TooSmall;
TooLarge = Standard_False;
Correction = Standard_True;
TooSmall = Standard_False;
while (Correction) { //Ajustement Du
if (isNeedToCheck)
{
aIdx[1] = getIntervalIdx(U2, Intervs, aIdx[0]);
if (aIdx[1] > aIdx[0]) // Jump to another polynom.
{
if (Du > (Intervs(aIdx[0] + 1) - Intervs(aIdx[0]) ) * Us3) // Set Du to the smallest value and check deflection on it.
{
Du = (Intervs(aIdx[0] + 1) - Intervs(aIdx[0]) ) * Us3;
U2 = U1 + Du;
if (U2 > lastu)
U2 = lastu;
D0 (C, U2, CurrentPoint);
}
}
}
MiddleU = (U1+U2)*0.5; //Verif / au point milieu
D0 (C, MiddleU, MiddlePoint);
V1 = (CurrentPoint.XYZ() - aPrevPoint.XYZ()); //Critere de fleche
V2 = (MiddlePoint.XYZ() - aPrevPoint.XYZ());
L1 = V1.Modulus ();
FCoef = (L1 > myMinLen) ?
V1.CrossMagnitude(V2)/(L1*curvatureDeflection) : 0.0;
V1 = (CurrentPoint.XYZ() - MiddlePoint.XYZ()); //Critere d'angle
L1 = V1.Modulus ();
L2 = V2.Modulus ();
if (L1 > myMinLen && L2 > myMinLen)
{
Standard_Real angg = V1.CrossMagnitude(V2) / (L1 * L2);
ACoef = angg / AngleMax;
}
else
ACoef = 0.0;
//On retient le plus penalisant
Coef = Max(ACoef, FCoef);
if (isNeedToCheck && Coef < 0.55)
{
isNeedToCheck = Standard_False;
Du = Dusave;
U2 = U1 + Du;
if (U2 > lastu)
U2 = lastu;
D0 (C, U2, CurrentPoint);
continue;
}
if (Coef <= 1.0) {
if (Abs (lastu-U2) < uTol) {
parameters.Append (lastu);
points .Append (LastPoint);
MorePoints = Standard_False;
Correction = Standard_False;
}
else {
if (Coef >= 0.55 || TooLarge) {
parameters.Append (U2);
points .Append (CurrentPoint);
aPrevPoint = CurrentPoint;
Correction = Standard_False;
isNeedToCheck = Standard_True;
}
else if (TooSmall) {
Correction = Standard_False;
aPrevPoint = CurrentPoint;
}
else {
TooSmall = Standard_True;
//Standard_Real UUU2 = U2;
Du += Min((U2-U1)*(1.-Coef), Du*Us3);
U2 = U1 + Du;
if (U2 > lastu)
U2 = lastu;
D0 (C, U2, CurrentPoint);
}
}
}
else {
if (Coef >= 1.5) {
if (!aPrevPoint.IsEqual(points.Last(), Precision::Confusion()))
{
parameters.Append (U1);
points .Append (aPrevPoint);
}
U2 = MiddleU;
Du = U2-U1;
CurrentPoint = MiddlePoint;
}
else {
Du*=0.9;
U2 = U1 + Du;
D0 (C, U2, CurrentPoint);
TooLarge = Standard_True;
}
}
}
Du = U2-U1;
if (MorePoints) {
if (U1 > firstu) {
if (FCoef > ACoef) {
//La fleche est critere de decoupage
EvaluateDu (C, U2, CurrentPoint, Du, NotDone);
if (NotDone) {
Du += (Du-Dusave)*(Du/Dusave);
if (Du > 1.5 * Dusave) Du = 1.5 * Dusave;
if (Du < 0.75* Dusave) Du = 0.75 * Dusave;
}
}
else {
//L'angle est le critere de decoupage
Du += (Du-Dusave)*(Du/Dusave);
if (Du > 1.5 * Dusave) Du = 1.5 * Dusave;
if (Du < 0.75* Dusave) Du = 0.75 * Dusave;
}
}
if (Du < uTol) {
Du = lastu - U2;
if (Du < uTol) {
parameters.Append (lastu);
points .Append (LastPoint);
MorePoints = Standard_False;
}
else if (Du*Us3 > uTol) Du*=Us3;
}
U1 = U2;
Dusave = Du;
}
}
//Recalage avant dernier point :
i = points.Length()-1;
// Real d = points (i).Distance (points (i+1));
// if (Abs(parameters (i) - parameters (i+1))<= 0.000001 || d < Precision::Confusion()) {
// cout<<"deux points confondus"<<endl;
// parameters.Remove (i+1);
// points.Remove (i+1);
// i--;
// }
if (i >= 2) {
MiddleU = parameters (i-1);
MiddleU = (lastu + MiddleU)*0.5;
D0 (C, MiddleU, MiddlePoint);
parameters.SetValue (i, MiddleU);
points .SetValue (i, MiddlePoint);
}
//-- On rajoute des points aux milieux des segments si le nombre
//-- mini de points n'est pas atteint
//--
Standard_Integer Nbp = points.Length();
//std::cout << "GCPnts_TangentialDeflection: Number of Points (" << Nbp << " " << minNbPnts << " )" << std::endl;
while(Nbp < minNbPnts)
{
for (i = 2; i <= Nbp; i += 2)
{
MiddleU = (parameters.Value(i-1)+parameters.Value(i))*0.5;
D0 (C, MiddleU, MiddlePoint);
parameters.InsertBefore(i,MiddleU);
points.InsertBefore(i,MiddlePoint);
Nbp++;
}
}
//Additional check for intervals
Standard_Real MinLen2 = myMinLen * myMinLen;
Standard_Integer MaxNbp = 10 * Nbp;
for(i = 1; i < Nbp; ++i)
{
U1 = parameters(i);
U2 = parameters(i + 1);
if (U2 - U1 <= uTol)
{
continue;
}
// Check maximal deflection on interval;
Standard_Real dmax = 0.;
Standard_Real umax = 0.;
Standard_Real amax = 0.;
EstimDefl(C, U1, U2, dmax, umax);
const gp_Pnt& P1 = points(i);
const gp_Pnt& P2 = points(i+1);
D0(C, umax, MiddlePoint);
amax = EstimAngl(P1, MiddlePoint, P2);
if(dmax > curvatureDeflection || amax > AngleMax)
{
if(umax - U1 > uTol && U2 - umax > uTol)
{
if (P1.SquareDistance(MiddlePoint) > MinLen2 && P2.SquareDistance(MiddlePoint) > MinLen2)
{
parameters.InsertAfter(i, umax);
points.InsertAfter(i, MiddlePoint);
++Nbp;
--i; //To compensate ++i in loop header: i must point to first part of split interval
if(Nbp > MaxNbp)
{
break;
}
}
}
}
}
//
}
//=======================================================================
//function : EstimDefl
//purpose : Estimation of maximal deflection for interval [U1, U2]
//
//=======================================================================
void GCPnts_TangentialDeflection::EstimDefl (const TheCurve& C,
const Standard_Real U1, const Standard_Real U2,
Standard_Real& MaxDefl, Standard_Real& UMax)
{
Standard_Real Du = (lastu - firstu);
//
TheMaxCurvLinDist aFunc(C, U1, U2);
//
const Standard_Integer aNbIter = 100;
Standard_Real reltol = Max(1.e-3, 2.*uTol/((Abs(U1) + Abs(U2))));
//
math_BrentMinimum anOptLoc(reltol, aNbIter, uTol);
anOptLoc.Perform(aFunc, U1, (U1+U2)/2., U2);
if(anOptLoc.IsDone())
{
MaxDefl = Sqrt(-anOptLoc.Minimum());
UMax = anOptLoc.Location();
return;
}
//
math_Vector aLowBorder(1,1);
math_Vector aUppBorder(1,1);
math_Vector aSteps(1,1);
//
aSteps(1) = Max(0.1 * Du, 100. * uTol);
Standard_Integer aNbParticles = Max(8, RealToInt(32 * (U2 - U1) / Du));
//
aLowBorder(1) = U1;
aUppBorder(1) = U2;
//
//
Standard_Real aValue;
math_Vector aT(1,1);
TheMaxCurvLinDistMV aFuncMV(aFunc);
math_PSO aFinder(&aFuncMV, aLowBorder, aUppBorder, aSteps, aNbParticles);
aFinder.Perform(aSteps, aValue, aT);
//
anOptLoc.Perform(aFunc, Max(aT(1) - aSteps(1), U1) , aT(1), Min(aT(1) + aSteps(1),U2));
if(anOptLoc.IsDone())
{
MaxDefl = Sqrt(-anOptLoc.Minimum());
UMax = anOptLoc.Location();
return;
}
MaxDefl = Sqrt(-aValue);
UMax = aT(1);
//
}

View File

@@ -16,10 +16,11 @@
#ifndef __IVTK_ISHAPEDATA_H__
#define __IVTK_ISHAPEDATA_H__
#include <gp_Pnt.hxx>
#include <IVtk_Interface.hxx>
#include <IVtk_Types.hxx>
#include <NCollection_Vec3.hxx>
class IVtk_IShapeData;
DEFINE_STANDARD_HANDLE( IVtk_IShapeData, IVtk_Interface )
//! @class IVtk_IShapeData
@@ -34,11 +35,11 @@ public:
DEFINE_STANDARD_RTTIEXT(IVtk_IShapeData,IVtk_Interface)
//! Insert a coordinate
//! @param [in] theX X coordinate
//! @param [in] theY Y coordinate
//! @param [in] theZ Z coordinate
//! @param [in] thePnt point position
//! @param [in] theNorm point normal
//! @return id of added point
virtual IVtk_PointId InsertCoordinate (double theX, double theY, double theZ) = 0;
virtual IVtk_PointId InsertPoint (const gp_Pnt& thePnt,
const NCollection_Vec3<float>& theNorm) = 0;
//! Insert a vertex.
//! @param [in] theShapeID id of the sub-shape to which the vertex belongs.
@@ -77,6 +78,27 @@ public:
const IVtk_PointId thePointId2,
const IVtk_PointId thePointId3,
const IVtk_MeshType theMeshType = MT_Undefined) = 0;
public:
//! Insert a coordinate
//! @param [in] theX X coordinate
//! @param [in] theY Y coordinate
//! @param [in] theZ Z coordinate
//! @return id of added point
virtual IVtk_PointId InsertCoordinate (double theX, double theY, double theZ)
{
return InsertCoordinate (gp_Pnt (theX, theY, theZ));
}
//! Insert a coordinate
//! @param [in] thePnt point position
//! @return id of added point
IVtk_PointId InsertCoordinate (const gp_Pnt& thePnt)
{
return InsertPoint (thePnt, NCollection_Vec3<float>(0.0f, 0.0f, 1.0f));
}
};
#endif // __IVTK_ISHAPEDATA_H__

View File

@@ -17,10 +17,10 @@
IMPLEMENT_STANDARD_RTTIEXT(IVtk_IShapeMesher,IVtk_Interface)
// Handle implementation
//! Executes the mesh generation algorithms. To be defined in implementation class.
// ================================================================
// Function : initialize
// Purpose :
// ================================================================
void IVtk_IShapeMesher::initialize (const IVtk_IShape::Handle& theShape,
const IVtk_IShapeData::Handle& theData)
{
@@ -28,9 +28,10 @@ void IVtk_IShapeMesher::initialize (const IVtk_IShape::Handle& theShape,
myShapeData = theData;
}
//! Main entry point for building shape representation
//! @param [in] shape IShape to be meshed
//! @param [in] data IShapeData interface visualization data is passed to.
// ================================================================
// Function : Build
// Purpose :
// ================================================================
void IVtk_IShapeMesher::Build (const IVtk_IShape::Handle& theShape,
const IVtk_IShapeData::Handle& theData)
{

View File

@@ -31,11 +31,15 @@ public:
typedef Handle(IVtk_IShapeMesher) Handle;
virtual ~IVtk_IShapeMesher() { }
//! Main entry point for building shape representation
//! @param [in] shape IShape to be meshed
//! @param [in] data IShapeData interface visualization data is passed to.
Standard_EXPORT void Build (const IVtk_IShape::Handle& theShape, const IVtk_IShapeData::Handle& theData);
DEFINE_STANDARD_RTTIEXT(IVtk_IShapeMesher,IVtk_Interface)
protected:
//! Executes the mesh generation algorithms. To be defined in implementation class.
Standard_EXPORT virtual void initialize (const IVtk_IShape::Handle& theShapeObj,
const IVtk_IShapeData::Handle& theShapeData);
virtual void internalBuild() = 0;

View File

@@ -74,6 +74,7 @@
#include <vtkSmartPointer.h>
#include <vtkTIFFWriter.h>
#include <vtkWindowToImageFilter.h>
#include <vtkXMLPolyDataWriter.h>
#ifndef _WIN32
#include <X11/X.h>
#include <X11/Shell.h>
@@ -91,6 +92,8 @@
#define HAVE_VTK_SRGB
#endif
#pragma comment(lib, "vtkIOXML-8.2.lib") ///
//================================================================
// TYPE DEFINITIONS
//================================================================
@@ -167,6 +170,22 @@ static Handle(PipelinePtr) PipelineByActorName (const TCollection_AsciiString& t
return PipelineByActor (anActor);
}
//! Create global presentation attributes.
static Handle(Prs3d_Drawer) createDefaultDrawer()
{
Handle(Prs3d_Drawer) aGlobalDrawer = new Prs3d_Drawer();
aGlobalDrawer->SetTypeOfDeflection (Aspect_TOD_RELATIVE);
aGlobalDrawer->SetDeviationCoefficient (0.0001);
return aGlobalDrawer;
}
//! Get global presentation attributes (analog of AIS_InteractiveContext::DefaultDrawer()).
static const Handle(Prs3d_Drawer)& GetDefaultDrawer()
{
static Handle(Prs3d_Drawer) aGlobalDrawer = createDefaultDrawer();
return aGlobalDrawer;
}
#ifdef _WIN32
static Handle(WNT_Window)& GetWindow()
@@ -495,12 +514,106 @@ vtkActor* CreateActor (const Standard_Integer theId,
return NULL;
}
Handle(PipelinePtr) aPL = new PipelinePtr (theShape, theId);
Handle(PipelinePtr) aPL = new PipelinePtr (theShape, theId, GetDefaultDrawer());
GetPipelines()->Bind (theId, aPL);
aPL->Actor()->GetProperty()->SetInterpolationToPhong();
return aPL->Actor();
}
//===============================================================================================
//function : VtkDefaults
//purpose :
//===============================================================================================
static int VtkDefaults (Draw_Interpretor& theDi,
Standard_Integer theArgsNb,
const char** theArgVec)
{
const Handle(Prs3d_Drawer)& aDefParams = GetDefaultDrawer();
if (theArgsNb < 2)
{
if (aDefParams->TypeOfDeflection() == Aspect_TOD_RELATIVE)
{
theDi << "DeflType: relative\n"
<< "DeviationCoeff: " << aDefParams->DeviationCoefficient() << "\n";
}
else
{
theDi << "DeflType: absolute\n"
<< "AbsoluteDeflection: " << aDefParams->MaximalChordialDeviation() << "\n";
}
theDi << "AngularDeflection: " << (180.0 * aDefParams->DeviationAngle() / M_PI) << "\n";
theDi << "AutoTriangulation: " << (aDefParams->IsAutoTriangulation() ? "on" : "off") << "\n";
return 0;
}
for (Standard_Integer anArgIter = 1; anArgIter < theArgsNb; ++anArgIter)
{
TCollection_AsciiString anArg (theArgVec[anArgIter]);
anArg.UpperCase();
if (anArg == "-ABSDEFL"
|| anArg == "-ABSOLUTEDEFLECTION"
|| anArg == "-DEFL"
|| anArg == "-DEFLECTION")
{
if (++anArgIter >= theArgsNb)
{
theDi << "Syntax error at " << anArg;
return 1;
}
aDefParams->SetTypeOfDeflection (Aspect_TOD_ABSOLUTE);
aDefParams->SetMaximalChordialDeviation (Draw::Atof (theArgVec[anArgIter]));
}
else if (anArg == "-RELDEFL"
|| anArg == "-RELATIVEDEFLECTION"
|| anArg == "-DEVCOEFF"
|| anArg == "-DEVIATIONCOEFF"
|| anArg == "-DEVIATIONCOEFFICIENT")
{
if (++anArgIter >= theArgsNb)
{
theDi << "Syntax error at " << anArg;
return 1;
}
aDefParams->SetTypeOfDeflection (Aspect_TOD_RELATIVE);
aDefParams->SetDeviationCoefficient (Draw::Atof (theArgVec[anArgIter]));
}
else if (anArg == "-ANGDEFL"
|| anArg == "-ANGULARDEFL"
|| anArg == "-ANGULARDEFLECTION")
{
if (++anArgIter >= theArgsNb)
{
theDi << "Syntax error at " << anArg;
return 1;
}
aDefParams->SetDeviationAngle (M_PI * Draw::Atof (theArgVec[anArgIter]) / 180.0);
}
else if (anArg == "-AUTOTR"
|| anArg == "-AUTOTRIANG"
|| anArg == "-AUTOTRIANGULATION")
{
++anArgIter;
bool toTurnOn = true;
if (anArgIter >= theArgsNb
|| !Draw::ParseOnOff (theArgVec[anArgIter], toTurnOn))
{
theDi << "Syntax error at '" << anArg << "'";
return 1;
}
aDefParams->SetAutoTriangulation (toTurnOn);
}
else
{
theDi << "Syntax error: unknown argument '" << anArg << "'";
return 1;
}
}
return 0;
}
//================================================================
// Function : VtkDisplay
// Purpose :
@@ -719,158 +832,159 @@ static Standard_Integer VtkRemove (Draw_Interpretor& ,
//================================================================
// Function : VtkSetDisplayMode
// Purpose :
// Draw args : ivtksetdispmode [name] mode(0,1)
// Purpose :
//================================================================
static Standard_Integer VtkSetDisplayMode (Draw_Interpretor& ,
static Standard_Integer VtkSetDisplayMode (Draw_Interpretor& theDI,
Standard_Integer theArgNum,
const char** theArgs)
{
if (!GetInteractor()
|| !GetInteractor()->IsEnabled())
{
Message::SendFail() << "Error: call ivtkinit before";
return 1;
}
else if (theArgNum != 2 && theArgNum != 3)
{
Message::SendFail() << "Syntax error: expects 1 or 2 arguments";
theDI << "Error: call ivtkinit before";
return 1;
}
if (theArgNum == 2)
Standard_Integer aDispMode = -1;
Standard_Integer isFaceBoundaryDraw = -1, isSmoothShading = -1;
Graphic3d_TypeOfShadingModel aShadingModel = Graphic3d_TOSM_DEFAULT;
NCollection_Sequence< vtkSmartPointer<vtkActor> > anActors;
for (Standard_Integer anArgIter = 1; anArgIter < theArgNum; ++anArgIter)
{
// Set disp mode for all objects
Standard_Integer aMode = Draw::Atoi (theArgs[1]); // Get mode
DoubleMapOfActorsAndNames::Iterator anIter (GetMapOfActors());
while (anIter.More())
TCollection_AsciiString anArgCase (theArgs[anArgIter]);
anArgCase.LowerCase();
if (anArgCase == "-faceboundarydraw"
|| anArgCase == "-drawfaceboundary"
|| anArgCase == "-faceboundary")
{
vtkSmartPointer<vtkActor> anActor = anIter.Key1();
IVtkTools_ShapeDataSource* aSrc = IVtkTools_ShapeObject::GetShapeSource (anActor);
if (aSrc)
bool toDraw = Draw::ParseOnOffNoIterator (theArgNum, theArgs, anArgIter);
isFaceBoundaryDraw = toDraw ? 1 : 0;
}
else if (anArgCase == "-smoothshading"
|| anArgCase == "-smooth")
{
bool toEnable = Draw::ParseOnOffNoIterator (theArgNum, theArgs, anArgIter);
isSmoothShading = toEnable ? 1 : 0;
}
else if (anArgIter + 1 < theArgNum
&& (anArgCase == "-shadingmodel"))
{
TCollection_AsciiString aModelName (theArgs[++anArgIter]);
aModelName.LowerCase();
if (aModelName == "fragment"
|| aModelName == "frag"
|| aModelName == "phong")
{
IVtkOCC_Shape::Handle anOccShape = aSrc->GetShape();
if (!anOccShape.IsNull())
aShadingModel = Graphic3d_TOSM_FRAGMENT;
}
else if (aModelName == "vertex"
|| aModelName == "vert"
|| aModelName == "gouraud")
{
aShadingModel = Graphic3d_TOSM_VERTEX;
}
else if (aModelName == "facet"
|| aModelName == "flat")
{
aShadingModel = Graphic3d_TOSM_FACET;
}
else
{
theDI << "Syntax error: unknown shading model '" << theArgs[anArgIter] << "'";
return 1;
}
}
else if (aDispMode == -1
&& (anArgCase == "0"
|| anArgCase == "1"))
{
aDispMode = Draw::Atoi (theArgs[anArgIter]);
}
else if (aDispMode == -1
&& (anArgCase == "-shaded"
|| anArgCase == "-shading"))
{
aDispMode = DM_Shading;
}
else if (aDispMode == -1
&& anArgCase == "-wireframe")
{
aDispMode = DM_Wireframe;
}
else
{
TCollection_AsciiString aName = theArgs[anArgIter];
vtkSmartPointer<vtkActor> anActor;
if (!GetMapOfActors().Find2 (aName, anActor))
{
theDI << "Syntax error: object '" << aName << "' not found";
return 1;
}
anActors.Append (anActor);
}
}
if (aDispMode == -1)
{
theDI << "Syntax error: wrong number of arguments";
return 1;
}
if (anActors.IsEmpty())
{
// update all objects
for (DoubleMapOfActorsAndNames::Iterator anIter (GetMapOfActors()); anIter.More(); anIter.Next())
{
anActors.Append (anIter.Key1());
}
}
for (NCollection_Sequence< vtkSmartPointer<vtkActor> >::Iterator anActorIter (anActors); anActorIter.More(); anActorIter.Next())
{
vtkSmartPointer<vtkActor> anActor = anActorIter.Value();
IVtkTools_ShapeDataSource* aSrc = IVtkTools_ShapeObject::GetShapeSource (anActor);
if (aSrc == NULL)
{
continue;
}
IVtkOCC_Shape::Handle anOccShape = aSrc->GetShape();
if (!anOccShape.IsNull())
{
IVtkTools_DisplayModeFilter* aFilter = GetPipeline ( anOccShape->GetId() )->GetDisplayModeFilter();
aFilter->SetDisplayMode ((IVtk_DisplayMode)aDispMode);
if (isFaceBoundaryDraw != -1)
{
// Set Red color for boundary edges
vtkLookupTable* aTable = (vtkLookupTable*)anActor->GetMapper()->GetLookupTable();
IVtkTools::SetLookupTableColor (aTable, MT_SharedEdge, 1., 0., 0., 1.);
aFilter->SetFaceBoundaryDraw (isFaceBoundaryDraw == 1);
}
if (isSmoothShading != -1)
{
aFilter->SetSmoothShading (isSmoothShading == 1);
}
switch (aShadingModel)
{
case Graphic3d_TOSM_FACET:
{
IVtkTools_DisplayModeFilter* aFilter = GetPipeline ( anOccShape->GetId() )->GetDisplayModeFilter();
aFilter->SetDisplayMode((IVtk_DisplayMode)aMode);
aFilter->Modified();
aFilter->Update();
anActor->GetProperty()->SetInterpolationToFlat();
break;
}
}
anIter.Next();
}
}
// Set disp mode for named object
else
{
TCollection_AsciiString aName = theArgs[1];
vtkSmartPointer<vtkActor> anActor;
if (!GetMapOfActors().Find2 (aName, anActor))
{
Message::SendFail() << "Syntax error: object '" << aName << "' not found";
return 1;
}
Standard_Integer aMode = atoi(theArgs[2]);
vtkSmartPointer<IVtkTools_ShapeDataSource> aSrc = IVtkTools_ShapeObject::GetShapeSource (anActor);
if (aSrc)
{
IVtkOCC_Shape::Handle anOccShape = aSrc->GetShape();
if (!anOccShape.IsNull())
{
IVtkTools_DisplayModeFilter* aFilter = GetPipeline (anOccShape->GetId())->GetDisplayModeFilter();
aFilter->SetDisplayMode ((IVtk_DisplayMode)aMode);
aFilter->Modified();
aFilter->Update();
}
}
}
// Redraw window
GetInteractor()->Render();
return 0;
}
//================================================================
// Function : VtkSetBoundaryDraw
// Purpose :
//================================================================
static Standard_Integer VtkSetBoundaryDraw (Draw_Interpretor& ,
Standard_Integer theArgNum,
const char** theArgs)
{
if (!GetInteractor()
|| !GetInteractor()->IsEnabled())
{
Message::SendFail() << "Error: call ivtkinit before";
return 1;
}
else if (theArgNum != 2 && theArgNum != 3)
{
Message::SendFail() << "Syntax error: expects 1 or 2 arguments";
return 1;
}
if (theArgNum == 2)
{
// Set disp mode for all objects
Standard_Boolean toDraw = true;
Draw::ParseOnOff (theArgs[1], toDraw);
DoubleMapOfActorsAndNames::Iterator anIter(GetMapOfActors());
while (anIter.More())
{
vtkSmartPointer<vtkActor> anActor = anIter.Key1();
// Set Red color for boundary edges
vtkLookupTable* aTable = (vtkLookupTable*)anActor->GetMapper()->GetLookupTable();
IVtkTools::SetLookupTableColor(aTable, MT_SharedEdge, 1., 0., 0., 1.);
IVtkTools_ShapeDataSource* aSrc = IVtkTools_ShapeObject::GetShapeSource(anActor);
if (aSrc)
{
IVtkOCC_Shape::Handle anOccShape = aSrc->GetShape();
if (!anOccShape.IsNull())
case Graphic3d_TOSM_VERTEX:
{
IVtkTools_DisplayModeFilter* aFilter = GetPipeline(anOccShape->GetId())->GetDisplayModeFilter();
aFilter->SetDisplayMode(DM_Shading);
aFilter->SetFaceBoundaryDraw(toDraw != 0);
aFilter->Modified();
aFilter->Update();
anActor->GetProperty()->SetInterpolationToGouraud();
break;
}
case Graphic3d_TOSM_FRAGMENT:
{
anActor->GetProperty()->SetInterpolationToPhong();
break;
}
default: break;
}
anIter.Next();
}
}
else
{
// Set disp mode for named object
TCollection_AsciiString aName = theArgs[1];
vtkSmartPointer<vtkActor> anActor;
if (!GetMapOfActors().Find2 (aName, anActor))
{
Message::SendFail() << "Syntax error: object '" << aName << "' not found";
return 1;
}
Standard_Boolean toDraw = true;
Draw::ParseOnOff (theArgs[2], toDraw);
// Set Red color for boundary edges
vtkLookupTable* aTable = (vtkLookupTable*)anActor->GetMapper()->GetLookupTable();
IVtkTools::SetLookupTableColor (aTable, MT_SharedEdge, 1., 0., 0., 1.);
vtkSmartPointer<IVtkTools_ShapeDataSource> aSrc = IVtkTools_ShapeObject::GetShapeSource (anActor);
if (aSrc)
{
IVtkOCC_Shape::Handle anOccShape = aSrc->GetShape();
if (!anOccShape.IsNull())
{
IVtkTools_DisplayModeFilter* aFilter = GetPipeline (anOccShape->GetId())->GetDisplayModeFilter();
aFilter->SetDisplayMode (DM_Shading);
aFilter->SetFaceBoundaryDraw (toDraw != 0);
aFilter->Modified();
aFilter->Update();
}
aFilter->Modified();
aFilter->Update();
}
}
@@ -1145,6 +1259,78 @@ static Standard_Integer VtkSetTransparency (Draw_Interpretor& ,
return 0;
}
//================================================================
// Function : VtkWriteVtp
// Purpose :
//================================================================
static Standard_Integer VtkWriteVtp (Draw_Interpretor& theDI,
Standard_Integer theArgNb,
const char** theArgVec)
{
if (!GetInteractor()
|| !GetInteractor()->IsEnabled())
{
Message::SendFail() << "Error: call ivtkinit before\n";
return 1;
}
vtkSmartPointer<vtkActor> anActor;
TCollection_AsciiString aFileName;
vtkSmartPointer<vtkXMLPolyDataWriter> aWriter = vtkSmartPointer<vtkXMLPolyDataWriter>::New();
for (Standard_Integer anArgIter = 1; anArgIter < theArgNb; ++anArgIter)
{
TCollection_AsciiString anArg (theArgVec[anArgIter]);
TCollection_AsciiString anArgCase (anArg);
anArgCase.LowerCase();
if (anArgCase == "-binary")
{
const bool isBinary = Draw::ParseOnOffIterator (theArgNb, theArgVec, anArgIter);
if (isBinary)
{
aWriter->SetDataModeToBinary();
}
else
{
aWriter->SetDataModeToAscii();
}
}
else if (anActor.GetPointer() == NULL
&& GetMapOfActors().Find2 (anArg, anActor))
{
vtkSmartPointer<IVtkTools_ShapeDataSource> aSrc = IVtkTools_ShapeObject::GetShapeSource (anActor);
if (aSrc.GetPointer() == NULL
|| aSrc->GetShape().IsNull())
{
theDI << "Syntax error: invalid actor '" << anArg << "'";
return 1;
}
aWriter->SetInputConnection (aSrc->GetOutputPort());
}
else if (aFileName.IsEmpty())
{
aFileName = anArg;
aWriter->SetFileName (aFileName.ToCString());
}
else
{
theDI << "Syntax error: unknown argument '" << anArg << "'";
return 1;
}
}
if (aFileName.IsEmpty() || anActor.GetPointer() == NULL)
{
Message::SendFail() << "Syntax error: wrong number of arguments";
return 1;
}
if (aWriter->Write() == 0)
{
theDI << "Error: unable to write file '" << aFileName << "'";
}
return 0;
}
//================================================================
// Function : VtkMoveTo
// Purpose :
@@ -1509,6 +1695,14 @@ void IVtkDraw::Commands (Draw_Interpretor& theCommands)
"ivtkclose : Closes the Vtk window.",
__FILE__, VtkClose, group);
theCommands.Add("ivtkdefaults",
"ivtkdefaults [-absDefl value]"
"\n\t\t: [-devCoeff value]"
"\n\t\t: [-angDefl value]"
"\n\t\t: [-autoTriang {off/on | 0/1}]"
"\n\t\t: Sets default VTK meshing parameters."
, __FILE__, VtkDefaults, group);
theCommands.Add("ivtkrenderparams",
"ivtkrenderparams [-depthPeeling NbLayers] [-shadows {on|off}]"
"\n\t\t: Sets Vtk rendering parameters."
@@ -1538,16 +1732,14 @@ void IVtkDraw::Commands (Draw_Interpretor& theCommands)
__FILE__, VtkRemove, group);
theCommands.Add("ivtksetdispmode",
"ivtksetdispmode [name] mode={0|1}"
"\n\t\t: Sets or unsets display mode 'mode' to the object with name 'name' or to all objects.",
"ivtksetdispmode [name] mode={0|1} [-faceBoundaryDraw {0|1}] [-smoothShading {0|1}]"
"\n\t\t: [-shadingModel {phong|gouraud|flat}]"
"\n\t\t: Sets or unsets display mode to the object with the given name or to all objects."
"\n\t\t: -faceBoundaryDraw show/hide boundaries within shading display mode"
"\n\t\t: -smoothShading enable/disable vertex normals for smooth shading"
"\n\t\t: -shadingModel sets specified shading model",
__FILE__, VtkSetDisplayMode, group);
theCommands.Add("ivtksetboundingdraw",
"ivtksetboundingdraw [name] {on|off}"
"\n\t\t: Sets or unsets boundaries drawing for shading display mode"
"\n\t\t: to the object with name 'name' or to all objects.",
__FILE__, VtkSetBoundaryDraw, group);
theCommands.Add("ivtksetselmode",
"ivtksetselmode [name] mode {on|off}"
"\n\t\t: Sets or unsets selection mode 'mode' to the object with name 'name'"
@@ -1616,6 +1808,11 @@ void IVtkDraw::Commands (Draw_Interpretor& theCommands)
"ivtksettransparency name 0..1"
"\n\t\t: Sets transparency to the object with name 'name'.",
__FILE__, VtkSetTransparency, group);
theCommands.Add("ivtkwritevtp",
"ivtkwritevtp name1 fileName"
"\n\t\t: Export IVtk actor into VTP format.",
__FILE__, VtkWriteVtp, group);
}
//================================================================

View File

@@ -39,7 +39,8 @@ IMPLEMENT_STANDARD_RTTIEXT(IVtkDraw_HighlightAndSelectionPipeline,Standard_Trans
//===========================================================
IVtkDraw_HighlightAndSelectionPipeline::IVtkDraw_HighlightAndSelectionPipeline (const TopoDS_Shape& theShape,
const Standard_Integer theShapeID)
const Standard_Integer theShapeID,
const Handle(Prs3d_Drawer)& theDrawerLink)
: Standard_Transient()
{
/* ===========================
@@ -57,7 +58,7 @@ IVtkDraw_HighlightAndSelectionPipeline::IVtkDraw_HighlightAndSelectionPipeline (
* ======================== */
myActor = vtkSmartPointer<vtkActor>::New();
IVtkOCC_Shape::Handle anIVtkShape = new IVtkOCC_Shape (theShape);
IVtkOCC_Shape::Handle anIVtkShape = new IVtkOCC_Shape (theShape, theDrawerLink);
anIVtkShape->SetId (theShapeID);
vtkSmartPointer<IVtkTools_ShapeDataSource> aDataSource = vtkSmartPointer<IVtkTools_ShapeDataSource>::New();
aDataSource->SetShape (anIVtkShape);

View File

@@ -37,6 +37,8 @@
typedef NCollection_DataMap <IVtk_IdType, vtkSmartPointer<IVtkTools_DisplayModeFilter> > DisplayModeFiltersMap;
typedef NCollection_DataMap <IVtk_IdType, vtkSmartPointer<IVtkTools_SubPolyDataFilter> > SubShapesFiltersMap;
class Prs3d_Drawer;
class IVtkDraw_HighlightAndSelectionPipeline;
DEFINE_STANDARD_HANDLE(IVtkDraw_HighlightAndSelectionPipeline, Standard_Transient)
@@ -61,7 +63,8 @@ public:
public:
IVtkDraw_HighlightAndSelectionPipeline (const TopoDS_Shape& theShape,
const Standard_Integer theShapeID);
const Standard_Integer theShapeID,
const Handle(Prs3d_Drawer)& theDrawerLink);
~IVtkDraw_HighlightAndSelectionPipeline() {}
public:

View File

@@ -18,6 +18,7 @@
#include <AIS_Shape.hxx>
#include <BRepBndLib.hxx>
#include <Message.hxx>
#include <StdPrs_ToolTriangulatedShape.hxx>
#include <Select3D_SensitiveBox.hxx>
#include <SelectMgr_Selection.hxx>
#include <Standard_ErrorHandler.hxx>
@@ -27,12 +28,9 @@
IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_SelectableObject,SelectMgr_SelectableObject)
// Handle implementation
//============================================================================
// Method: Constructor
// Purpose: Constructs a selectable object initialized by the given shape
// Purpose:
//============================================================================
IVtkOCC_SelectableObject::IVtkOCC_SelectableObject (const IVtkOCC_Shape::Handle& theShape)
: SelectMgr_SelectableObject (PrsMgr_TOP_AllView),
@@ -42,37 +40,35 @@ IVtkOCC_SelectableObject::IVtkOCC_SelectableObject (const IVtkOCC_Shape::Handle&
{
myShape->SetSelectableObject (this);
}
// Minor stuff - but it facilitates usage of OCCT selection
// classes dealing with deflection, see ComputeSelection() below
myOCCTDrawer = new Prs3d_Drawer();
}
//============================================================================
// Method: Constructor
// Purpose: Constructs uninitialized selectable object.
// setShape() should be called later.
// Purpose:
//============================================================================
IVtkOCC_SelectableObject::IVtkOCC_SelectableObject()
: SelectMgr_SelectableObject (PrsMgr_TOP_AllView),
myShape (0)
{ }
: SelectMgr_SelectableObject (PrsMgr_TOP_AllView)
{
//
}
//============================================================================
// Method: Destructor
// Purpose:
// Purpose:
//============================================================================
IVtkOCC_SelectableObject::~IVtkOCC_SelectableObject()
{ }
{
//
}
//============================================================================
// Method: SetShape
// Purpose: Sets the selectable shape
// Purpose:
//============================================================================
void IVtkOCC_SelectableObject::SetShape (const IVtkOCC_Shape::Handle& theShape)
{
myShape = theShape;
if (! myShape.IsNull())
if (!myShape.IsNull())
{
myShape->SetSelectableObject (this);
}
@@ -84,7 +80,7 @@ void IVtkOCC_SelectableObject::SetShape (const IVtkOCC_Shape::Handle& theShape)
//============================================================================
// Method: ComputeSelection
// Purpose: Internal method, computes selection data for viewer selector
// Purpose:
//============================================================================
void IVtkOCC_SelectableObject::ComputeSelection (const Handle(SelectMgr_Selection)& theSelection,
const Standard_Integer theMode)
@@ -94,33 +90,17 @@ void IVtkOCC_SelectableObject::ComputeSelection (const Handle(SelectMgr_Selectio
return;
}
TopoDS_Shape anOcctShape = myShape->GetShape();
if (anOcctShape.ShapeType() == TopAbs_COMPOUND && anOcctShape.NbChildren() == 0)
const TopoDS_Shape& anOcctShape = myShape->GetShape();
if (anOcctShape.ShapeType() == TopAbs_COMPOUND
&& anOcctShape.NbChildren() == 0)
{
// Shape empty -> go away
return;
}
TopAbs_ShapeEnum aTypeOfSel = AIS_Shape::SelectionType (theMode);
Standard_Real aDeflection = myOCCTDrawer->MaximalChordialDeviation();
if (myOCCTDrawer->TypeOfDeflection() == Aspect_TOD_RELATIVE)
{
Bnd_Box aBndBox;
BRepBndLib::Add (anOcctShape, aBndBox);
if (!aBndBox.IsVoid())
{
Standard_Real aXmin, aYmin, aZmin, aXmax, aYmax, aZmax;
aBndBox.Get (aXmin, aYmin, aZmin, aXmax, aYmax, aZmax);
aDeflection = Max (aXmax - aXmin, Max (aYmax - aYmin, aZmax - aZmin)) *
myOCCTDrawer->DeviationCoefficient();
}
}
// Assume the shape has been displayed already -> triangulation should exist
Standard_Boolean isAutoTriangulation = Standard_False;
const TopAbs_ShapeEnum aTypeOfSel = AIS_Shape::SelectionType (theMode);
const Handle(Prs3d_Drawer)& aDrawer = myShape->Attributes();
const Standard_Real aDeflection = StdPrs_ToolTriangulatedShape::GetDeflection (anOcctShape, aDrawer);
try
{
OCC_CATCH_SIGNALS
@@ -129,8 +109,8 @@ void IVtkOCC_SelectableObject::ComputeSelection (const Handle(SelectMgr_Selectio
anOcctShape,
aTypeOfSel,
aDeflection,
myOCCTDrawer->DeviationAngle(),
isAutoTriangulation);
aDrawer->DeviationAngle(),
aDrawer->IsAutoTriangulation());
}
catch (const Standard_Failure& anException)
{
@@ -158,8 +138,7 @@ const Bnd_Box& IVtkOCC_SelectableObject::BoundingBox()
return myBndBox;
}
TopoDS_Shape anOcctShape = myShape->GetShape();
const TopoDS_Shape& anOcctShape = myShape->GetShape();
if (anOcctShape.ShapeType() == TopAbs_COMPOUND && anOcctShape.NbChildren() == 0)
{
// Shape empty -> nothing to do

View File

@@ -73,7 +73,6 @@ private:
private:
IVtkOCC_Shape::Handle myShape;
Bnd_Box myBndBox;
Handle(Prs3d_Drawer) myOCCTDrawer;
};
#endif // __IVTKOCC_SELECTABLEOBJECT_H__

View File

@@ -14,20 +14,29 @@
// commercial license or contractual agreement.
#include <IVtkOCC_Shape.hxx>
#include <TopExp.hxx>
IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_Shape,IVtk_IShape)
// Handle implementation
//============================================================================
// Method: Constructor
// Purpose:
//============================================================================
IVtkOCC_Shape::IVtkOCC_Shape (const TopoDS_Shape& theShape)
: myTopoDSShape (theShape)
IVtkOCC_Shape::IVtkOCC_Shape (const TopoDS_Shape& theShape,
const Handle(Prs3d_Drawer)& theDrawerLink)
: myTopoDSShape (theShape),
myOCCTDrawer (new Prs3d_Drawer())
{
if (!theDrawerLink.IsNull())
{
myOCCTDrawer->SetLink (theDrawerLink);
}
else
{
// these old defaults have been moved from IVtkOCC_ShapeMesher constructor
myOCCTDrawer->SetDeviationCoefficient (0.0001); // Aspect_TOD_RELATIVE
}
buildSubShapeIdMap();
}
@@ -38,26 +47,24 @@ IVtkOCC_Shape::IVtkOCC_Shape (const TopoDS_Shape& theShape)
IVtkOCC_Shape::~IVtkOCC_Shape() { }
//============================================================================
// Method: getSubShapeId
// Purpose: Returns unique ID of the given sub-shape within the top-level shape.
// Method: GetSubShapeId
// Purpose:
//============================================================================
IVtk_IdType IVtkOCC_Shape::GetSubShapeId (const TopoDS_Shape& theSubShape) const
{
Standard_Integer anIndex = theSubShape.IsSame (myTopoDSShape) ?
-1 :
mySubShapeIds.FindIndex (theSubShape);
if (!anIndex) // Not found in the map
if (anIndex == 0) // Not found in the map
{
anIndex = -1;
return (IVtk_IdType )-1;
}
return (IVtk_IdType)anIndex;
}
//============================================================================
// Method: getSubIds
// Purpose: Get ids of sub-shapes composing a sub-shape with the given id.
// Purpose:
//============================================================================
IVtk_ShapeIdList IVtkOCC_Shape::GetSubIds (const IVtk_IdType theId) const
{
@@ -73,7 +80,7 @@ IVtk_ShapeIdList IVtkOCC_Shape::GetSubIds (const IVtk_IdType theId) const
}
else
{
// Find all composing vertices, edges and faces of the the found sub-shape
// Find all composing vertices, edges and faces of the found sub-shape
// and append their ids to the result.
TopTools_IndexedMapOfShape aSubShapes;
if (aShape.IsSame (myTopoDSShape))

View File

@@ -32,19 +32,23 @@ public:
typedef Handle(IVtkOCC_Shape) Handle;
//! Constructor for OCC IShape implementation
Standard_EXPORT IVtkOCC_Shape (const TopoDS_Shape& theShape);
//! Constructor for OCC IShape implementation.
//! @param theShape [in] shape to display
//! @param theDrawerLink [in] default attributes to link
Standard_EXPORT IVtkOCC_Shape (const TopoDS_Shape& theShape,
const Handle(Prs3d_Drawer)& theDrawerLink = Handle(Prs3d_Drawer)());
//! Destructor
Standard_EXPORT virtual ~IVtkOCC_Shape();
//! Returns unique ID of the given sub-shape within the top-level shape.
Standard_EXPORT IVtk_IdType GetSubShapeId (const IVtk_IShape::Handle&) const;
DEFINE_STANDARD_RTTIEXT(IVtkOCC_Shape,IVtk_IShape)
//! Get the wrapped original OCCT shape
//! @return TopoDS_Shape the wrapped original OCCT shape
TopoDS_Shape GetShape() const
const TopoDS_Shape& GetShape() const
{
return myTopoDSShape;
}
@@ -78,11 +82,17 @@ public:
}
//! @return Handle to the selectable object for this shape.
Handle(SelectMgr_SelectableObject) GetSelectableObject() const
const Handle(SelectMgr_SelectableObject)& GetSelectableObject() const
{
return mySelectable;
}
//! Return presentation attributes.
const Handle(Prs3d_Drawer)& Attributes() const { return myOCCTDrawer; }
//! Set presentation attributes.
void SetAttributes (const Handle(Prs3d_Drawer)& theDrawer) { myOCCTDrawer = theDrawer; }
private:
//! @brief Build a map of sub-shapes by their IDs
//!
@@ -94,6 +104,7 @@ private:
private:
TopTools_IndexedMapOfShape mySubShapeIds; //!< Map of sub-shapes by their IDs
TopoDS_Shape myTopoDSShape; //!< The wrapped main OCCT shape
Handle(Prs3d_Drawer) myOCCTDrawer; //!< presentation attributes
Handle(SelectMgr_SelectableObject) mySelectable; //!< Link to a holder of selection primitives
};

View File

@@ -15,54 +15,71 @@
#include <IVtkOCC_ShapeMesher.hxx>
#include <Adaptor3d_IsoCurve.hxx>
#include <Bnd_Box.hxx>
#include <BRep_Tool.hxx>
#include <BRepBndLib.hxx>
#include <BRepMesh_DiscretFactory.hxx>
#include <BRepMesh_DiscretRoot.hxx>
#include <BRepTools.hxx>
#include <Hatch_Hatcher.hxx>
#include <GCPnts_QuasiUniformDeflection.hxx>
#include <GCPnts_TangentialDeflection.hxx>
#include <Geom_BezierSurface.hxx>
#include <Geom_BSplineSurface.hxx>
#include <Geom2dAdaptor_Curve.hxx>
#include <GeomAdaptor_Curve.hxx>
#include <gp_Dir2d.hxx>
#include <gp_Pnt2d.hxx>
#include <Message.hxx>
#include <NCollection_Array1.hxx>
#include <Poly_Polygon3D.hxx>
#include <Poly_PolygonOnTriangulation.hxx>
#include <Poly_Triangulation.hxx>
#include <Precision.hxx>
#include <Prs3d.hxx>
#include <Prs3d_Drawer.hxx>
#include <Prs3d_IsoAspect.hxx>
#include <Standard_ErrorHandler.hxx>
#include <StdPrs_Isolines.hxx>
#include <StdPrs_ToolTriangulatedShape.hxx>
#include <TColgp_SequenceOfPnt2d.hxx>
#include <TColStd_Array1OfReal.hxx>
#include <TopExp.hxx>
#include <TopExp_Explorer.hxx>
#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_ShapeMesher,IVtk_IShapeMesher)
// Handle implementation
//================================================================
// Function : IVtkOCC_ShapeMesher
// Purpose :
//================================================================
IVtkOCC_ShapeMesher::IVtkOCC_ShapeMesher()
{
//
}
//================================================================
// Function : ~IVtkOCC_ShapeMesher
// Purpose :
//================================================================
IVtkOCC_ShapeMesher::~IVtkOCC_ShapeMesher()
{
//
}
//================================================================
// Function : internalBuild
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::internalBuild()
{
// TODO: do we need any protection here so as not to triangualte
// the shape twice??? This can be done e.g. by checking if
// triangulation exists for TopoDS_Shape..
meshShape();
const TopoDS_Shape& anOcctShape = GetShapeObj()->GetShape();
if (anOcctShape.IsNull())
{
return;
}
const Handle(Prs3d_Drawer)& anOcctDrawer = GetShapeObj()->Attributes();
const Standard_Real aShapeDeflection = StdPrs_ToolTriangulatedShape::GetDeflection (anOcctShape, anOcctDrawer);
if (anOcctDrawer->IsAutoTriangulation())
{
StdPrs_ToolTriangulatedShape::ClearOnOwnDeflectionChange (anOcctShape, anOcctDrawer, true);
StdPrs_ToolTriangulatedShape::Tessellate (anOcctShape, anOcctDrawer);
}
for (TopExp_Explorer aFaceIter (anOcctShape, TopAbs_FACE); aFaceIter.More(); aFaceIter.Next())
{
const TopoDS_Face& anOcctFace = TopoDS::Face (aFaceIter.Current());
TopLoc_Location aLoc;
if (const Handle(Poly_Triangulation)& anOcctTriangulation = BRep_Tool::Triangulation (anOcctFace, aLoc))
{
StdPrs_ToolTriangulatedShape::ComputeNormals (anOcctFace, anOcctTriangulation);
}
}
// Free vertices and free edges should always be shown.
// Shared edges are needed in WF representation only.
@@ -71,83 +88,79 @@ void IVtkOCC_ShapeMesher::internalBuild()
addEdges();
// Build wireframe points and cells (lines for isolines)
addWireFrameFaces();
for (TopExp_Explorer aFaceIter (anOcctShape, TopAbs_FACE); aFaceIter.More(); aFaceIter.Next())
{
const TopoDS_Face& anOcctFace = TopoDS::Face (aFaceIter.Current());
try
{
OCC_CATCH_SIGNALS
addWFFace (anOcctFace, GetShapeObj()->GetSubShapeId (anOcctFace), aShapeDeflection);
}
catch (const Standard_Failure& anException)
{
Message::SendFail (TCollection_AsciiString("Error: addWireFrameFaces() wireframe presentation builder has failed (")
+ anException.GetMessageString() + ")");
}
}
// Build shaded representation (based on Poly_Triangulation)
addShadedFaces();
for (TopExp_Explorer aFaceIter (anOcctShape, TopAbs_FACE); aFaceIter.More(); aFaceIter.Next())
{
const TopoDS_Face& anOcctFace = TopoDS::Face (aFaceIter.Current());
addShadedFace (anOcctFace, GetShapeObj()->GetSubShapeId (anOcctFace));
}
}
//================================================================
// Function : GetShapeObj
// Purpose :
// Purpose :
//================================================================
const IVtkOCC_Shape::Handle IVtkOCC_ShapeMesher::GetShapeObj() const
{
return (IVtkOCC_Shape::Handle::DownCast(myShapeObj));
return IVtkOCC_Shape::Handle::DownCast(myShapeObj);
}
//================================================================
// Function : GetDeflection
// Purpose : Returns absolute deflection used by this algorithm.
// Purpose :
//================================================================
Standard_Real IVtkOCC_ShapeMesher::GetDeflection() const
{
if (myDeflection < Precision::Confusion()) // if not yet initialized
{
Handle(Prs3d_Drawer) aDefDrawer = new Prs3d_Drawer();
aDefDrawer->SetTypeOfDeflection (Aspect_TOD_RELATIVE);
aDefDrawer->SetDeviationCoefficient (GetDeviationCoeff());
myDeflection = StdPrs_ToolTriangulatedShape::GetDeflection (GetShapeObj()->GetShape(), aDefDrawer);
}
return myDeflection;
const TopoDS_Shape& anOcctShape = GetShapeObj()->GetShape();
return !anOcctShape.IsNull()
? StdPrs_ToolTriangulatedShape::GetDeflection (anOcctShape, GetShapeObj()->Attributes())
: 0.0;
}
//================================================================
// Function : meshShape
// Purpose :
// Function : GetDeflection
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::meshShape()
Standard_Real IVtkOCC_ShapeMesher::GetDeviationCoeff() const
{
const TopoDS_Shape& anOcctShape = GetShapeObj()->GetShape();
if (anOcctShape.IsNull())
if (IVtkOCC_Shape::Handle aShape = GetShapeObj())
{
return;
return aShape->Attributes()->DeviationCoefficient();
}
return 0.0;
}
//Clean triangulation before compute incremental mesh
BRepTools::Clean (anOcctShape);
//Compute triangulation
Standard_Real aDeflection = GetDeflection();
if (aDeflection < Precision::Confusion())
//================================================================
// Function : GetDeviationAngle
// Purpose :
//================================================================
Standard_Real IVtkOCC_ShapeMesher::GetDeviationAngle() const
{
if (IVtkOCC_Shape::Handle aShape = GetShapeObj())
{
return;
}
try
{
OCC_CATCH_SIGNALS
Handle(BRepMesh_DiscretRoot) anAlgo;
anAlgo = BRepMesh_DiscretFactory::Get().Discret (anOcctShape,
aDeflection,
GetDeviationAngle());
if (!anAlgo.IsNull())
{
anAlgo->Perform();
}
}
catch (const Standard_Failure& anException)
{
Message::SendFail (TCollection_AsciiString("Error: IVtkOCC_ShapeMesher::meshShape() triangulation builder has failed (")
+ anException.GetMessageString() + ")");
return aShape->Attributes()->DeviationAngle();
}
return 0.0;
}
//================================================================
// Function : addFreeVertices
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addFreeVertices()
{
@@ -157,26 +170,20 @@ void IVtkOCC_ShapeMesher::addFreeVertices()
TopAbs_EDGE,
aVertexMap);
Standard_Integer aVertNum = aVertexMap.Extent();
IVtk_MeshType aType;
for (Standard_Integer anIt = 1; anIt <= aVertNum; anIt++)
const Standard_Integer aVertNum = aVertexMap.Extent();
for (Standard_Integer aVertIter = 1; aVertIter <= aVertNum; ++aVertIter)
{
if (aVertexMap.FindFromIndex(anIt).IsEmpty())
{
aType = MT_FreeVertex;
}
else
{
aType = MT_SharedVertex;
}
const TopoDS_Vertex& aVertex = TopoDS::Vertex (aVertexMap.FindKey (anIt));
const IVtk_MeshType aType = aVertexMap.FindFromIndex (aVertIter).IsEmpty()
? MT_FreeVertex
: MT_SharedVertex;
const TopoDS_Vertex& aVertex = TopoDS::Vertex (aVertexMap.FindKey (aVertIter));
addVertex (aVertex, GetShapeObj()->GetSubShapeId (aVertex), aType);
}
}
//================================================================
// Function : addEdges
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addEdges()
{
@@ -185,16 +192,14 @@ void IVtkOCC_ShapeMesher::addEdges()
TopAbs_EDGE,
TopAbs_FACE,
anEdgesMap);
int aNbFaces;
IVtk_MeshType aType;
myEdgesTypes.Clear();
TopTools_IndexedDataMapOfShapeListOfShape::Iterator aEdgeIt(anEdgesMap);
for (; aEdgeIt.More(); aEdgeIt.Next())
for (TopTools_IndexedDataMapOfShapeListOfShape::Iterator aEdgeIt(anEdgesMap);
aEdgeIt.More(); aEdgeIt.Next())
{
const TopoDS_Edge& anOcctEdge = TopoDS::Edge (aEdgeIt.Key());
const TopTools_ListOfShape& aFaceList = aEdgeIt.Value();
aNbFaces = aFaceList.Extent();
const int aNbFaces = aFaceList.Extent();
IVtk_MeshType aType = MT_Undefined;
if (aNbFaces == 0)
{
aType = MT_FreeEdge;
@@ -213,54 +218,9 @@ void IVtkOCC_ShapeMesher::addEdges()
}
}
//================================================================
// Function : addWireFrameFaces
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addWireFrameFaces()
{
// Check the deflection value once for all faces
if (GetDeflection() < Precision::Confusion())
{
return;
}
TopExp_Explorer aFaceIter (GetShapeObj()->GetShape(), TopAbs_FACE);
for (; aFaceIter.More(); aFaceIter.Next())
{
const TopoDS_Face& anOcctFace = TopoDS::Face (aFaceIter.Current());
try
{
OCC_CATCH_SIGNALS
addWFFace (anOcctFace,
GetShapeObj()->GetSubShapeId (anOcctFace));
}
catch (const Standard_Failure& anException)
{
Message::SendFail (TCollection_AsciiString("Error: addWireFrameFaces() wireframe presentation builder has failed (")
+ anException.GetMessageString() + ")");
}
}
}
//================================================================
// Function : addShadedFaces
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addShadedFaces()
{
TopExp_Explorer aFaceIter (GetShapeObj()->GetShape(), TopAbs_FACE);
for (; aFaceIter.More(); aFaceIter.Next())
{
const TopoDS_Face& anOcctFace = TopoDS::Face (aFaceIter.Current());
addShadedFace (anOcctFace,
GetShapeObj()->GetSubShapeId (anOcctFace));
}
}
//================================================================
// Function : addVertex
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addVertex (const TopoDS_Vertex& theVertex,
const IVtk_IdType theShapeId,
@@ -273,53 +233,14 @@ void IVtkOCC_ShapeMesher::addVertex (const TopoDS_Vertex& theVertex,
gp_Pnt aPnt3d = BRep_Tool::Pnt (theVertex);
IVtk_PointId anId =
myShapeData->InsertCoordinate (aPnt3d.X(), aPnt3d.Y(), aPnt3d.Z());
IVtk_PointId anId = myShapeData->InsertCoordinate (aPnt3d);
myShapeData->InsertVertex (theShapeId, anId, theMeshType);
}
//================================================================
// Function : processPolyline
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::processPolyline (Standard_Integer theNbNodes,
const TColgp_Array1OfPnt& thePoints,
const TColStd_Array1OfInteger& thePointIds,
const IVtk_IdType theOcctId,
bool theNoTransform,
gp_Trsf theTransformation,
const IVtk_MeshType theMeshType)
{
if (theNbNodes < 2)
{
return;
}
IVtk_PointIdList aPolyPointIds;
IVtk_PointId anId;
for (Standard_Integer aJ = 0; aJ < theNbNodes; aJ++)
{
Standard_Integer aPntId = thePointIds (aJ + 1);
gp_Pnt point = thePoints (aPntId);
if (!theNoTransform)
{
// Apply the transformation to points
point.Transform (theTransformation);
}
anId = myShapeData->InsertCoordinate (point.X(), point.Y(), point.Z());
aPolyPointIds.Append (anId);
}
myShapeData->InsertLine (theOcctId, &aPolyPointIds, theMeshType);
}
//================================================================
// Function : addEdge
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addEdge (const TopoDS_Edge& theEdge,
const IVtk_IdType theShapeId,
@@ -330,81 +251,69 @@ void IVtkOCC_ShapeMesher::addEdge (const TopoDS_Edge& theEdge,
return;
}
// Two discrete representations of an OCCT edge are possible:
// 1. Polygon on trinagulation - holds Ids of points
// contained in Poly_Triangulation object
Handle(Poly_PolygonOnTriangulation) aPolyOnTriangulation;
Handle(Poly_Triangulation) aTriangulation;
TopLoc_Location aLocation;
BRep_Tool::PolygonOnTriangulation (theEdge,
aPolyOnTriangulation,
aTriangulation,
aLocation,
1);
// 2. 3D polygon - holds 3D points
Handle(Poly_Polygon3D) aPoly3d;
if (aPolyOnTriangulation.IsNull())
TopLoc_Location aLoc;
BRep_Tool::PolygonOnTriangulation (theEdge, aPolyOnTriangulation, aTriangulation, aLoc, 1);
if (!aPolyOnTriangulation.IsNull()
&& aPolyOnTriangulation->NbNodes() >= 2)
{
aPoly3d = BRep_Tool::Polygon3D (theEdge, aLocation);
// prefer polygon on triangulation when defined
const gp_Trsf aTrsf = aLoc.Transformation();
const bool hasTransform = !aLoc.IsIdentity();
IVtk_PointIdList aPolyPointIds;
const Standard_Integer aNbNodes = aPolyOnTriangulation->NbNodes();
for (Standard_Integer aNodeIter = 0; aNodeIter < aNbNodes; ++aNodeIter)
{
const Standard_Integer aPntId = aPolyOnTriangulation->Node (aNodeIter + 1);
gp_Pnt aPoint = aTriangulation->Node (aPntId);
gp_Dir aNorm = aTriangulation->HasNormals() ? aTriangulation->Normal (aPntId) : gp::DZ();
if (hasTransform)
{
aPoint.Transform (aTrsf);
aNorm .Transform (aTrsf);
}
const IVtk_PointId anId = myShapeData->InsertPoint (aPoint, Graphic3d_Vec3 ((float )aNorm.X(), (float )aNorm.Y(), (float )aNorm.Z()));
aPolyPointIds.Append (anId);
}
myShapeData->InsertLine (theShapeId, &aPolyPointIds, theMeshType);
return;
}
if (aPoly3d.IsNull() && aPolyOnTriangulation.IsNull())
// try polygon 3d
Handle(Poly_Polygon3D) aPoly3d = BRep_Tool::Polygon3D (theEdge, aLoc);
if (aPoly3d.IsNull()
|| aPoly3d->NbNodes() < 2)
{
return;
}
// Handle a non-identity transofmation applied to the edge
gp_Trsf anEdgeTransf;
bool noTransform = true;
if (!aLocation.IsIdentity())
const gp_Trsf anEdgeTransf = aLoc.Transformation();
const bool noTransform = aLoc.IsIdentity();
IVtk_PointIdList aPolyPointIds;
for (Standard_Integer aNodeIter = 1; aNodeIter <= aPoly3d->NbNodes(); ++aNodeIter)
{
noTransform = false;
anEdgeTransf = aLocation.Transformation();
}
if (!aPoly3d.IsNull())
{
Standard_Integer aNbNodes = aPoly3d->NbNodes();
const TColgp_Array1OfPnt& aPoints = aPoly3d->Nodes();
TColStd_Array1OfInteger aPointIds (1, aNbNodes);
for (Standard_Integer anI = 1; anI <= aNbNodes; anI++)
gp_Pnt aPnt = aPoly3d->Nodes().Value (aNodeIter);
if (!noTransform)
{
aPointIds.SetValue (anI, anI);
aPnt.Transform (anEdgeTransf);
}
processPolyline (aNbNodes,
aPoints,
aPointIds,
theShapeId,
noTransform,
anEdgeTransf,
theMeshType);
}
else if (aPolyOnTriangulation->NbNodes() >= 2)
{
IVtk_PointIdList aPolyPointIds;
const Standard_Integer aNbNodes = aPolyOnTriangulation->NbNodes();
for (Standard_Integer aJ = 0; aJ < aNbNodes; aJ++)
{
const Standard_Integer aPntId = aPolyOnTriangulation->Node (aJ + 1);
gp_Pnt aPoint = aTriangulation->Node (aPntId);
if (!noTransform) { aPoint.Transform (anEdgeTransf); }
IVtk_PointId anId = myShapeData->InsertCoordinate (aPoint.X(), aPoint.Y(), aPoint.Z());
aPolyPointIds.Append (anId);
}
myShapeData->InsertLine (theShapeId, &aPolyPointIds, theMeshType);
const IVtk_PointId anId = myShapeData->InsertCoordinate (aPnt);
aPolyPointIds.Append (anId);
}
myShapeData->InsertLine (theShapeId, &aPolyPointIds, theMeshType);
}
//================================================================
// Function : addWFFace
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId)
void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId,
const Standard_Real theDeflection)
{
if (theFace.IsNull())
{
@@ -414,12 +323,6 @@ void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
TopoDS_Face aFaceToMesh = theFace;
aFaceToMesh.Orientation (TopAbs_FORWARD);
// The code that builds wireframe representation for a TopoDS_Face
// has been adapted from some OCCT 6.5.1 methods:
// - Prs3d_WFShape::Add()
// - StdPrs_WFDeflectionRestrictedFace::Add()
// - StdPrs_DeflectionCurve::Add()
// Add face's edges here but with the face ID
for (TopExp_Explorer anEdgeIter (aFaceToMesh, TopAbs_EDGE); anEdgeIter.More(); anEdgeIter.Next())
{
@@ -434,16 +337,8 @@ void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
return;
}
const Standard_Real aDeflection = GetDeflection();
Handle(Prs3d_Drawer) aDrawer = new Prs3d_Drawer();
aDrawer->SetUIsoAspect (new Prs3d_IsoAspect (Quantity_NOC_WHITE, Aspect_TOL_SOLID, 1.0f, myNbIsos[0]));
aDrawer->SetVIsoAspect (new Prs3d_IsoAspect (Quantity_NOC_WHITE, Aspect_TOL_SOLID, 1.0f, myNbIsos[1]));
aDrawer->SetDeviationAngle (myDevAngle);
aDrawer->SetDeviationCoefficient (myDevCoeff);
aDrawer->SetMaximalChordialDeviation (aDeflection);
Prs3d_NListOfSequenceOfPnt aPolylines;
StdPrs_Isolines::Add (theFace, aDrawer, aDeflection, aPolylines, aPolylines);
StdPrs_Isolines::Add (theFace, GetShapeObj()->Attributes(), theDeflection, aPolylines, aPolylines);
for (Prs3d_NListOfSequenceOfPnt::Iterator aPolyIter (aPolylines); aPolyIter.More(); aPolyIter.Next())
{
const Handle(TColgp_HSequenceOfPnt)& aPoints = aPolyIter.Value();
@@ -457,7 +352,7 @@ void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
for (TColgp_HSequenceOfPnt::Iterator aNodeIter (*aPoints); aNodeIter.More(); aNodeIter.Next())
{
const gp_Pnt& aPnt = aNodeIter.Value();
const IVtk_PointId anId = myShapeData->InsertCoordinate (aPnt.X(), aPnt.Y(), aPnt.Z());
const IVtk_PointId anId = myShapeData->InsertCoordinate (aPnt);
aPolyPointIds.Append (anId);
}
@@ -467,7 +362,7 @@ void IVtkOCC_ShapeMesher::addWFFace (const TopoDS_Face& theFace,
//================================================================
// Function : addShadedFace
// Purpose :
// Purpose :
//================================================================
void IVtkOCC_ShapeMesher::addShadedFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId)
@@ -477,52 +372,57 @@ void IVtkOCC_ShapeMesher::addShadedFace (const TopoDS_Face& theFace,
return;
}
// Build triangulation of the face.
TopLoc_Location aLoc;
Handle(Poly_Triangulation) anOcctTriangulation = BRep_Tool::Triangulation (theFace, aLoc);
const Handle(Poly_Triangulation)& anOcctTriangulation = BRep_Tool::Triangulation (theFace, aLoc);
if (anOcctTriangulation.IsNull())
{
return;
}
gp_Trsf aPntTransform;
Standard_Boolean noTransform = Standard_True;
if (!aLoc.IsIdentity())
{
noTransform = Standard_False;
aPntTransform = aLoc.Transformation();
}
// Determinant of transform matrix less then 0 means that mirror transform applied
const gp_Trsf aTrsf = aLoc.Transformation();
const bool hasTransform = !aLoc.IsIdentity();
const bool isMirrored = aTrsf.VectorialPart().Determinant() < 0;
// Get triangulation points.
Standard_Integer aNbPoints = anOcctTriangulation->NbNodes();
// Keep inserted points id's of triangulation in an array.
NCollection_Array1<IVtk_PointId> aPointIds (1, aNbPoints);
IVtk_PointId anId;
Standard_Integer anI;
for (anI = 1; anI <= aNbPoints; anI++)
for (Standard_Integer aNodeIter = 1; aNodeIter <= aNbPoints; ++aNodeIter)
{
gp_Pnt aPoint = anOcctTriangulation->Node (anI);
if (!noTransform)
gp_Pnt aPoint = anOcctTriangulation->Node (aNodeIter);
gp_Dir aNorm = anOcctTriangulation->HasNormals() ? anOcctTriangulation->Normal (aNodeIter) : gp::DZ();
if ((theFace.Orientation() == TopAbs_REVERSED) ^ isMirrored)
{
aPoint.Transform (aPntTransform);
aNorm.Reverse();
}
if (hasTransform)
{
aPoint.Transform (aTrsf);
aNorm .Transform (aTrsf);
}
// Add a point into output shape data and keep its id in the array.
anId = myShapeData->InsertCoordinate (aPoint.X(), aPoint.Y(), aPoint.Z());
aPointIds.SetValue (anI, anId);
const IVtk_PointId anId = myShapeData->InsertPoint (aPoint, Graphic3d_Vec3 ((float )aNorm.X(), (float )aNorm.Y(), (float )aNorm.Z()));
aPointIds.SetValue (aNodeIter, anId);
}
// Create triangles on the created triangulation points.
Standard_Integer aNbTriangles = anOcctTriangulation->NbTriangles();
const Standard_Integer aNbTriangles = anOcctTriangulation->NbTriangles();
Standard_Integer aN1, aN2, aN3;
for (anI = 1; anI <= aNbTriangles; anI++)
for (Standard_Integer aTriIter = 1; aTriIter <= aNbTriangles; ++aTriIter)
{
anOcctTriangulation->Triangle (anI).Get (aN1, aN2, aN3); // get indexes of triangle's points
if (theFace.Orientation() == TopAbs_REVERSED)
{
anOcctTriangulation->Triangle (aTriIter).Get (aN1, aN3, aN2);
}
else
{
anOcctTriangulation->Triangle (aTriIter).Get (aN1, aN2, aN3);
}
// Insert new triangle on these points into output shape data.
myShapeData->InsertTriangle (
theShapeId, aPointIds(aN1), aPointIds(aN2), aPointIds(aN3), MT_ShadedFace);
myShapeData->InsertTriangle (theShapeId, aPointIds(aN1), aPointIds(aN2), aPointIds(aN3), MT_ShadedFace);
}
}

View File

@@ -16,24 +16,22 @@
#ifndef __IVTKOCC_SHAPEMESHER_H__
#define __IVTKOCC_SHAPEMESHER_H__
#include <BRepAdaptor_Surface.hxx>
#include <IVtkOCC_Shape.hxx>
#include <IVtk_IShapeMesher.hxx>
#include <TColgp_Array1OfPnt.hxx>
#include <TColgp_SequenceOfPnt.hxx>
#include <TColStd_Array1OfInteger.hxx>
#include <TopoDS.hxx>
#include <TopoDS_Edge.hxx>
#include <TopoDS_Face.hxx>
#include <TopoDS_Vertex.hxx>
#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
#include <TopTools_ListOfShape.hxx>
#include <TopTools_ShapeMapHasher.hxx>
typedef NCollection_DataMap <TopoDS_Shape, IVtk_MeshType, TopTools_ShapeMapHasher> IVtk_ShapeTypeMap;
typedef NCollection_Sequence <gp_Pnt> IVtk_Polyline;
typedef NCollection_List <IVtk_Polyline> IVtk_PolylineList;
class Prs3d_Drawer;
class IVtkOCC_ShapeMesher;
DEFINE_STANDARD_HANDLE( IVtkOCC_ShapeMesher, IVtk_IShapeMesher )
@@ -47,19 +45,11 @@ DEFINE_STANDARD_HANDLE( IVtkOCC_ShapeMesher, IVtk_IShapeMesher )
class IVtkOCC_ShapeMesher : public IVtk_IShapeMesher
{
public:
IVtkOCC_ShapeMesher (const Standard_Real& theDevCoeff = 0.0001,
const Standard_Real& theDevAngle = 12.0 * M_PI / 180.0,
const Standard_Integer theNbUIsos = 1,
const Standard_Integer theNbVIsos = 1)
: myDevCoeff (theDevCoeff),
myDevAngle (theDevAngle),
myDeflection (0.0)
{
myNbIsos[0] = theNbUIsos;
myNbIsos[1] = theNbVIsos;
}
//! Main constructor.
Standard_EXPORT IVtkOCC_ShapeMesher();
virtual ~IVtkOCC_ShapeMesher() { }
//! Destructor.
Standard_EXPORT virtual ~IVtkOCC_ShapeMesher();
//! Returns absolute deflection used by this algorithm.
//! This value is calculated on the basis of the shape's bounding box.
@@ -71,28 +61,19 @@ public:
//! Returns relative deviation coefficient used by this algorithm.
//! @return relative deviation coefficient
Standard_Real GetDeviationCoeff() const
{
return myDevCoeff;
}
Standard_EXPORT Standard_Real GetDeviationCoeff() const;
//! Returns deviation angle used by this algorithm.
//! This is the maximum allowed angle between the normals to the
//! curve/surface and the normals to polyline/faceted representation.
//! @return deviation angle (in radians)
Standard_Real GetDeviationAngle() const
{
return myDevAngle;
}
Standard_EXPORT Standard_Real GetDeviationAngle() const;
protected:
//! Executes the mesh generation algorithms. To be defined in implementation class.
Standard_EXPORT virtual void internalBuild() Standard_OVERRIDE;
private:
//! Internal method, generates OCCT triangulation starting from TopoDS_Shape
//! @see IVtkOCC_ShapeMesher::addEdge, IVtkOCC_ShapeMesher::addShadedFace
void meshShape();
//! Extracts free vertices from the shape (i.e. those not belonging to any edge)
//! and passes the geometry to IPolyData.
@@ -102,12 +83,6 @@ private:
//! Adds all the edges (free and non-free) to IPolyData.
void addEdges();
//! Adds wireframe representations of all faces to IPolyData.
void addWireFrameFaces();
//! Adds shaded representations of all faces to IPolyData.
void addShadedFaces();
//! Adds the point coordinates, connectivity info and
//! sub-shape ID for the OCCT vertex.
//!
@@ -130,33 +105,22 @@ private:
//! Generates wireframe representation of the given TopoDS_Face object
//! with help of OCCT algorithms. The resulting polylines are passed to IPolyData
//! interface and associated with the given sub-shape ID.
//! @param [in] faceToMesh TopoDS_Face object to build wireframe representation for.
//! @param [in] shapeId The face' sub-shape ID
void addWFFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId);
//! @param [in] theFace TopoDS_Face object to build wireframe representation for
//! @param [in] theShapeId The face' sub-shape ID
//! @param [in] theDeflection curve deflection
void addWFFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId,
const Standard_Real theDeflection);
//! Creates shaded representation of the given TopoDS_Face object
//! starting from OCCT triangulation that should be created in advance.
//! The resulting triangles are passed to IPolyData
//! interface and associated with the given sub-shape ID.
//! @param [in] faceToMesh TopoDS_Face object to build shaded representation for.
//! @param [in] shapeId The face' sub-shape ID
//! @param [in] theFace TopoDS_Face object to build shaded representation for
//! @param [in] theShapeId the face' sub-shape ID
//! @see IVtkOCC_ShapeMesher::meshShape, IVtkOCC_ShapeMesher::addEdge
void addShadedFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId);
//! Internal helper method that unpacks the input arrays of points and
//! connectivity and creates the polyline using IPolyData interface.
//! Optionally, the transformation specified through the last argument
//! can be applied to each point's coordinates (noTransform == true).
//! The polyline is associated with the given sub-shape ID.
void processPolyline (Standard_Integer theNbNodes,
const TColgp_Array1OfPnt& thePoints,
const TColStd_Array1OfInteger& thePointIds,
const IVtk_IdType theOcctId,
bool theNoTransform,
gp_Trsf theTransformation,
const IVtk_MeshType theMeshType);
void addShadedFace (const TopoDS_Face& theFace,
const IVtk_IdType theShapeId);
//! Get the IShape as OCC implementation
const IVtkOCC_Shape::Handle GetShapeObj() const;
@@ -164,11 +128,7 @@ private:
DEFINE_STANDARD_RTTIEXT(IVtkOCC_ShapeMesher,IVtk_IShapeMesher)
private:
IVtk_ShapeTypeMap myEdgesTypes;
Standard_Real myDevCoeff;
Standard_Real myDevAngle;
mutable Standard_Real myDeflection;
Standard_Integer myNbIsos[2];
IVtk_ShapeTypeMap myEdgesTypes;
};
#endif // __IVTKOCC_SHAPEMESHER_H__

View File

@@ -23,12 +23,9 @@
IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_ShapePickerAlgo,IVtk_IShapePickerAlgo)
// Handle implementation
//================================================================
// Function : Constructor
// Purpose :
// Purpose :
//================================================================
IVtkOCC_ShapePickerAlgo::IVtkOCC_ShapePickerAlgo() :
myViewerSelector (new IVtkOCC_ViewerSelector())
@@ -36,7 +33,7 @@ myViewerSelector (new IVtkOCC_ViewerSelector())
//================================================================
// Function : Destructor
// Purpose :
// Purpose :
//================================================================
IVtkOCC_ShapePickerAlgo::~IVtkOCC_ShapePickerAlgo()
{ }
@@ -57,30 +54,29 @@ void IVtkOCC_ShapePickerAlgo::SetView (const IVtk_IView::Handle& theView)
IVtk_SelectionModeList IVtkOCC_ShapePickerAlgo::GetSelectionModes (
const IVtk_IShape::Handle& theShape) const
{
IVtk_SelectionModeList aRes;
if (! theShape.IsNull())
if (theShape.IsNull())
{
// Get shape implementation from shape interface.
Handle(IVtkOCC_Shape) aShapeImpl = Handle(IVtkOCC_Shape)::DownCast(theShape);
// Get selectable object from the shape implementation.
Handle(IVtkOCC_SelectableObject) aSelObj =
Handle(IVtkOCC_SelectableObject)::DownCast(aShapeImpl->GetSelectableObject());
if (!aSelObj.IsNull())
{
IVtk_SelectionMode aSelMode;
for (aSelMode = SM_Shape; aSelMode <= SM_Compound; aSelMode = (IVtk_SelectionMode)(aSelMode + 1))
{
if (myViewerSelector->IsActive (aSelObj, aSelMode))
{
aRes.Append (aSelMode);
}
}
}
return IVtk_SelectionModeList();
}
// Get shape implementation from shape interface.
Handle(IVtkOCC_Shape) aShapeImpl = Handle(IVtkOCC_Shape)::DownCast(theShape);
// Get selectable object from the shape implementation.
Handle(IVtkOCC_SelectableObject) aSelObj = Handle(IVtkOCC_SelectableObject)::DownCast(aShapeImpl->GetSelectableObject());
if (aSelObj.IsNull())
{
return IVtk_SelectionModeList();
}
IVtk_SelectionModeList aRes;
for (IVtk_SelectionMode aSelMode = SM_Shape; aSelMode <= SM_Compound; aSelMode = (IVtk_SelectionMode)(aSelMode + 1))
{
if (myViewerSelector->IsActive (aSelObj, aSelMode))
{
aRes.Append (aSelMode);
}
}
return aRes;
}
@@ -102,8 +98,7 @@ void IVtkOCC_ShapePickerAlgo::SetSelectionMode (const IVtk_IShape::Handle& theSh
// are destroyed when shapes are deactivated...
// Get shape implementation from shape interface.
Handle(IVtkOCC_Shape) aShapeImpl =
Handle(IVtkOCC_Shape)::DownCast(theShape);
Handle(IVtkOCC_Shape) aShapeImpl = Handle(IVtkOCC_Shape)::DownCast(theShape);
// Get selectable object from the shape implementation.
Handle(IVtkOCC_SelectableObject) aSelObj =
@@ -180,11 +175,9 @@ void IVtkOCC_ShapePickerAlgo::SetSelectionMode (const IVtk_ShapePtrList& theShap
const IVtk_SelectionMode theMode,
const bool /*theIsTurnOn*/)
{
IVtk_IShape::Handle aShape;
IVtk_ShapePtrList::Iterator anIt (theShapes);
for (; anIt.More(); anIt.Next())
for (IVtk_ShapePtrList::Iterator anIt (theShapes); anIt.More(); anIt.Next())
{
aShape = anIt.Value();
IVtk_IShape::Handle aShape = anIt.Value();
SetSelectionMode (aShape, theMode);
}
}
@@ -371,8 +364,7 @@ void IVtkOCC_ShapePickerAlgo::RemoveSelectableObject(const IVtk_IShape::Handle&
{
clearPicked();
// Get shape implementation from shape interface.
Handle(IVtkOCC_Shape) aShapeImpl =
Handle(IVtkOCC_Shape)::DownCast(theShape);
Handle(IVtkOCC_Shape) aShapeImpl = Handle(IVtkOCC_Shape)::DownCast(theShape);
// Get selectable object from the shape implementation.
Handle(IVtkOCC_SelectableObject) aSelObj =
@@ -381,4 +373,4 @@ void IVtkOCC_ShapePickerAlgo::RemoveSelectableObject(const IVtk_IShape::Handle&
myViewerSelector->RemoveSelectableObject(aSelObj);
myViewerSelector->Clear();
aShapeImpl->SetSelectableObject(NULL);
}
}

View File

@@ -14,11 +14,11 @@
// commercial license or contractual agreement.
#include <IVtkOCC_ViewerSelector.hxx>
#include <Select3D_SensitiveBox.hxx>
#include <TColgp_Array1OfPnt2d.hxx>
#include <Graphic3d_Camera.hxx>
IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_ViewerSelector,SelectMgr_ViewerSelector)
//============================================================================
@@ -27,8 +27,8 @@ IMPLEMENT_STANDARD_RTTIEXT(IVtkOCC_ViewerSelector,SelectMgr_ViewerSelector)
//============================================================================
IVtkOCC_ViewerSelector::IVtkOCC_ViewerSelector()
: SelectMgr_ViewerSelector(),
myPixTol(2),
myToUpdateTol(Standard_True)
myPixTol(2),
myToUpdateTol(Standard_True)
{
}

View File

@@ -25,7 +25,6 @@
//! @brief Class that implements OCCT selection algorithm.
//!
//! Inspired by StdSelect_ViewerSelector3d class from OCCT 6.5.1
class IVtkOCC_ViewerSelector : public SelectMgr_ViewerSelector
{
public:
@@ -66,4 +65,5 @@ private:
};
DEFINE_STANDARD_HANDLE( IVtkOCC_ViewerSelector, SelectMgr_ViewerSelector )
#endif // __IVTKOCC_VIEWERSELECTOR_H__

View File

@@ -34,9 +34,10 @@ vtkStandardNewMacro(IVtkTools_DisplayModeFilter)
// Purpose:
//============================================================================
IVtkTools_DisplayModeFilter::IVtkTools_DisplayModeFilter()
: myDisplayMode (DM_Wireframe),
myDoDisplaySharedVertices (false),
myDrawFaceBoundaries( false )
: myDisplayMode (DM_Wireframe),
myDoDisplaySharedVertices (false),
myDrawFaceBoundaries (false),
myIsSmoothShading (true)
{
// Filter according to values in subshapes types array.
myIdsArrayName = IVtkVTK_ShapeData::ARRNAME_MESH_TYPES();
@@ -78,6 +79,7 @@ int IVtkTools_DisplayModeFilter::RequestData (vtkInformation *theRequest,
vtkInformationVector *theOutputVector)
{
SetData (myModesDefinition[myDisplayMode]);
myToCopyNormals = myIsSmoothShading && (myDisplayMode == DM_Shading);
return Superclass::RequestData (theRequest, theInputVector, theOutputVector);
}
@@ -184,3 +186,16 @@ void IVtkTools_DisplayModeFilter::SetFaceBoundaryDraw(bool theToDraw)
}
Modified();
}
//============================================================================
// Method: SetSmoothShading
// Purpose:
//============================================================================
void IVtkTools_DisplayModeFilter::SetSmoothShading (bool theIsSmooth)
{
if (myIsSmoothShading != theIsSmooth)
{
myIsSmoothShading = theIsSmooth;
Modified();
}
}

View File

@@ -58,21 +58,26 @@ public:
//! Returns True if drawing Boundary of faces for shading mode is defined.
bool FaceBoundaryDraw() const { return myDrawFaceBoundaries; }
//! Returns TRUE if vertex normals should be included for smooth shading within DM_Shading mode or not.
bool IsSmoothShading() const { return myIsSmoothShading; }
//! Set if vertex normals should be included for smooth shading or not.
void SetSmoothShading (bool theIsSmooth);
protected:
//! Filter cells according to the given set of ids.
virtual int RequestData (vtkInformation *, vtkInformationVector **, vtkInformationVector *);
virtual int RequestData (vtkInformation *, vtkInformationVector **, vtkInformationVector *) Standard_OVERRIDE;
IVtkTools_DisplayModeFilter();
virtual ~IVtkTools_DisplayModeFilter();
protected:
//! Display mode defining mesh types to pass through this filter.
IVtk_DisplayMode myDisplayMode;
IVtk_DisplayMode myDisplayMode; //!< Display mode defining mesh types to pass through this filter
IVtk_IdTypeMap myModesDefinition[2];
bool myDoDisplaySharedVertices;
//! Draw Face boundaries flag is applicable only for shading display mode.
bool myDrawFaceBoundaries;
bool myDrawFaceBoundaries; //!< Draw Face boundaries within shading display mode
bool myIsSmoothShading; //!< include vertex normals for smooth shading or not
};
#ifdef _MSC_VER

View File

@@ -38,10 +38,10 @@ vtkStandardNewMacro(IVtkTools_ShapeDataSource)
//================================================================
// Function : Constructor
// Purpose :
// Purpose :
//================================================================
IVtkTools_ShapeDataSource::IVtkTools_ShapeDataSource()
: myPolyData (new IVtkVTK_ShapeData),
: myPolyData (new IVtkVTK_ShapeData()),
myIsFastTransformMode (Standard_False),
myIsTransformOnly (Standard_False)
{
@@ -51,130 +51,112 @@ IVtkTools_ShapeDataSource::IVtkTools_ShapeDataSource()
//================================================================
// Function : Destructor
// Purpose :
// Purpose :
//================================================================
IVtkTools_ShapeDataSource::~IVtkTools_ShapeDataSource()
{ }
{
//
}
//================================================================
// Function : SetShape
// Purpose :
// Purpose :
//================================================================
void IVtkTools_ShapeDataSource::SetShape (const IVtkOCC_Shape::Handle& theOccShape)
{
if (myIsFastTransformMode && !myOccShape.IsNull() &&
theOccShape->GetShape().IsPartner (myOccShape->GetShape() ) )
{
myIsTransformOnly = Standard_True;
}
else
{
myIsTransformOnly = Standard_False;
}
myIsTransformOnly = myIsFastTransformMode
&& !myOccShape.IsNull()
&& theOccShape->GetShape().IsPartner (myOccShape->GetShape());
myOccShape = theOccShape;
this->Modified();
}
//================================================================
// Function : GetShape
// Purpose :
//================================================================
IVtkOCC_Shape::Handle IVtkTools_ShapeDataSource::GetShape()
{
return myOccShape;
}
//================================================================
// Function : RequestData
// Purpose :
// Purpose :
//================================================================
int IVtkTools_ShapeDataSource::RequestData(vtkInformation *vtkNotUsed(theRequest),
vtkInformationVector **vtkNotUsed(theInputVector),
vtkInformationVector *theOutputVector)
{
vtkSmartPointer<vtkPolyData> aPolyData = vtkPolyData::GetData (theOutputVector);
if (aPolyData.GetPointer() != NULL)
if (aPolyData.GetPointer() == NULL)
{
aPolyData->Allocate();
vtkSmartPointer<vtkPoints> aPts = vtkSmartPointer<vtkPoints>::New();
aPolyData->SetPoints (aPts);
return 1;
}
vtkSmartPointer<vtkPolyData> aTransformedData;
TopoDS_Shape aShape = myOccShape->GetShape();
TopLoc_Location aShapeLoc = aShape.Location();
aPolyData->Allocate();
vtkSmartPointer<vtkPoints> aPts = vtkSmartPointer<vtkPoints>::New();
aPolyData->SetPoints (aPts);
if (myIsTransformOnly)
vtkSmartPointer<vtkPolyData> aTransformedData;
TopoDS_Shape aShape = myOccShape->GetShape();
const TopLoc_Location aShapeLoc = aShape.Location();
if (myIsTransformOnly)
{
vtkSmartPointer<vtkPolyData> aPrevData = myPolyData->getVtkPolyData();
if (!aShapeLoc.IsIdentity())
{
vtkSmartPointer<vtkPolyData> aPrevData = myPolyData->getVtkPolyData();
if ( !aShapeLoc.IsIdentity() )
{
aTransformedData = this->transform (aPrevData, aShapeLoc);
}
else
{
aTransformedData = aPrevData;
}
aTransformedData = this->transform (aPrevData, aShapeLoc);
}
else
{
IVtkOCC_Shape::Handle aShapeWrapperCopy;
if ( myIsFastTransformMode && !aShapeLoc.IsIdentity() )
{
// Reset location before meshing
aShape.Location (TopLoc_Location());
aShapeWrapperCopy = new IVtkOCC_Shape (aShape);
aShapeWrapperCopy->SetId (myOccShape->GetId());
}
else
{
aShapeWrapperCopy = myOccShape;
}
myPolyData = new IVtkVTK_ShapeData;
IVtkOCC_ShapeMesher::Handle aMesher = new IVtkOCC_ShapeMesher;
aMesher->Build (aShapeWrapperCopy, myPolyData);
vtkSmartPointer<vtkPolyData> aMeshData = myPolyData->getVtkPolyData();
if ( myIsFastTransformMode && !aShapeLoc.IsIdentity() )
{
aTransformedData = this->transform (aMeshData, aShapeLoc);
}
else
{
aTransformedData = aMeshData;
}
aTransformedData = aPrevData;
}
}
else
{
IVtkOCC_Shape::Handle aShapeWrapperCopy = myOccShape;
if (myIsFastTransformMode
&& !aShapeLoc.IsIdentity())
{
// Reset location before meshing
aShape.Location (TopLoc_Location());
aShapeWrapperCopy = new IVtkOCC_Shape (aShape);
aShapeWrapperCopy->SetAttributes (myOccShape->Attributes());
aShapeWrapperCopy->SetId (myOccShape->GetId());
}
aPolyData->CopyStructure (aTransformedData); // Copy points and cells
aPolyData->CopyAttributes (aTransformedData); // Copy data arrays (sub-shapes IDs)
// We store the OccShape instance in a IVtkTools_ShapeObject
// wrapper in vtkInformation object of vtkDataObject, then pass it
// to the actors through pipelines, so selection logic can access
// OccShape easily given the actor instance.
IVtkTools_ShapeObject::SetShapeSource (this, aPolyData);
aPolyData->GetAttributes (vtkDataObject::CELL)->SetPedigreeIds (SubShapeIDs());
myPolyData = new IVtkVTK_ShapeData();
IVtkOCC_ShapeMesher::Handle aMesher = new IVtkOCC_ShapeMesher();
aMesher->Build (aShapeWrapperCopy, myPolyData);
vtkSmartPointer<vtkPolyData> aMeshData = myPolyData->getVtkPolyData();
if (myIsFastTransformMode
&& !aShapeLoc.IsIdentity())
{
aTransformedData = this->transform (aMeshData, aShapeLoc);
}
else
{
aTransformedData = aMeshData;
}
}
aPolyData->CopyStructure (aTransformedData); // Copy points and cells
aPolyData->CopyAttributes (aTransformedData); // Copy data arrays (sub-shapes IDs)
// We store the OccShape instance in a IVtkTools_ShapeObject
// wrapper in vtkInformation object of vtkDataObject, then pass it
// to the actors through pipelines, so selection logic can access
// OccShape easily given the actor instance.
IVtkTools_ShapeObject::SetShapeSource (this, aPolyData);
aPolyData->GetAttributes (vtkDataObject::CELL)->SetPedigreeIds (SubShapeIDs());
return 1;
}
//================================================================
// Function : SubShapeIDs
// Purpose :
// Purpose :
//================================================================
vtkSmartPointer<vtkIdTypeArray> IVtkTools_ShapeDataSource::SubShapeIDs()
{
vtkSmartPointer<vtkDataArray> arr =
GetOutput()->GetCellData()->GetArray(IVtkVTK_ShapeData::ARRNAME_SUBSHAPE_IDS());
return vtkSmartPointer<vtkIdTypeArray>(
vtkIdTypeArray::SafeDownCast(arr.GetPointer()) );
vtkSmartPointer<vtkDataArray> anArr = GetOutput()->GetCellData()->GetArray(IVtkVTK_ShapeData::ARRNAME_SUBSHAPE_IDS());
return vtkSmartPointer<vtkIdTypeArray> (vtkIdTypeArray::SafeDownCast (anArr.GetPointer()));
}
//================================================================
// Function : GetId
// Purpose :
// Purpose :
//================================================================
IVtk_IdType IVtkTools_ShapeDataSource::GetId() const
{
@@ -183,16 +165,16 @@ IVtk_IdType IVtkTools_ShapeDataSource::GetId() const
//================================================================
// Function : Contains
// Purpose :
// Purpose :
//================================================================
Standard_Boolean IVtkTools_ShapeDataSource::Contains (const IVtkOCC_Shape::Handle& shape) const
Standard_Boolean IVtkTools_ShapeDataSource::Contains (const IVtkOCC_Shape::Handle& theShape) const
{
return ((myOccShape == shape) ? Standard_True : Standard_False);
return myOccShape == theShape;
}
//================================================================
// Function : transform
// Purpose :
// Purpose :
//================================================================
vtkSmartPointer<vtkPolyData> IVtkTools_ShapeDataSource::transform (vtkPolyData* theSource,
const gp_Trsf& theTrsf) const
@@ -205,10 +187,12 @@ vtkSmartPointer<vtkPolyData> IVtkTools_ShapeDataSource::transform (vtkPolyData*
vtkSmartPointer<vtkTransform> aTransform = vtkSmartPointer<vtkTransform>::New();
vtkSmartPointer<vtkMatrix4x4> aMx = vtkSmartPointer<vtkMatrix4x4>::New();
for (Standard_Integer aRow = 0; aRow < 3; ++aRow)
{
for (Standard_Integer aCol = 0; aCol < 4; ++aCol)
{
aMx->SetElement (aRow, aCol, theTrsf.Value (aRow + 1, aCol + 1) );
}
}
aTransform->SetMatrix (aMx);
vtkSmartPointer<vtkTransformPolyDataFilter> aTrsfFilter

View File

@@ -51,7 +51,8 @@ public: //! @name Initialization
//! Get the source OCCT shape.
//! @return occShape OCCT shape wrapper.
IVtkOCC_Shape::Handle GetShape();
const IVtkOCC_Shape::Handle& GetShape() { return myOccShape; }
inline void FastTransformModeOn() { myIsFastTransformMode = true; }
inline void FastTransformModeOff() { myIsFastTransformMode = false; }
@@ -82,7 +83,7 @@ protected: //! @name Interface to override
//! @param theOutputVector [in] the pointer to output data, that is filled in this method.
virtual int RequestData(vtkInformation* theRequest,
vtkInformationVector** theInputVector,
vtkInformationVector* theOutputVector);
vtkInformationVector* theOutputVector) Standard_OVERRIDE;
protected: //! @name Internals

View File

@@ -39,7 +39,7 @@ class IVtkTools_ShapeDataSource;
//! @class IVtkTools_ShapeObject
//! @brief VTK holder class for OCC shapes to pass them through pipelines.
//!
//! It is descendent of vtkObject (data). Logically it is a one of milestones of VTK pipeline.
//! It is descendant of vtkObject (data). Logically it is a one of milestones of VTK pipeline.
//! It stores data of OCC shape (the OccShape instance) in vtkInformation object of vtkDataObject.
//! Then pass it to the actors through pipelines,
//! so selection logic can access OccShape easily given the actor instance.

View File

@@ -49,7 +49,7 @@ public:
//! Pick entities in the given point.
//! @return Number of detected entities.
int Pick (double theX, double theY, double theZ, vtkRenderer *theRenderer = NULL);
virtual int Pick (double theX, double theY, double theZ, vtkRenderer *theRenderer = NULL) Standard_OVERRIDE;
//! Pick entities in the given rectangle area.
//! @return Number of detected entities.

View File

@@ -21,30 +21,109 @@
#pragma warning(push)
#endif
#include <vtkCellData.h>
#include <vtkFloatArray.h>
#include <vtkGenericCell.h>
#include <vtkIdList.h>
#include <vtkIdTypeArray.h>
#include <vtkInformation.h>
#include <vtkInformationVector.h>
#include <vtkObjectFactory.h>
#include <vtkPointData.h>
#ifdef _MSC_VER
#pragma warning(pop)
#endif
namespace
{
//! Modified version of vtkPolyData::CopyCells() that includes copying of normals.
//! How to ask vtkPolyData::CopyCells() to do that automatically?
static void copyCells (vtkPolyData* theDst,
vtkPolyData* theSrc,
vtkIdList* theIdList)
{
//theDst->CopyCells (theSrc, theIdList);
const vtkIdType aNbPts = theSrc->GetNumberOfPoints();
vtkDataArray* anOldNormals = theSrc->GetPointData()->GetNormals();
if (theDst->GetPoints() == NULL)
{
theDst->SetPoints (vtkSmartPointer<vtkPoints>::New());
}
vtkSmartPointer<vtkIdList> aNewCellPts = vtkSmartPointer<vtkIdList>::New();
vtkSmartPointer<vtkGenericCell> aCell = vtkSmartPointer<vtkGenericCell>::New();
NCollection_Vec3<double> anXYZ;
vtkPointData* aNewPntData = theDst->GetPointData();
vtkCellData* aNewCellData = theDst->GetCellData();
vtkPoints* aNewPoints = theDst->GetPoints();
vtkSmartPointer<vtkFloatArray> aNewNormals;
if (anOldNormals != NULL)
{
aNewNormals = vtkSmartPointer<vtkFloatArray>::New();
aNewNormals->SetName ("Normals");
aNewNormals->SetNumberOfComponents (3);
theDst->GetPointData()->SetNormals (aNewNormals);
}
vtkSmartPointer<vtkIdList> aPntMap = vtkSmartPointer<vtkIdList>::New(); // maps old pt ids into new
aPntMap->SetNumberOfIds (aNbPts);
for (vtkIdType aPntIter = 0; aPntIter < aNbPts; ++aPntIter)
{
aPntMap->SetId (aPntIter, -1);
}
// Filter the cells
for (vtkIdType aCellIter = 0; aCellIter < theIdList->GetNumberOfIds(); ++aCellIter)
{
theSrc->GetCell (theIdList->GetId (aCellIter), aCell);
vtkIdList* aCellPts = aCell->GetPointIds();
const vtkIdType aNbCellPts = aCell->GetNumberOfPoints();
for (vtkIdType aCellPntIter = 0; aCellPntIter < aNbCellPts; ++aCellPntIter)
{
const vtkIdType aPtId = aCellPts->GetId (aCellPntIter);
vtkIdType aNewId = aPntMap->GetId (aPtId);
if (aNewId < 0)
{
theSrc->GetPoint (aPtId, anXYZ.ChangeData());
aNewId = aNewPoints->InsertNextPoint (anXYZ.GetData());
aPntMap->SetId (aPtId, aNewId);
aNewPntData->CopyData (theSrc->GetPointData(), aPtId, aNewId);
if (anOldNormals != NULL)
{
anOldNormals->GetTuple (aPtId, anXYZ.ChangeData());
aNewNormals->InsertNextTuple (anXYZ.GetData());
}
}
aNewCellPts->InsertId (aCellPntIter, aNewId);
}
const vtkIdType aNewCellId = theDst->InsertNextCell (aCell->GetCellType(), aNewCellPts);
aNewCellData->CopyData (theSrc->GetCellData(), theIdList->GetId (aCellIter), aNewCellId);
aNewCellPts->Reset();
}
}
}
vtkStandardNewMacro(IVtkTools_SubPolyDataFilter)
//================================================================
// Function : Constructor
// Purpose :
// Purpose :
//================================================================
IVtkTools_SubPolyDataFilter::IVtkTools_SubPolyDataFilter()
: myIdsArrayName (IVtkVTK_ShapeData::ARRNAME_SUBSHAPE_IDS()),
myDoFiltering (true),
myToCopyNormals (true)
{
myIdsArrayName = IVtkVTK_ShapeData::ARRNAME_SUBSHAPE_IDS();
myDoFiltering = true;
//
}
//================================================================
// Function : Destructor
// Purpose :
// Purpose :
//================================================================
IVtkTools_SubPolyDataFilter::~IVtkTools_SubPolyDataFilter() { }
@@ -70,18 +149,17 @@ int IVtkTools_SubPolyDataFilter::RequestData (vtkInformation *vtkNotUsed(theRequ
if (myDoFiltering)
{
vtkSmartPointer<vtkCellData> aCellData = anInput->GetCellData();
vtkIdType aSize = 0;
vtkSmartPointer<vtkIdTypeArray> aDataArray =
vtkIdTypeArray::SafeDownCast (aCellData->GetArray (myIdsArrayName));
vtkSmartPointer<vtkCellData> anInputCellData = anInput->GetCellData();
vtkSmartPointer<vtkCellData> anOutputCellData = anOutput->GetCellData();
vtkSmartPointer<vtkIdTypeArray> aDataArray = vtkIdTypeArray::SafeDownCast (anInputCellData->GetArray (myIdsArrayName));
// List of cell ids to be passed
vtkSmartPointer<vtkIdList> anIdList = vtkSmartPointer<vtkIdList>::New();
anIdList->Allocate(myIdsSet.Extent()); // Allocate the list of ids
anIdList->Allocate (myIdsSet.Extent()); // Allocate the list of ids
if (aDataArray.GetPointer() != NULL)
const vtkIdType aSize = aDataArray.GetPointer() != NULL ? aDataArray->GetNumberOfTuples() : 0;
if (aSize != 0)
{
aSize = aDataArray->GetNumberOfTuples();
anIdList->Allocate (aSize); // Allocate the list of ids
}
@@ -100,39 +178,41 @@ int IVtkTools_SubPolyDataFilter::RequestData (vtkInformation *vtkNotUsed(theRequ
}
// Copy cells with their points according to the prepared list of cell ids.
anOutput->GetCellData()->AllocateArrays(anInput->GetCellData()->GetNumberOfArrays());
anOutput->Allocate(anInput, anIdList->GetNumberOfIds()); // Allocate output cells
anOutputCellData->AllocateArrays (anInputCellData->GetNumberOfArrays());
anOutput->Allocate (anInput, anIdList->GetNumberOfIds()); // Allocate output cells
// Pass data arrays.
// Create new arrays for output data
vtkSmartPointer<vtkCellData> anInData = anInput->GetCellData();
vtkSmartPointer<vtkCellData> anOutData = anOutput->GetCellData();
vtkSmartPointer<vtkDataArray> anInArr, anOutArr;
for (Standard_Integer anI = 0; anI < anInData->GetNumberOfArrays(); anI++)
for (Standard_Integer anI = 0; anI < anInputCellData->GetNumberOfArrays(); anI++)
{
anInArr = anInData->GetArray (anI);
anOutArr = vtkSmartPointer<vtkDataArray>::Take(
vtkDataArray::CreateDataArray(anInArr->GetDataType()));
anOutArr->SetName(anInArr->GetName());
anOutArr->Allocate(anIdList->GetNumberOfIds() * anInArr->GetNumberOfComponents());
vtkSmartPointer<vtkDataArray> anInArr = anInputCellData->GetArray (anI);
vtkSmartPointer<vtkDataArray> anOutArr = vtkSmartPointer<vtkDataArray>::Take (vtkDataArray::CreateDataArray(anInArr->GetDataType()));
anOutArr->SetName (anInArr->GetName());
anOutArr->Allocate (anIdList->GetNumberOfIds() * anInArr->GetNumberOfComponents());
anOutArr->SetNumberOfTuples (anIdList->GetNumberOfIds());
anOutArr->SetNumberOfComponents (anInArr->GetNumberOfComponents());
anOutData->AddArray(anOutArr);
anOutputCellData->AddArray (anOutArr);
}
// Copy cells with ids from our list.
anOutput->CopyCells (anInput, anIdList);
if (myToCopyNormals)
{
copyCells (anOutput, anInput, anIdList);
}
else
{
anOutput->CopyCells (anInput, anIdList);
}
// Copy filtered arrays data
vtkIdType anOutId, anInId;
for (Standard_Integer anI = 0; anI < anInData->GetNumberOfArrays(); anI++)
for (Standard_Integer anI = 0; anI < anInputCellData->GetNumberOfArrays(); anI++)
{
anInArr = anInData->GetArray (anI);
anOutArr = anOutData->GetArray(anI);
for (anOutId = 0; anOutId < anIdList->GetNumberOfIds(); anOutId++)
vtkSmartPointer<vtkDataArray> anInArr = anInputCellData ->GetArray (anI);
vtkSmartPointer<vtkDataArray> anOutArr = anOutputCellData->GetArray (anI);
for (vtkIdType anOutId = 0; anOutId < anIdList->GetNumberOfIds(); anOutId++)
{
anInId = anIdList->GetId (anOutId);
const vtkIdType anInId = anIdList->GetId (anOutId);
anOutArr->SetTuple (anOutId, anInId, anInArr);
}
}
@@ -148,7 +228,7 @@ int IVtkTools_SubPolyDataFilter::RequestData (vtkInformation *vtkNotUsed(theRequ
//================================================================
// Function : SetDoFiltering
// Purpose :
// Purpose :
//================================================================
void IVtkTools_SubPolyDataFilter::SetDoFiltering (const bool theDoFiltering)
{
@@ -169,12 +249,12 @@ void IVtkTools_SubPolyDataFilter::PrintSelf (std::ostream& theOs, vtkIndent theI
IVtk_IdTypeMap::Iterator anIter(myIdsSet);
while (anIter.More())
{
theOs << " " << anIter.Value();
anIter.Next();
if (anIter.More())
{
theOs << "; ";
}
theOs << " " << anIter.Value();
anIter.Next();
if (anIter.More())
{
theOs << "; ";
}
}
theOs << "}" << "\n";
}
@@ -203,8 +283,7 @@ void IVtkTools_SubPolyDataFilter::SetData (const IVtk_IdTypeMap theSet)
//================================================================
void IVtkTools_SubPolyDataFilter::AddData (const IVtk_IdTypeMap theSet)
{
IVtk_IdTypeMap::Iterator anIt (theSet);
for (; anIt.More(); anIt.Next())
for (IVtk_IdTypeMap::Iterator anIt (theSet); anIt.More(); anIt.Next())
{
if (!myIdsSet.Contains (anIt.Value()))
{
@@ -229,8 +308,7 @@ void IVtkTools_SubPolyDataFilter::SetData (const IVtk_ShapeIdList theIdList)
//================================================================
void IVtkTools_SubPolyDataFilter::AddData (const IVtk_ShapeIdList theIdList)
{
IVtk_ShapeIdList::Iterator anIt (theIdList);
for (; anIt.More(); anIt.Next())
for (IVtk_ShapeIdList::Iterator anIt (theIdList); anIt.More(); anIt.Next())
{
if (!myIdsSet.Contains (anIt.Value()))
{
@@ -239,10 +317,9 @@ void IVtkTools_SubPolyDataFilter::AddData (const IVtk_ShapeIdList theIdList)
}
}
//! Set ids to be passed through this filter.
//================================================================
// Function : SetIdsArrayName
// Purpose :
// Purpose :
//================================================================
void IVtkTools_SubPolyDataFilter::SetIdsArrayName (const char* theArrayName)
{

View File

@@ -60,7 +60,7 @@ public:
protected:
//! @brief Filter cells according to the given set of ids.
//! Note: Data arrays are not passed through if filtering is turned on.
virtual int RequestData(vtkInformation *, vtkInformationVector **, vtkInformationVector *);
virtual int RequestData(vtkInformation *, vtkInformationVector **, vtkInformationVector *) Standard_OVERRIDE;
IVtkTools_SubPolyDataFilter();
virtual ~IVtkTools_SubPolyDataFilter();
@@ -70,6 +70,7 @@ protected:
IVtk_IdTypeMap myIdsSet;
const char* myIdsArrayName;
bool myDoFiltering;
bool myToCopyNormals;
};
#ifdef _MSC_VER

View File

@@ -19,7 +19,9 @@
#include <Standard_WarningsDisable.hxx>
#include <vtkCellData.h>
#include <vtkDoubleArray.h>
#include <vtkFloatArray.h>
#include <vtkIdList.h>
#include <vtkPointData.h>
#include <vtkPoints.h>
#include <vtkPolyData.h>
#include <Standard_WarningsRestore.hxx>
@@ -28,7 +30,7 @@ IMPLEMENT_STANDARD_RTTIEXT(IVtkVTK_ShapeData,IVtk_IShapeData)
//================================================================
// Function : Constructor
// Purpose :
// Purpose :
//================================================================
IVtkVTK_ShapeData::IVtkVTK_ShapeData()
{
@@ -36,6 +38,11 @@ IVtkVTK_ShapeData::IVtkVTK_ShapeData()
myPolyData->Allocate();
myPolyData->SetPoints (vtkSmartPointer<vtkPoints>::New());
myNormals = vtkSmartPointer<vtkFloatArray>::New();
myNormals->SetName ("Normals");
myNormals->SetNumberOfComponents (3);
myPolyData->GetPointData()->SetNormals (myNormals);
mySubShapeIDs = vtkSmartPointer<vtkIdTypeArray>::New();
mySubShapeIDs->SetName (IVtkVTK_ShapeData::ARRNAME_SUBSHAPE_IDS());
mySubShapeIDs->SetNumberOfComponents (1);
@@ -49,25 +56,29 @@ IVtkVTK_ShapeData::IVtkVTK_ShapeData()
//================================================================
// Function : Destructor
// Purpose :
// Purpose :
//================================================================
IVtkVTK_ShapeData::~IVtkVTK_ShapeData()
{ }
//================================================================
// Function : InsertCoordinate
// Purpose :
// Function : InsertPoint
// Purpose :
//================================================================
IVtk_PointId IVtkVTK_ShapeData::InsertCoordinate (double theX,
double theY,
double theZ)
IVtk_PointId IVtkVTK_ShapeData::InsertPoint (const gp_Pnt& thePnt,
const NCollection_Vec3<float>& theNorm)
{
return myPolyData->GetPoints()->InsertNextPoint (theX, theY, theZ);
IVtk_PointId aPointId = myPolyData->GetPoints()->InsertNextPoint (thePnt.X(), thePnt.Y(), thePnt.Z());
if (myNormals.GetPointer() != NULL)
{
myNormals->InsertNextTuple (theNorm.GetData());
}
return aPointId;
}
//================================================================
// Function : InsertVertex
// Purpose :
// Purpose :
//================================================================
void IVtkVTK_ShapeData::InsertVertex (const IVtk_IdType theShapeID,
const IVtk_PointId thePointId,
@@ -80,7 +91,7 @@ void IVtkVTK_ShapeData::InsertVertex (const IVtk_IdType theShapeID,
//================================================================
// Function : InsertLine
// Purpose :
// Purpose :
//================================================================
void IVtkVTK_ShapeData::InsertLine (const IVtk_IdType theShapeID,
const IVtk_PointId thePointId1,
@@ -94,7 +105,7 @@ void IVtkVTK_ShapeData::InsertLine (const IVtk_IdType theShapeID,
//================================================================
// Function : InsertLine
// Purpose :
// Purpose :
//================================================================
void IVtkVTK_ShapeData::InsertLine (const IVtk_IdType theShapeID,
const IVtk_PointIdList* thePointIds,
@@ -119,7 +130,7 @@ void IVtkVTK_ShapeData::InsertLine (const IVtk_IdType theShapeID,
//================================================================
// Function : InsertTriangle
// Purpose :
// Purpose :
//================================================================
void IVtkVTK_ShapeData::InsertTriangle (const IVtk_IdType theShapeID,
const IVtk_PointId thePointId1,

View File

@@ -16,6 +16,8 @@
#ifndef __IVTKVTK_SHAPEDATA_H__
#define __IVTKVTK_SHAPEDATA_H__
#include <gp_Dir.hxx>
#include <gp_Pnt.hxx>
#include <IVtk_IShapeData.hxx>
// prevent disabling some MSVC warning messages by VTK headers
@@ -26,6 +28,7 @@
#include <Standard_WarningsRestore.hxx>
class vtkIdTypeArray;
class vtkFloatArray;
class IVtkVTK_ShapeData;
DEFINE_STANDARD_HANDLE( IVtkVTK_ShapeData, IVtk_IShapeData )
@@ -51,11 +54,11 @@ public:
DEFINE_STANDARD_RTTIEXT(IVtkVTK_ShapeData,IVtk_IShapeData)
//! Insert a coordinate
//! @param [in] theX X coordinate
//! @param [in] theY Y coordinate
//! @param [in] theZ Z coordinate
//! @param [in] thePnt point position
//! @param [in] theNorm point normal
//! @return id of added point
Standard_EXPORT virtual IVtk_PointId InsertCoordinate (double theX, double theY, double theZ) Standard_OVERRIDE;
Standard_EXPORT virtual IVtk_PointId InsertPoint (const gp_Pnt& thePnt,
const NCollection_Vec3<float>& theNorm) Standard_OVERRIDE;
//! Insert a vertex.
//! @param [in] theShapeID id of the subshape to which the vertex belongs.
@@ -121,6 +124,7 @@ private:
private:
vtkSmartPointer< vtkPolyData > myPolyData; //!< Shape geometry as vtkPolyData
vtkSmartPointer< vtkFloatArray > myNormals; //!< vertex normals
vtkSmartPointer< vtkIdTypeArray > mySubShapeIDs; //!< Array of sub-shapes ids
vtkSmartPointer< vtkIdTypeArray > myMeshTypes; //!< Array of type codes of mesh parts
};

View File

@@ -13,7 +13,6 @@
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <IVtkVTK_View.hxx>
// prevent disabling some MSVC warning messages by VTK headers

19
tests/vtk/ivtk/autotriang Normal file
View File

@@ -0,0 +1,19 @@
puts "============"
puts "0032247: VIS, IVtkOCC_ShapeMesher - allow disabling auto-triangulation behavior"
puts "============"
puts ""
pload MODELING VIS
psphere s 1
explode s F
tessellate r s_1 10 10
trinfo r
checktrinfo r -tri 200
ivtkinit
ivtkdefaults -autoTriang 0
ivtkdisplay r
ivtksetdispmode 1
checktrinfo r -tri 200
ivtkdump $imagedir/${casename}.png

View File

@@ -7,9 +7,8 @@ pload MODELING VIS
box b 1 1 1
ivtkinit
ivtkdisplay b
ivtksetdispmode 1
ivtksetboundingdraw 1
ivtkdump $imagedir/${casename}_1.png
ivtksetboundingdraw 0
ivtksetdispmode 1 -faceBoundaryDraw 0 -smoothShading 1
ivtkdump $imagedir/${casename}_2.png
ivtksetdispmode 1 -faceBoundaryDraw 1 -smoothShading 0
ivtkdump $imagedir/${casename}_1.png

View File

@@ -7,7 +7,8 @@ pload MODELING VIS
psphere s 10 15 80
ivtkinit
ivtkdisplay s
ivtksetdispmode 1
ivtksetboundingdraw 1
ivtksetdispmode 1 -faceBoundaryDraw 1 -smoothShading 0
ivtkdump $imagedir/${casename}.png
ivtksetdispmode 1 -faceBoundaryDraw 1 -smoothShading 1
ivtkdump $imagedir/${casename}_smooth.png