OpenCasCade拓扑变换(使用gp_trsf)(转)

一.废话
在OCC中如果要实现一个拓扑(TopoDS_Shape)的变换(平移,(点,轴,面)镜像,旋转,缩放,移位,形状),那么gp_trsf,gp_GTrsf是一个很好的媒介。深入理解其中的含义,可以组合起来使用,实现复杂的拓扑变换功能,要想熟练使用,必须在实践中体会

在此使用到的几何知识可以参考:几何变换之仿射变换

在OpenCaseCade6.8.0源代码中有介绍:

gp_trsf(平移,(点,轴,面)镜像,旋转,缩放,移位)

//! Geometric transformation on a shape.
//! The transformation to be applied is defined as a
//! gp_Trsf transformation, i.e. a transformation which does
//! not modify the underlying geometry of shapes.
//! The transformation is applied to:
//! - all curves which support edges of a shape, and
//! - all surfaces which support its faces.
//! A Transform object provides a framework for:
//! - defining the geometric transformation to be applied,
//! - implementing the transformation algorithm, and
//! - consulting the results.

谷歌翻译:

在3D空间中定义非持久变换。 实现了以下转换:。 平移,旋转,缩放。 关于点,线,平面的对称性。 复杂的转换可以通过使用矩阵“乘”方法组合先前的基本转换来获得。 转换可以表示如下:
//! V1 V2 V3 T XYZ XYZ
//! | a11 a12 a13 a14 | | x | | x'|
//! | a21 a22 a23 a24 | | y | | y'|
//! | a31 a32 a33 a34 | | z | = | z'|
//! | 0 0 0 1 | | 1 | | 1 |
//! 其中{V1,V2,V3}定义转换的矢量部分,T定义转换的平移部分。 这种转换永远不会改变对象的性质。

 

gp_GTrsf(形状变换)

//! Defines a non-persistent transformation in 3D space.
//! This transformation is a general transformation.
//! It can be a Trsf from gp, an affinity, or you can define
//! your own transformation giving the matrix of transformation.
//!
//! With a Gtrsf you can transform only a triplet of coordinates
//! XYZ. It is not possible to transform other geometric objects
//! because these transformations can change the nature of non-
//! elementary geometric objects.
//! The transformation GTrsf can be represented as follow :
//!
//! V1 V2 V3 T XYZ XYZ
//! | a11 a12 a13 a14 | | x | | x'|
//! | a21 a22 a23 a24 | | y | | y'|
//! | a31 a32 a33 a34 | | z | = | z'|
//! | 0 0 0 1 | | 1 | | 1 |
//!
//! where {V1, V2, V3} define the vectorial part of the
//! transformation and T defines the translation part of the
//! transformation.
//! Warning
//! A GTrsf transformation is only applicable to
//! coordinates. Be careful if you apply such a
//! transformation to all points of a geometric object, as
//! this can change the nature of the object and thus
//! render it incoherent!
//! Typically, a circle is transformed into an ellipse by an
//! affinity transformation. To avoid modifying the nature of
//! an object, use a gp_Trsf transformation instead, as
//! objects of this class respect the nature of geometric objects.

谷歌翻译:

在3D空间中定义非持久变换。此转换是一般转换。它可以是来自gp的Trsf,相似性,也可以定义自己的转换以提供转换矩阵。使用Gtrsf,您只能变换坐标XYZ的三元组。无法变换其他几何对象,因为这些变换可以改变非基本几何对象的性质。转换GTrsf可以表示为:
//! V1 V2 V3 T XYZ XYZ
//! | a11 a12 a13 a14 | | x | | x'|
//! | a21 a22 a23 a24 | | y | | y'|
//! | a31 a32 a33 a34 | | z | = | z'|
//! | 0 0 0 1 | | 1 | | 1 |
//!
其中{V1,V2,V3}定义转换的矢量部分,T定义转换的平移部分。
警告
GTrsf转换仅适用于坐标。如果将这样的变换应用于几何对象的所有点,请小心,因为这会改变对象的性质,从而使其变得不连贯!
通常,通过亲和力转换将圆转换为椭圆。为避免修改对象的性质,请改用gp_Trsf转换,因为此类的对象尊重几何对象的性质。

 

