You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
AppFlow/FITK_Component/FITKGeoCompOCC/FITKOCCTransformation.cpp

249 lines
8.0 KiB
C++

#include "FITKOCCTransformation.h"
#include "FITK_Interface/FITKInterfaceGeometry/FITKGeoEnum.h"
#include "FITK_Interface/FITKInterfaceGeometry/FITKVirtualTopoManager.h"
#include "FITKOCCVirtualTopoCreator.h"
#include "FITK_Kernel/FITKAppFramework/FITKAppFramework.h"
#include "FITK_Kernel/FITKAppFramework/FITKGlobalData.h"
#include "FITK_Interface/FITKInterfaceGeometry/FITKGeoCommandList.h"
#include "FITK_Interface/FITKInterfaceGeometry/FITKGeoInterfaceFactory.h"
#include "FITK_Interface/FITKInterfaceGeometry/FITKAbsGeoModelSurface.h"
#include <TopoDS.hxx>
#include <TopoDS_Shape.hxx>
#include <TopoDS_Edge.hxx>
#include <gp_Trsf.hxx>
#include <gp_GTrsf.hxx>
#include <BRepBuilderAPI_Transform.hxx>
#include <gp_Ax1.hxx>
#include <TopLoc_Location.hxx>
#include <Precision.hxx>
#include <BRepBuilderAPI_GTransform.hxx>
namespace OCC {
// 构造函数
FITKOCCModelTransform::FITKOCCModelTransform() :OCCShapeAgent(this)
{
_shapeAgent = _occShapeAgent;
}
// 更新数据
bool FITKOCCModelTransform::update()
{
if (m_SourceShape.isNull()) return false;
auto geoCmdList = FITKGLODATA->getGeometryData<Interface::FITKGeoCommandList>();
auto cmd = geoCmdList->getDataByID(m_SourceShape.CmdId);
if (cmd == nullptr) return false;
auto agent = dynamic_cast<OCC::FITKAbstractOCCModel*>(cmd->getShapeAgent());
if (agent == nullptr) return false;
TopoDS_Shape* shape = agent->getShape();
if (shape->IsNull()) return false;
try {
gp_Trsf trans;
trans.SetTranslation(gp_Vec(m_Vector[0], m_Vector[1], m_Vector[2]));
auto newShape = shape->Located(shape->Location() * trans);
_occShapeAgent->updateShape(newShape);
}
catch (...)
{
printLog(tr("Failed to transform!"), 3);
return false;
}
return true;
}
// 构造函数
FITKOCCModelTransformByTwoPoints::FITKOCCModelTransformByTwoPoints() :OCCShapeAgent(this)
{
_shapeAgent = _occShapeAgent;
}
// 更新数据
bool FITKOCCModelTransformByTwoPoints::update()
{
if (m_SourceShape.isNull()) return false;
auto geoCmdList = FITKGLODATA->getGeometryData<Interface::FITKGeoCommandList>();
auto cmd = geoCmdList->getDataByID(m_SourceShape.CmdId);
if (cmd == nullptr) return false;
auto agent = dynamic_cast<OCC::FITKAbstractOCCModel*>(cmd->getShapeAgent());
if (agent == nullptr) return false;
TopoDS_Shape* shape = agent->getShape();
if (shape->IsNull()) return false;
m_Vector[0] = m_EndPoint[0] - m_StartPoint[0];
m_Vector[1] = m_EndPoint[1] - m_StartPoint[1];
m_Vector[2] = m_EndPoint[2] - m_StartPoint[2];
try {
gp_Trsf trans;
trans.SetTranslation(gp_Vec(m_Vector[0], m_Vector[1], m_Vector[2]));
auto newShape = shape->Located(shape->Location() * trans);
_occShapeAgent->updateShape(newShape);
}
catch (...)
{
printLog(tr("Failed to transform!"), 3);
return false;
}
return true;
}
// 构造函数
FITKOCCModelTransformByDirAndDis::FITKOCCModelTransformByDirAndDis() :OCCShapeAgent(this)
{
_shapeAgent = _occShapeAgent;
}
// 更新数据
bool FITKOCCModelTransformByDirAndDis::update()
{
if (m_SourceShape.isNull()) return false;
auto geoCmdList = FITKGLODATA->getGeometryData<Interface::FITKGeoCommandList>();
auto cmd = geoCmdList->getDataByID(m_SourceShape.CmdId);
if (cmd == nullptr) return false;
auto agent = dynamic_cast<OCC::FITKAbstractOCCModel*>(cmd->getShapeAgent());
if (agent == nullptr) return false;
TopoDS_Shape* shape = agent->getShape();
if (shape->IsNull()) return false;
gp_Vec vec(m_Direction[0], m_Direction[1], m_Direction[2]);
auto mag = vec.Magnitude();
if (mag <= Precision::Confusion()) {
printLog(tr("The direction cannot be zero vector!"), 3);
return false;
}
vec = m_Distance / mag * vec;
m_Vector = { vec.X(), vec.Y(), vec.Z() };
try {
gp_Trsf trans;
trans.SetTranslation(vec);
auto newShape = shape->Located(shape->Location() * trans);
_occShapeAgent->updateShape(newShape);
}
catch (...)
{
printLog(tr("Failed to transform!"), 3);
return false;
}
return true;
}
// 构造函数
FITKOCCModelRotate::FITKOCCModelRotate() :OCCShapeAgent(this)
{
_shapeAgent = _occShapeAgent;
}
// 更新数据
bool FITKOCCModelRotate::update()
{
if (m_SourceShape.isNull()) return false;
auto geoCmdList = FITKGLODATA->getGeometryData<Interface::FITKGeoCommandList>();
auto cmd = geoCmdList->getDataByID(m_SourceShape.CmdId);
if (cmd == nullptr) return false;
auto agent = dynamic_cast<OCC::FITKAbstractOCCModel*>(cmd->getShapeAgent());
if (agent == nullptr) return false;
TopoDS_Shape* shape = agent->getShape();
if (shape->IsNull()) return false;
try {
gp_Trsf trans;
gp_Ax1 rotateAxis(
gp_Pnt(m_AxisStartPoint[0], m_AxisStartPoint[1], m_AxisStartPoint[2]),
gp_Dir(m_AxisEndPoint[0] - m_AxisStartPoint[0], m_AxisEndPoint[1] - m_AxisStartPoint[1], m_AxisEndPoint[2] - m_AxisStartPoint[2])
);
trans.SetRotation(rotateAxis, m_Angle);
auto newShape = shape->Located(shape->Location() * trans);
_occShapeAgent->updateShape(newShape);
}
catch (...)
{
printLog(tr("Failed to transform!"), 3);
return false;
}
return true;
}
// 构造函数
FITKOCCModelScale::FITKOCCModelScale() :OCCShapeAgent(this)
{
_shapeAgent = _occShapeAgent;
}
// 更新数据
bool FITKOCCModelScale::update()
{
if (m_SourceShape.isNull()) return false;
auto geoCmdList = FITKGLODATA->getGeometryData<Interface::FITKGeoCommandList>();
auto cmd = geoCmdList->getDataByID(m_SourceShape.CmdId);
if (cmd == nullptr) return false;
auto agent = dynamic_cast<OCC::FITKAbstractOCCModel*>(cmd->getShapeAgent());
if (agent == nullptr) return false;
TopoDS_Shape* shape = agent->getShape();
if (shape->IsNull()) return false;
try {
// 如果基准点不在原点的话需要进行两次平移操作
bool isOriginBase = (std::abs(m_BasePoint[0]) <= Precision::Confusion()) &&
(std::abs(m_BasePoint[1]) <= Precision::Confusion()) &&
(std::abs(m_BasePoint[2]) <= Precision::Confusion());
TopoDS_Shape newShape = *shape;
// 平移基准点到原点
if (!isOriginBase) {
gp_Trsf trsf;
trsf.SetTranslation(gp_Vec(-m_BasePoint[0], -m_BasePoint[1], -m_BasePoint[2]));
newShape = newShape.Located(newShape.Location() * trsf);
}
// 进行缩放
gp_GTrsf gtrsf;
gtrsf.SetValue(1, 1, m_Factors[0]);
gtrsf.SetValue(2, 2, m_Factors[1]);
gtrsf.SetValue(3, 3, m_Factors[2]);
BRepBuilderAPI_GTransform transform(newShape, gtrsf);
newShape = transform.Shape();
// 从原点移动到基准点
if (!isOriginBase) {
gp_Trsf trsf;
trsf.SetTranslation(gp_Vec(m_BasePoint[0], m_BasePoint[1], m_BasePoint[2]));
newShape = newShape.Located(newShape.Location() * trsf);
}
//auto newShape = shape->Located(shape->Location() * trans);
_occShapeAgent->updateShape(newShape);
}
catch (...)
{
printLog(tr("Failed to scale!"), 3);
return false;
}
return true;
}
}