Files
envi-code/SourceCode/Code2026/EarthWormCmd/GLTUDlg.cpp
T
gjm 164968b62e chore
把非utf8-bom编码的cpp/h文件改为 utf8 bom 编码, msvc识别utf8编码时,如果不是bom格式的,会使用当前cp_oem来解码.
2026-10-04 00:04:20 +08:00

534 lines
12 KiB
C++

#include "stdafx.h"
#include "GLTUDlg.h"
#include "AecDbEarthWorm.h"
#include "KTCADUtilityEx.h"
#include "AcDbX3dSolid.h"
#include "AecDbX3dGroup.h"
#include "axlock.h"
#include "CCSYDlg.h"
#include "UITools.h"
extern Acad::ErrorStatus AddToModelSpace(AcDbEntity* pEnt,AcDbDatabase* pDb ,bool bClose );
extern CString IDCreate();
IMPLEMENT_DYNAMIC(CGLTUDlg, CDialog)
static void FreeBuffer(AcDbVoidPtrArray& arTextPtrs)
{
AcDbEntity* pEnt = NULL;
while (arTextPtrs.length() > 0)
{
pEnt = (AcDbEntity*)arTextPtrs.first();
arTextPtrs.removeFirst();
DELETE_PTR(pEnt);
}
}
CGLTUDlg::CGLTUDlg(CWnd* pParent /*=NULL*/)
: CDialog(CGLTUDlg::IDD, pParent)
, m_dL1(10)
, m_dL2(3)
, m_dAngle(90)
, m_bOnAllEw(FALSE)
, m_nPos(0)
, m_idxRoom(0)
, m_dL4(5)
, m_dA2(90)
{
m_pRectCell = new AcDbPolyline;
m_pRectCell->addVertexAt(0, AcGePoint2d::kOrigin);
m_pRectCell->addVertexAt(1, AcGePoint2d(1, 0));
m_pRectCell->addVertexAt(1, AcGePoint2d(1, 1));
m_pRectCell->addVertexAt(1, AcGePoint2d(0, 1));
m_pRectCell->setColorIndex(6);
m_pRectCell->setClosed(Adesk::kTrue);
m_pRectCell->setConstantWidth(0.1);
UIDataCache::Read(_T("%d%d%d%i%i%d%i%s"), _T("CGLTUDlg")
, &m_dL1 , &m_dL2 , &m_dAngle
, &m_bOnAllEw, &m_nPos , &m_dL4
, &m_idxRoom , &m_sCrossSectionScr );
m_nPos = 0;
}
CGLTUDlg::~CGLTUDlg()
{
}
void CGLTUDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
DDX_Text(pDX, IDC_EDIT1, m_dL1);
DDX_Text(pDX, IDC_EDIT2, m_dL2);
DDX_Text(pDX, IDC_EDIT10, m_dAngle);
DDX_Check(pDX, IDC_CHECK1, m_bOnAllEw);
DDX_Radio(pDX, IDC_RADIO2, m_nPos);
DDX_Control(pDX, IDC_STATIC_EW, m_wndViewCtrl);
DDX_Text(pDX, IDC_EDIT34, m_dL4);
DDX_Text(pDX, IDC_EDIT35, m_dA2);
}
BEGIN_MESSAGE_MAP(CGLTUDlg, CDialog)
ON_BN_CLICKED(IDOK, &CGLTUDlg::OnBnClickedOk)
ON_MESSAGE(WM_VIEW_LBUTTONDOWN, &CGLTUDlg::OnViewLButtonDown)
ON_BN_CLICKED(IDC_BUTTON1, &CGLTUDlg::OnBnClickedButton1)
END_MESSAGE_MAP()
BOOL CGLTUDlg::OnInitDialog()
{
CDialog::OnInitDialog();
// 子类化控件对象
if (!m_wndViewCtrl.SubclassDlgItem(IDC_STATIC_EW, this))
{
// 错误时,结束对话框
EndDialog(IDCANCEL);
return FALSE;
}
if (m_dA2 < 1.e-3)
m_dA2 = m_dAngle;
ShowEarthWorm();
UpdateData(FALSE);
return TRUE;
}
void CGLTUDlg::ShowEarthWorm()
{
m_wndViewCtrl.clearAll();
m_wndViewCtrl.init(true);
m_wndViewCtrl.SetOrbitFlag(OBF_PAN | OBF_ZOOM | OBF_COTE);
AecDbEarthWorm worm;
worm.SetCrossSectionScr(m_sCrossSectionScr);
worm.SetChamferInter(100.0f);
ESection eType = eRect;
AcGePoint2dArray arDatas;
eType = worm.ExtractEarthWormScr(arDatas);
AcGeLineSeg3d ln;
AcGePoint3d pt2(1000.0,0,0);
ln.set(AcGePoint3d::kOrigin,pt2);
AcDbRegion* pEWRegion = worm.CreateSectionRegion(ln,eType,arDatas);
if (pEWRegion != NULL)
{
AcDbExtents exts;
pEWRegion->getGeomExtents(exts);
AcGeMatrix3d xform;
xform.setToScaling(0.95);
pEWRegion->transformBy(xform);
m_wndViewCtrl.InitFromCurrentView2D(exts,true);
AcDbVoidPtrArray arr;
int rooms = worm.CreateSectionRoomRegion(ln, eType, arDatas, arr);
AcDbEntity* pEnt = NULL;
AcDbVoidPtrArray arr2;
worm.CreateSectionRoomAddition(ln,eType,arr2);
for (int i = 0; i < arr2.length(); i++)
{
pEnt = (AcDbEntity*)arr2.at(i);
m_wndViewCtrl.Add(pEnt);
}
m_wndViewCtrl.Add(pEWRegion);
m_wndViewCtrl.view()->invalidate();
m_wndViewCtrl.Invalidate();
m_wndViewCtrl.RedrawWindow();
}
}
void CGLTUDlg::OnBnClickedOk()
{
UpdateData();
if (m_dAngle - 90.0 > 1.e-10 || m_dAngle < 10.0)
{
AfxMessageBox(_T("底角必须小于等于90度!且大于10度"));
return;
}
if (m_dA2 - 90.0 > 1.e-10 || m_dA2 < 10.0)
{
AfxMessageBox(_T("底角必须小于等于90度!且大于10度"));
return;
}
if (sin(m_dAngle * PI / 180.0) < 1.e-10)
{
AfxMessageBox(_T("底角必须小于等于90度!且大于0"));
return;
}
if (sin(m_dA2 * PI / 180.0) < 1.e-10)
{
AfxMessageBox(_T("底角必须小于等于90度!且大于0"));
return;
}
double dHX = m_dL1 - m_dL2 * cos(m_dAngle * PI / 180.0) / sin(m_dAngle * PI / 180.0) - m_dL2 * cos(m_dA2 * PI / 180.0) / sin(m_dA2 * PI / 180.0);
if (dHX < 1.0)
{
AfxMessageBox(_T("在当前角度下,L1 尺寸太小,无法创建下凸出!"));
return;
}
UIDataCache::Write(_T("%d%d%d%i%i%d%i%s"), _T("CGLTUDlg")
, &m_dL1 , &m_dL2 , &m_dAngle
, &m_bOnAllEw, &m_nPos
, &m_dL4
, &m_idxRoom
, &m_sCrossSectionScr );
OnOK();
}
int CGLTUDlg::GetX3dSolidRecs(AecDbX3dGroup*& pGroup)
{
//_T("RECT:3900x3600|2900x3600|400x300|EXT:...");//EXT为扩充字段
AecDbEarthWorm worm;
worm.SetCrossSectionScr(m_sCrossSectionScr);
worm.SetChamferInter(100.0);
ESection eType = eRect;
AcGePoint2dArray arDatas;
eType = worm.ExtractEarthWormScr(arDatas);
//外壁厚,内隔壁厚
double dOutW = 0.0,dIntW = 0.0;
if (arDatas.length() > 0)
{
dOutW = arDatas.last().x;
dIntW = arDatas.last().y;
}
//总高度
double dHeight = arDatas.first().y;
dHeight += 2 * arDatas.last().x;
//底部壁厚增加
double dBomAdd = worm.GetBomThickAdd();
//总宽度
double dWidth = 0.0;
for (int i = 0;i < arDatas.length()-1;i++)
{
dWidth += arDatas.at(i).x;
}
dWidth += (arDatas.length() - 2) * dIntW;
dWidth += dOutW * 2.0;
double dWY = 0.0;
AcGeVector3d vtZ;
AcGePoint3d ptOrg;
if (m_bOnAllEw)
{
dWY = dWidth;//包括壁厚
switch(m_nPos)
{
case 0://上
{
vtZ.set(0,0,1);
ptOrg.set(m_dL4 + m_dL1 / 2.0,0,dHeight / 2.0);
break;
}
case 1://下
{
vtZ.set(0,0,-1);
ptOrg.set(m_dL4 + m_dL1 / 2.0,0,-dHeight / 2.0);
break;
}
case 2://左
{
vtZ.set(0,1,0);
ptOrg.set(m_dL4 + m_dL1 / 2.0,dWidth / 2.0,0.0);
dWY = dHeight;
break;
}
case 3://右
{
vtZ.set(0,-1,0);
ptOrg.set(m_dL4 + m_dL1 / 2.0,-dWidth / 2.0,0.0);
dWY = dHeight;
break;
}
default:
break;
}
}
else
{
AcArray<ERoom> arRooms;
ERoom room;
AcGePoint2d ptThick;
AcGeLineSeg3d ln(AcGePoint3d::kOrigin,AcGePoint3d(10.0,0.0,0));
worm.GetSectionRoomsTo(ln,arRooms,ptThick);
room = arRooms.at(m_idxRoom);
switch(m_nPos)
{
case 0://上
{
dWY = room.ptGe[0].distanceTo(room.ptGe[1]) + 2.0 * dOutW;
vtZ.set(0,0,1);
Midpoint(room.ptGe[2],room.ptGe[3],ptOrg);
ptOrg.z = dHeight / 2.0;
ptOrg.x = m_dL4 + m_dL1 / 2.0;
break;
}
case 1://下
{
dWY = room.ptGe[0].distanceTo(room.ptGe[1]) + 2.0 * dOutW;
vtZ.set(0,0,-1);
Midpoint(room.ptGe[0],room.ptGe[1],ptOrg);
ptOrg.z = -dHeight / 2.0;;
ptOrg.x = m_dL4 + m_dL1 / 2.0;
break;
}
case 2://左
{
vtZ.set(0,1,0);
ptOrg.set(m_dL4 + m_dL1 / 2.0,dWidth / 2.0,0.0);
dWY = dHeight;
break;
}
case 3://右
{
vtZ.set(0,-1,0);
ptOrg.set(m_dL4 + m_dL1 / 2.0,-dWidth / 2.0,0.0);
dWY = dHeight;
break;
}
default:
{
return 0;
break;
}
}
}
if (pGroup != NULL)
{
pGroup->RemoveAll3dSolidRec();
}
else
{
pGroup = new AecDbX3dGroup;
}
AcDbX3dSolid* pXSolid = NULL;
//外侧
X3dSolidRec rec;
if ( fabs(m_dAngle - m_dA2) < 1.e-3)
{
if (m_nPos == 2 || m_nPos == 3)
{
ptOrg.z -= 0.5 * dBomAdd;
dWY += dBomAdd;
}
//LxWxHxAng
pXSolid = new AcDbX3dSolid;
pXSolid->Create(AcDbX3dSolid::kQPyramid,ptOrg,vtZ,4,m_dL1 + 2.0 * dOutW / sin(m_dAngle * PI / 180.0),dWY,m_dL2,m_dAngle * PI / 180.0);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolUnite;
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
if ( m_nPos == 2 || m_nPos == 3)
{
ptOrg.z += 0.5 * dBomAdd;
dWY -= dBomAdd;
}
//挖去 四方台 LxWxHxAng
pXSolid = new AcDbX3dSolid;
pXSolid->Create(AcDbX3dSolid::kQPyramid,ptOrg,vtZ,4,m_dL1,dWY - 2.0 * dOutW,m_dL2 - dOutW,m_dAngle * PI / 180.0);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolSubtract;
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
//skin
pXSolid = new AcDbX3dSolid;
AcGePoint3d ptOrg2 = ptOrg + vtZ * ( ( m_dL2 - dOutW ) * 0.5 + 0.5 * dOutW );
pXSolid->Create(AcDbX3dSolid::kQPyramid,ptOrg2,vtZ,4,m_dL1,dWY - 2.0 * dOutW,dOutW,m_dAngle * PI / 180.0);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolIntersect;//剖开用
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
}
else//梯形
{
if (m_nPos == 2 || m_nPos == 3)
{
ptOrg.z -= 0.5 * dBomAdd;
dWY += dBomAdd;
}
pXSolid = new AcDbX3dSolid;
pXSolid->Create(AcDbX3dSolid::kWPyramid,ptOrg,vtZ,5,m_dL1 + dOutW / sin(m_dAngle * PI / 180.0) + dOutW / sin(m_dA2 * PI / 180.0),dWY,m_dL2,m_dAngle * PI / 180.0,m_dA2 * PI / 180.0);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolUnite;
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
if (m_nPos == 2 || m_nPos == 3)
{
ptOrg.z += 0.5 * dBomAdd;
dWY -= dBomAdd;
}
//挖去
pXSolid = new AcDbX3dSolid;
pXSolid->Create(AcDbX3dSolid::kWPyramid,ptOrg,vtZ,5,m_dL1,dWY - 2.0 * dOutW,m_dL2 - dOutW,m_dAngle * PI / 180.0,m_dA2 * PI / 180.0);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolSubtract;
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
//skin
}
//管廊上开口
pXSolid = new AcDbX3dSolid;
pXSolid->Create(AcDbX3dSolid::kBox,ptOrg,vtZ,3,m_dL1,dWY - 2.0 * dOutW,dOutW);
pXSolid->AddMove(-vtZ * dOutW * 0.5);
rec.pXSolid = pXSolid;
rec.bType = AcDb::kBoolSubtract;
_tcscpy(rec.szLockId,IDCreate());
pGroup->AddX3dSolidRec(rec);
pGroup->SetOrgPoint( ptOrg );
pGroup->SetAxis(X,AcGeVector3d::kXAxis);
pGroup->SetAxis(Y,AcGeVector3d::kYAxis);
pGroup->SetAxis(Z,AcGeVector3d::kZAxis);
//序列化BIM数据
pGroup->GetSpecialtyData()->SetAt(_T("m_dL1"),m_dL1);
pGroup->GetSpecialtyData()->SetAt(_T("m_dL2"),m_dL2);
pGroup->GetSpecialtyData()->SetAt(_T("m_dL4"),m_dL4);
pGroup->GetSpecialtyData()->SetAt(_T("m_dAngle"),m_dAngle);
pGroup->GetSpecialtyData()->SetAt(_T("m_dA2"),m_dA2);
pGroup->GetSpecialtyData()->SetAt(_T("m_bOnAllEw"),m_bOnAllEw);
pGroup->GetSpecialtyData()->SetAt(_T("m_nPos"),m_nPos);
pGroup->GetSpecialtyData()->SetAt(_T("m_idxRoom"),m_idxRoom);
pGroup->GetSpecialtyData()->SetAt(_T("m_sCrossSectionScr"),m_sCrossSectionScr);
return TRUE;
}
LRESULT CGLTUDlg::OnViewLButtonDown(WPARAM wp, LPARAM lp)
{
AcGePoint3d* pPt = (AcGePoint3d*)lp;
pPt->z = 0.0;
//判断 点落在 room 内
AecDbEarthWorm worm;
worm.SetCrossSectionScr(m_sCrossSectionScr);
worm.SetChamferInter(100.0);
ESection eType = eRect;
AcGePoint2dArray arDatas;
eType = worm.ExtractEarthWormScr(arDatas);
AcGeLineSeg3d ln;
AcGePoint3d pt2(1000.0, 0, 0);
ln.set(AcGePoint3d::kOrigin, pt2);
AcGePoint3d ptGe[4];
AcDbVoidPtrArray arRegPtrs;
int nRooms = worm.CreateSectionRoomRegion(ln, eType, arDatas, arRegPtrs);
if (nRooms > 0)
{
AcDbRegion* pReg = NULL;
for (int i = 0; i < arRegPtrs.length(); i++)
{
pReg = (AcDbRegion*)arRegPtrs.at(i);
if (pReg != NULL)
{
AcDbExtents ext;
pReg->getGeomExtents(ext);
ptGe[0] = ext.minPoint();
ptGe[1] = ptGe[0];
ptGe[1].x = ext.maxPoint().x;
ptGe[2] = ext.maxPoint();
ptGe[3] = ptGe[0];
ptGe[3].y = ext.maxPoint().y;
if (KTCADUtilityEx::IsPointInBoundary(*pPt, ptGe[0], ptGe[2]))
{
m_idxRoom = i;
AcGsView* pView = m_wndViewCtrl.view();
AcGsModel* pModel = m_wndViewCtrl.model();
if (pView != NULL)
{
if (m_pRectCell != NULL)
pView->erase(m_pRectCell);
}
if (m_pRectCell != NULL)
{
for (int i = 0; i < 4; i++)
{
m_pRectCell->setPointAt(i, ptGe[i].convert2d(AcGePlane::kXYPlane));
}
}
if (pView != NULL)
{
pView->add(m_pRectCell, pModel);
}
break;
}
}
}
if (m_idxRoom == -1)
{
m_pRectCell->setPointAt(0, AcGePoint2d::kOrigin);
m_pRectCell->setPointAt(1, AcGePoint2d(1, 0));
m_pRectCell->setPointAt(2, AcGePoint2d(1, 1));
m_pRectCell->setPointAt(3, AcGePoint2d(0, 1));
}
FreeBuffer(arRegPtrs);
m_wndViewCtrl.view()->invalidate();
m_wndViewCtrl.RedrawWindow();
}
return 0L;
}
void CGLTUDlg::OnBnClickedButton1()
{
//尺寸示意图
CCCSYDlg dlg;
dlg.SetBmpFileName(_T("GLTU.bmp"));
dlg.DoModal();
}