下面介绍参考自网络资料,稍有改动,Occ6.8.0版,其它版本可能会有稍许变动。

 

二.拓扑变换的基本描述

 

 

1.BRepBuilderAPI_Transform
(类,Occ标准头文件BRepBuilderAPI_Transform.hxx)

(1) 功能说明:拓扑变换
此对象与gp_Trsf相关联进行变换

(2) 构造函数:

BRepBuilderAPI_Transform(const gp_Trsf& T);
 
BRepBuilderAPI_Transform(const TopoDS_Shape& S, const gp_Trsf& T, const Standard_Boolean Copy = Standard_False);

(3)    参数说明:

T:要进行的变换

S:进行变换的拓扑图形

Copy:是否用副本进行变换

(4)    备注:

Perform是该对象的一个方法。

BRepBuilderAPI_Transform(gp_Trsf T) 与public void Perform(TopoDS_Shape S, bool Copy)
相等于
BRepBuilderAPI_Transform(TopoDS_Shape S, gp_Trsf T, bool Copy)。

(4)    备注:

Perform是该对象的一个方法。

BRepBuilderAPI_Transform(gp_Trsf T) 与public void Perform(TopoDS_Shape S, bool Copy)
相等于
BRepBuilderAPI_Transform(TopoDS_Shape S, gp_Trsf T, bool Copy)。

(5)    实例:

例1:点对称

 OCC源码:

Makes the transformation into a symmetrical transformation.
  //! P is the center of the symmetry.
      void SetMirror (const gp_Pnt& P) ;

  使用示例:

TopoDS_Shape S;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Pnt PntCenterOfTheTransformation = new gp_Pnt(110, 60, 60);
 
theTransformation.SetMirror(PntCenterOfTheTransformation);//点对称镜像
 
BRepBuilderAPI_Transform myBRepTransformation =new BRepBuilderAPI_Transform(S,theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape();  //获得通过镜像转换后的新的拓扑

 

例2:轴对称

OCC源码:

//! Makes the transformation into a symmetrical transformation.
//! A1 is the center of the axial symmetry.
Standard_EXPORT void SetMirror (const gp_Ax1& A1) ;

使用实例:

TopoDS_Shape S ;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Ax1 axe = new gp_Ax1(new gp_Pnt(110, 60, 60), new gp_Dir(0.0, 1.0, 0.0));                   
 
theTransformation.SetMirror(axe);//镜像
 
BRepBuilderAPI_Transform myBRepTransformation =
 
new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape(); //获取通过轴对称转换的新的拓扑

例3:面对称

OCC源代码:

//! Makes the transformation into a symmetrical transformation.
//! A2 is the center of the planar symmetry
//! and defines the plane of symmetry by its origin, "X
//! Direction" and "Y Direction".
Standard_EXPORT   void SetMirror (const gp_Ax2& A2) ;

使用示例:

TopoDS_Shape S = new BRepPrimAPI_MakeWedge(60.0, 100.0, 80.0, 20.0).Shape();        
 
gp_Trsf theTransformation = new OCgp_Trsf();
 
gp_Ax2 axe2 = new gp_Ax2(new gp_Pnt(0, 0, 0), new gp_Dir(1, 0, 0));
 
theTransformation.SetMirror(axe2);//镜像
 
BRepBuilderAPI_Transform myBRepTransformation =
 
new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape();  //获取通过面对称转换的新的拓扑

关于面对称,需要说明一下:

gp_Ax1(3D空间中的一个轴)

gp_Ax2(右手坐标系)

gp_Ax3(左手坐标系)

此示例中使用的是gp_Ax2右手坐标系,面对称会以该定义的坐标系中x轴y轴所构成的面作为对称的面来转换。

例4:旋转变换

OCC源代码:

 //! Changes the transformation into a rotation.
 //! A1 is the rotation axis and Ang is the angular value of the
 //! rotation in radians.
 Standard_EXPORT   void SetRotation (const gp_Ax1& A1, const Standard_Real Ang) ;
  
 
 //! Changes the transformation into a rotation defined by quaternion.
 //! Note that rotation is performed around origin, i.e.
 //! no translation is involved.
 Standard_EXPORT   void SetRotation (const gp_Quaternion& R) ;

使用示例:

TopoDS_Shape S;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Ax1 axe = new gp_Ax1(new gp_Pnt(200, 60, 60), new gp_Dir(0.0, 1.0, 0.0));//指定旋转轴         
 
theTransformation.SetRotation(axe, 30 * System.Math.PI / 180); //旋转角度(单位:弧度)
 
BRepBuilderAPI_Transform myBRepTransformation =
 
new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape();//获取旋转转换的新的拓扑

例5:缩放变换

OCC源代码:

//! Changes the transformation into a scale.
//! P is the center of the scale and S is the scaling value.
//! Raises ConstructionError  If <S> is null.
Standard_EXPORT   void SetScale (const gp_Pnt& P, const Standard_Real S) ;

使用示例:

TopoDS_Shape S;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Pnt theCenterOfScale = new gp_Pnt(100, 60, 60);  //旋转基本点
 
theTransformation.SetScale(theCenterOfScale, 0.3);  //缩放比例
 
BRepBuilderAPI_Transform myBRepTransformation =new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape();//获取缩放转换后的新的拓扑

例6:平移变换

OCC源代码:

//! Changes the transformation into a translation.
//! V is the vector of the translation.
    void SetTranslation (const gp_Vec& V) ;
  
//! Makes the transformation into a translation where the translation vector
//! is the vector (P1, P2) defined from point P1 to point P2.
    void SetTranslation (const gp_Pnt& P1, const gp_Pnt& P2) ;

使用示例:

TopoDS_Shape S;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Vec theVectorOfTranslation = new gp_Vec(-6, -6, 6);  //此处平移向量是带有长度与方向的
 
theTransformation.SetTranslation(theVectorOfTranslation);
 
BRepBuilderAPI_Transform myBRepTransformation =
 
new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape();

例7:移位(Displacement)变换

OCC源代码:

 //! Modifies this transformation so that it transforms the
 //! coordinate system defined by FromSystem1 into the
 //! one defined by ToSystem2. After this modification, this
 //! transformation transforms:
 //! -   the origin of FromSystem1 into the origin of ToSystem2,
 //! -   the "X Direction" of FromSystem1 into the "X
 //! Direction" of ToSystem2,
 //! -   the "Y Direction" of FromSystem1 into the "Y
 //! Direction" of ToSystem2, and
 //! -   the "main Direction" of FromSystem1 into the "main
 //! Direction" of ToSystem2.
 //! Warning
 //! When you know the coordinates of a point in one
 //! coordinate system and you want to express these
 //! coordinates in another one, do not use the
 //! transformation resulting from this function. Use the
 //! transformation that results from SetTransformation instead.
 //! SetDisplacement and SetTransformation create
 //! related transformations: the vectorial part of one is the
 //! inverse of the vectorial part of the other.
 Standard_EXPORT   void SetDisplacement (const gp_Ax3& FromSystem1, const gp_Ax3& ToSystem2) ;

使用示例:

TopoDS_Shape S;
 
gp_Trsf theTransformation = new gp_Trsf();
 
gp_Ax3 ax3_1 = new gp_Ax3(new OCgp_Pnt(0, 0, 0), new gp_Dir(0, 0, 1));  //左手坐标系
 
gp_Ax3 ax3_2 = new OCgp_Ax3(new gp_Pnt(60, 60, 60), new gp_Dir(1, 1, 1));
 
theTransformation.SetDisplacement(ax3_1, ax3_2);
 
BRepBuilderAPI_Transform myBRepTransformation =new BRepBuilderAPI_Transform(S, theTransformation, false);
 
TopoDS_Shape TransformedShape = myBRepTransformation.Shape();
 

例8:组合变换

       功能:可以将上述多个变换组合在一起,组合方式即:每一个gp_Trsf对象相乘即可(OCC提供对应方法与重载的*运算符)

OCC源码:

gp_Trsf Multiplied (const gp_Trsf& T)  const;   //两个变换gp_Trsf相乘的函数
 
 
gp_Trsf operator * (const gp_Trsf& T)  const     //重载的*运算符,可以直接使用两个对象相乘
{
  return Multiplied(T);
}
  
 
  //! Computes the transformation composed with <me> and T.
  //! <me> = <me> * T
Standard_EXPORT   void Multiply (const gp_Trsf& T) ;  //如注释<me> = <me> * T
 
void operator *= (const gp_Trsf& T)                   //重载的*=  运算符
{
  Multiply(T);
}

使用示例:

假如要实现旋转加平移,直接将旋转的gp_Trsf对象与平移的gp_Trsf 对象相乘即可其它操作类似,虽然是相乘但是实际是OCC内部对转换矩阵平移部分与旋转部分做了矩阵运算,构成了一个新的变换矩阵,将旋转部分与平移部分结合到了一起,详细矩阵变化请查阅文章开头仿射变换 文章介绍的各种图形变换的转换矩阵规则与运算。

2.BRepBuilderAPI_GTransform
(类,Occ标准头文件BRepBuilderAPI_GTransform.hxx)

(1) 功能说明:拓扑变换
此对象与gp_GTrsf相关联进行变换

(2) 构造函数:

//! Constructs a framework for applying the geometric
//! transformation T to a shape. Use the function
//! Perform to define the shape to transform.
Standard_EXPORT BRepBuilderAPI_GTransform(const gp_GTrsf& T);
  
//! Constructs a framework for applying the geometric
//! transformation T to a shape, and applies it to the shape S.
//! -   If the transformation T is direct and isometric (i.e. if
//! the determinant of the vectorial part of T is equal to
//! 1.), and if Copy equals false (default value), the
//! resulting shape is the same as the original but with
//! a new location assigned to it.
//! -   In all other cases, the transformation is applied to
//! a duplicate of S.
//! Use the function Shape to access the result.
//! Note: the constructed framework can be reused to
//! apply the same geometric transformation to other
//! shapes: just specify them with the function Perform.
Standard_EXPORT BRepBuilderAPI_GTransform(const TopoDS_Shape& S, const gp_GTrsf& T, const Standard_Boolean Copy = Standard_False);

(3)    参数说明:

T:要进行的变换

S:进行变换的拓扑图形

Copy:是否用副本进行变换

(4)    实例:

例1:变形(deform)变换

OCC源代码:

//! Replaces the vectorial part of this transformation by Matrix.
    void SetVectorialPart (const gp_Mat& Matrix) ;
 
 
//! Replaces the translation part of
//! this transformation by the coordinates of the number triple Coord.
  Standard_EXPORT   void SetTranslationPart (const gp_XYZ& Coord) ;

使用示例:

TopoDS_Shape S;
 
gp_GTrsf theTransformation = new gp_GTrsf();
 
gp_Mat rot = new gp_Mat(1, 0, 0, 0, 0.5, 0, 0, 0, 1.5);  //描述一个三行三列的矩阵,用以替换转换的矢量部分
 
theTransformation.SetVectorialPart(rot);
 
theTransformation.SetTranslationPart(new gp_XYZ(5, 5, 5)); //使用一个给定的坐标系作为转换,即替换原图形的局部坐标系
 
BRepBuilderAPI_GTransform myBRepTransformation =new BRepBuilderAPI_GTransform(S, theTransformation, false);
 
TopoDS_Shape S2 = myBRepTransformation.Shape(); //改变形状以及位置后的拓扑

参考资料:

http://www.cppblog.com/eryar/archive/2015/01/22/209612.html

网络文档资料


————————————————
版权声明:本文为CSDN博主「小哈龙」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/qq_22642239/article/details/102608607

posted @ 2022-08-29 10:27  格美格美  阅读(1258)  评论(0编辑  收藏  举报