#include "stdafx.h" #include "THImpHvacDuct.h" #include "TDbInterfaceMsgWrite.h" #include "TDbPipeBase.h" #include "math.h" #include "dbelipse.h" #include "TDbHvacEquipment.h" using namespace TDb; extern AcGePlane GetStdPrjPlan( const AcGePoint3d &ptOnPlan ); THImpHvacDuct::THImpHvacDuct() { // 初始化 m_pOwnerEnt = NULL; } THImpHvacDuct::THImpHvacDuct(TDbPipeBase* pOwner) { // 初始化 m_pOwnerEnt = pOwner; m_pXDataMap = pOwner->GetSpecialtyData(); } THImpHvacDuct::~THImpHvacDuct() { } Acad::ErrorStatus THImpHvacDuct::getClassID(CLSID* pClsid) const { // #if (ADS < 16) // // {C7DFDF6A-A5F2-4add-ADCC-7AC0675AB6E2} // CLSID CLSID_PipeBaseEntity = {0xC7DFDF6B, 0xA5F2, 0x4ADE, { 0xAD, 0xCC, 0x7A, 0xC0, 0x67, 0x5A, 0xB6, 0xE2 }}; // #endif // // #if (ADS == 16) // // {C7DFDF6A-A5F2-4add-ADCC-7AC0675AB6E3} // CLSID CLSID_PipeBaseEntity = {0xC7DFDF6B, 0xA5F2, 0x4ADE, { 0xAD, 0xCC, 0x7A, 0xC0, 0x67, 0x5A, 0xB6, 0xE3 }}; // #endif // // #if (ADS == 17) // // {C7DFDF6A-A5F2-4add-ADCC-7AC0675AB6E4} // CLSID CLSID_PipeBaseEntity = {0xC7DFDF6B, 0xA5F2, 0x4ADE, { 0xAD, 0xCC, 0x7A, 0xC0, 0x67, 0x5A, 0xB6, 0xE4 }}; // #endif // // #if (ADS == 18) // // {C7DFDF6A-A5F2-4add-ADCC-7AC0675AB6E5} // CLSID CLSID_PipeBaseEntity = {0xC7DFDF6B, 0xA5F2, 0x4ADE, { 0xAD, 0xCC, 0x7A, 0xC0, 0x67, 0x5A, 0xB6, 0xE5 }}; // #endif // // #if (ADS == 19) // // {C7DFDF6A-A5F2-4add-ADCC-7AC0675AB6E5} // CLSID CLSID_PipeBaseEntity = {0xC7DFDF6B, 0xA5F2, 0x4ADE, { 0xAD, 0xCC, 0x7A, 0xC0, 0x67, 0x5A, 0xB6, 0xE5 }}; // #endif return Acad::eOk; } BOOL THImpHvacDuct::OPMInfo(LPCTSTR pszName, TDb::OPMInfo* pInfo) { ASSERT(NULL != pszName && NULL != pInfo && NULL != m_pXDataMap); if (0 == _tcsicmp(pszName, HVAC_SectType)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("矩形")); pInfo->parlValues->Add(TDb::eRectangular); pInfo->parsValues->Add(_T("圆形")); pInfo->parlValues->Add(TDb::eCircular); } return TRUE; } if (0 == _tcsicmp(pszName, HVAC_DrawType)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("旧标准")); pInfo->parlValues->Add(TDb::eOldStyle); pInfo->parsValues->Add(_T("新标准进风")); pInfo->parlValues->Add(TDb::eNewImmit); pInfo->parsValues->Add(_T("新标准排风")); pInfo->parlValues->Add(TDb::eNewEject); } return TRUE; } if (0 == _tcsicmp(pszName, HVAC_HasBaseLine)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("隐藏")); pInfo->parlValues->Add(0); pInfo->parsValues->Add(_T("显示")); pInfo->parlValues->Add(1); } return TRUE; } if (0 == _tcsicmp(pszName, HVAC_HasLining)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("隐藏")); pInfo->parlValues->Add(0); pInfo->parsValues->Add(_T("显示")); pInfo->parlValues->Add(1); } return TRUE; } if (0 == _tcsicmp(pszName, HVAC_IsSingleLine)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("双线")); pInfo->parlValues->Add(0); pInfo->parsValues->Add(_T("单线")); pInfo->parlValues->Add(1); } TAuxTools::SetAndUpdateCover((TDbInterfacesObj*)m_pOwnerEnt, pszName, pInfo); return TRUE; } // 获得单线状态,当状态为单线时不显示 BOOL bSingleLine = FALSE; m_pXDataMap->GetAt(HVAC_IsSingleLine, bSingleLine); // // 风管参数数据设置 // if (0 == _tcsicmp(pszName, HVAC_Elevation)) // { // // 获得单线类型,当类型为单线时显示并可改 // pInfo->bEditable = bSingleLine; // pInfo->bVisible = bSingleLine; // // return TRUE; // } if (0 == _tcsicmp(pszName, HDCT_Type)) { pInfo->bVisible = TRUE; pInfo->bEditable = FALSE; // 提供数据列表和对应关系 if (NULL != pInfo->parsValues && NULL != pInfo->parlValues) { pInfo->parsValues->Add(_T("直管")); pInfo->parlValues->Add(TDb::eStraight); pInfo->parsValues->Add(_T("软管")); pInfo->parlValues->Add(TDb::eSoft); } return TRUE; } if (0 == _tcsicmp(pszName, HDCT_Width)) { // 获得风管截面,当截面不为圆型时显示并可改 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); pInfo->bVisible = (TDb::eCircular != eSectType); pInfo->bEditable = (TDb::eCircular != eSectType); // 设置数据 if (NULL != pInfo->pXData && 0 != pInfo->pXData->nVt) { // 传递尺寸消息及更新遮挡 TDbHvacDuct* pDuct = TDbHvacDuct::cast(m_pOwnerEnt); if (NULL != pDuct) { TAuxTools::SetAndUpdateCover(pDuct, pszName, pInfo); if (TAuxTools::IsAutoWorkSize()) { double dOrigHeigh(0.0); m_pXDataMap->GetAt(HDCT_Thick, dOrigHeigh); pDuct->WriteSizeChangeMsg(pInfo->pXData->dVal[0], dOrigHeigh); } //BEGIN==================================================== pDuct->UpdateDimData(); //修改时间:2010-04-15 //修改人 :王亚东 //修改原因:风管数据修改后更新标注内容 //END====================================================== // 点不变,也要更新下,否则下次接口记录找不到正确值,导致尺寸不联动 AcGePoint3d ptStart, ptEnd; m_pXDataMap->GetAt(HDCT_START, ptStart); m_pXDataMap->GetAt(HDCT_END , ptEnd); pDuct->UpdateInterfaceRec(ptStart, ptStart); pDuct->UpdateInterfaceRec(ptEnd, ptEnd); pDuct->close(); acedPostCommand(_T("redraw\n")); acedPostCommand(_T("redraw\n")); } } return TRUE; } if (0 == _tcsicmp(pszName, HDCT_Thick)) { // 获得风管截面,当截面不为圆型时显示并可改 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); pInfo->bVisible = (TDb::eCircular != eSectType); pInfo->bEditable = (TDb::eCircular != eSectType); // 更新尺寸 if (NULL != pInfo->pXData && 0 != pInfo->pXData->nVt) { // 传递尺寸消息及更新遮挡 TDbHvacDuct* pDuct = TDbHvacDuct::cast(m_pOwnerEnt); if (NULL != pDuct) { m_pXDataMap->SetAt(pszName, *pInfo->pXData); pInfo->pXData->nVt = 0; // 设置处理完成标识 if (TAuxTools::IsAutoWorkSize()) { double dOrigWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dOrigWidth); pDuct->WriteSizeChangeMsg(dOrigWidth, pInfo->pXData->dVal[0]); } //BEGIN==================================================== pDuct->UpdateDimData(); //修改时间:2010-04-15 //修改人 :王亚东 //修改原因:风管数据修改后更新标注内容 //END====================================================== AcGePoint3d ptStart, ptEnd; m_pXDataMap->GetAt(HDCT_START, ptStart); m_pXDataMap->GetAt(HDCT_END , ptEnd); pDuct->UpdateInterfaceRec(ptStart, ptStart); pDuct->UpdateInterfaceRec(ptEnd, ptEnd); pDuct->close(); acedPostCommand(_T("redraw\n")); acedPostCommand(_T("redraw\n")); } } return TRUE; } // HDCT_Diameter和HDCT_Width定义相同,为同一个值 // 为区分显示名称,借用未被使用的KEY_Diameter值来表达 if (0 == _tcsicmp(pszName, KEY_Diameter)) { // 获得风管截面,当截面为圆型时显示并可改 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); pInfo->bVisible = (TDb::eCircular == eSectType); pInfo->bEditable = (TDb::eCircular == eSectType); // 替代属性,需要特殊处理数据获取和设置 if (NULL != pInfo->pXData) { // 获取数据 if (0 == pInfo->pXData->nVt) { m_pXDataMap->GetAt(HDCT_Diameter, *pInfo->pXData); } // 设置数据 else { TAuxTools::SetAndUpdateCover((TDbInterfacesObj*)m_pOwnerEnt, HDCT_Diameter, pInfo); // m_pXDataMap->SetAt(HDCT_Diameter, *pInfo->pXData); // pInfo->pXData->nVt = 0; // 设置处理完成标识 TDbHvacDuct* pDuct = TDbHvacDuct::cast(m_pOwnerEnt); if (NULL != pDuct) { if (TAuxTools::IsAutoWorkSize()) pDuct->WriteSizeChangeMsg(pInfo->pXData->dVal[0], pInfo->pXData->dVal[0]); //BEGIN==================================================== pDuct->UpdateDimData(); //修改时间:2010-04-15 //修改人 :王亚东 //修改原因:风管数据修改后更新标注内容 //END====================================================== // 点不变,也要更新下,否则下次接口记录找不到正确值,导致尺寸不联动 AcGePoint3d ptStart, ptEnd; m_pXDataMap->GetAt(HDCT_START, ptStart); m_pXDataMap->GetAt(HDCT_END , ptEnd); pDuct->UpdateInterfaceRec(ptStart, ptStart); pDuct->UpdateInterfaceRec(ptEnd, ptEnd); pDuct->close(); acedPostCommand(_T("redraw\n")); acedPostCommand(_T("redraw\n")); } } } return TRUE; } if (0 == _tcsicmp(pszName, KEY_START)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 位置变化,需要在设置之前更新接口位置和方向 if (NULL != pInfo->pXData && TXPT3D == pInfo->pXData->nVt) { // 获得原来的起点和终点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 获得新的起点和方向 AcGePoint3d ptNewStart = asPnt3d(pInfo->pXData->dVal); // 贴壁联动,MoveNextToAirLet()要在风管首位点变化之前进行 BOOL bAutoOffset(FALSE); AcGeVector3d vtOff; GetGlobalContext(HVAC_AUTOOFFSET, bAutoOffset); if (bAutoOffset) { vtOff = ptNewStart - ptStart; if (vtOff.length() > 1e-6) ((TDbHvacDuct*)m_pOwnerEnt)->MoveNextToAirLet(vtOff); } m_pXDataMap->SetAt(KEY_START, ptNewStart); // 设置normal ResetNormalByPt(); AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); // 更新接口方向和位置 ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, vtStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, vtEnd); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, ptNewStart); TAuxTools::SetAndUpdateCover((TDbInterfacesObj*)m_pOwnerEnt, pszName, pInfo); // 接口联动 if (bAutoOffset && vtOff.length() > 1e-6) { ((TDbHvacDuct*)m_pOwnerEnt)->WriteMoveTransMsg(vtOff); m_pOwnerEnt->close(); acedPostCommand(_T("redraw\n")); } } return TRUE; } if (0 == _tcsicmp(pszName, KEY_END)) { pInfo->bVisible = TRUE; pInfo->bEditable = TRUE; // 位置变化,需要在设置之前更新接口位置和方向 if (NULL != pInfo->pXData && TXPT3D == pInfo->pXData->nVt) { // 获得原来的起点和终点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 获得新的终点和方向 AcGePoint3d ptNewEnd = asPnt3d(pInfo->pXData->dVal); // 贴壁联动,MoveNextToAirLet()要在风管首位点变化之前进行 BOOL bAutoOffset(FALSE); AcGeVector3d vtOff; GetGlobalContext(HVAC_AUTOOFFSET, bAutoOffset); if (bAutoOffset) { vtOff = ptNewEnd - ptEnd; if (vtOff.length() > 1e-6) ((TDbHvacDuct*)m_pOwnerEnt)->MoveNextToAirLet(vtOff); } m_pXDataMap->SetAt(KEY_END, ptNewEnd); // 设置normal ResetNormalByPt(); AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); // 更新接口方向和位置 ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, vtStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, vtEnd); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, ptNewEnd); TAuxTools::SetAndUpdateCover((TDbInterfacesObj*)m_pOwnerEnt, pszName, pInfo); // 接口连接联动 if (bAutoOffset) { if (vtOff.length() > 1e-6) { ((TDbHvacDuct*)m_pOwnerEnt)->WriteMoveTransMsg(vtOff); m_pOwnerEnt->close(); acedPostCommand(_T("redraw\n")); } } } return TRUE; } return FALSE; } void THImpHvacDuct::GetTips(CMapStringToString& mapLable2Tip) const { } void THImpHvacDuct::list() const { ASSERT(NULL != m_pXDataMap); // 管件类型 acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t\t\t 暖通:风管")); // 截面类型 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); switch (eSectType) { case TDb::eRectangular: acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t\t\t 截面:矩形")); break; case TDb::eCircular: acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t\t\t 截面:圆形")); break; case TDb::eOblate: acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t\t\t 截面:扁圆形")); break; } // 圆型截面显示直径 if (TDb::eCircular == eSectType) { double dDiameter = 0.0; m_pXDataMap->GetAt(HDCT_Diameter, dDiameter); acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t直径:%.2f"), dDiameter); } // 非圆型截面显示宽度和厚度 else { double dWidth = 0.0, dThick = 0.0; m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); acutPrintf(_T("\n\t\t\t\t\t\t\t\t\t宽度:%.2f\t 厚度:%.2f"), dWidth, dThick); } // 起点 AcGePoint3d pt; pt = StartPoint(); acutPrintf(_T("\n\t\t\t\t\t\t\t\t自 点,X=%.4f\t Y=%.4f\t Z=%.4f"), pt.x, pt.y, pt.z); // 终点 pt = EndPoint(); acutPrintf(_T("\n\t\t\t\t\t\t\t\t到 点,X=%.4f\t Y=%.4f\t Z=%.4f"), pt.x, pt.y, pt.z); } AcGePoint3d THImpHvacDuct::GetDirect(AcGeVector3d& vtStart, AcGeVector3d& vtEnd) const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); // 获得软风管曲率 double dBulge = 0.0; if (eStraight != eDuctType) m_pXDataMap->GetAt(HDCT_Bulge, dBulge); // 获得风管参数 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 计算软风管中点 AcGePoint3d ptMid; Midpoint(ptStart, ptEnd, ptMid); // 直管 if (fabs(dBulge) < 0.0000001) { vtStart = ptStart - ptEnd; vtEnd = -vtStart; return ptMid; } // 调整中点 AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = (ptStart - ptEnd).normal(); vtDirect.rotateBy(PI / 2.0, vtNormal); ptMid += vtDirect * dBulge * ptStart.distanceTo(ptEnd) / 2.0; // 计算始末点方向 AcGeCircArc3d arc(ptStart, ptMid, ptEnd); AcGePoint3d ptCenter = arc.center(); vtStart = ptStart - ptCenter; vtEnd = ptEnd - ptCenter; if (dBulge > 0.0) { vtStart.rotateBy(-PI / 2.0, vtNormal); vtEnd.rotateBy(PI / 2.0, vtNormal); } else { vtStart.rotateBy(PI / 2.0, vtNormal); vtEnd.rotateBy(-PI / 2.0, vtNormal); } // 对于弧管,如果人为设置了端点方向,使用设置的方向Lixl add 2012-3-1 if (eSoft == eDuctType) { m_pXDataMap->GetAt(HDCT_StartDir, vtStart); m_pXDataMap->GetAt(HDCT_EndDir, vtEnd); } vtStart.normalize(); vtEnd.normalize(); return ptMid; } // 设置接口截面类型SectType,宽度Width,厚度Thick到pipeInterface BOOL THImpHvacDuct::GetInterfaceSizeData(int nIndex, TInterface& pipeInterface) const { ASSERT(NULL != m_pXDataMap); // 获取截面类型 TDb::HvacSectType eSectType = TDb::eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); // 获取接口截面、宽度、厚度数据key值 LPCTSTR pszWidthKey, pszThickKey; switch (nIndex) { case 0: pszWidthKey = ((TDb::eCircular == eSectType) ? HDCT_Diameter : HDCT_Width); pszThickKey = HDCT_Thick; break; case 1: pszWidthKey = ((TDb::eCircular == eSectType) ? HDCT_Diameter : HDCT_Width); pszThickKey = HDCT_Thick; break; default: return FALSE; } // 获取尺寸 double dWidth = 0.0, dThick = 0.0; m_pXDataMap->GetAt(pszWidthKey, dWidth); m_pXDataMap->GetAt(pszThickKey, dThick); // 设置接口数据 pipeInterface.SetType(eSectType); pipeInterface.SetSize(dWidth, dThick); return TRUE; } // 根据接口索引(0-起点,1-终点),获得风管接口信息 // 当前无接口,将信息填充到接口结构,确保返回的接口对象有效 BOOL THImpHvacDuct::GetInterface(int nIndex, TInterface& pipeInterface) const { ASSERT(NULL != m_pXDataMap); // 获得风管参数 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 获得始末方向向量 AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); AcDbObjectId id; switch(nIndex) { case 0: // 如果起始接口和第一个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT1, id) && MakesureInterfaceValidate(id, ptStart, vtStart, pipeInterface)) { GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; } // 如果起始接口和第二个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT2, id) && MakesureInterfaceValidate(id, ptStart, vtStart, pipeInterface)) { GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; } // 没有管件连接,用风管数据填充接口对象 pipeInterface.SetOwnerId(m_pOwnerEnt->objectId()); pipeInterface.SetPosition(ptStart); pipeInterface.SetOutDir(vtStart); GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; case 1: // 如果末尾接口和第一个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT1, id) && MakesureInterfaceValidate(id, ptEnd, vtEnd, pipeInterface)) { GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; } // 如果末尾接口和第二个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT2, id) && MakesureInterfaceValidate(id, ptEnd, vtEnd, pipeInterface)) { GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; } // 没有管件连接,用风管数据填充接口对象 pipeInterface.SetOwnerId(m_pOwnerEnt->objectId()); pipeInterface.SetPosition(ptEnd); pipeInterface.SetOutDir(vtEnd); GetInterfaceSizeData(nIndex, pipeInterface); return TRUE; } return FALSE; } BOOL THImpHvacDuct::GetInterface(const AcGePoint3d& ptConnect, TInterface& pipeInterface) const { ASSERT(NULL != m_pXDataMap); // 获得风管参数 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 获得始末方向向量 AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); // 计算测试点到始末点的距离 double dDist1 = ptConnect.distanceTo(ptStart); double dDist2 = ptConnect.distanceTo(ptEnd); AcDbObjectId id; // 位于起始点 if (dDist1 < 1.e-3) { // 如果起始接口和第一个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT1, id) && MakesureInterfaceValidate(id, ptStart, vtStart, pipeInterface)) { GetInterfaceSizeData(0, pipeInterface); return TRUE; } // 如果起始接口和第二个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT2, id) && MakesureInterfaceValidate(id, ptStart, vtStart, pipeInterface)) { GetInterfaceSizeData(0, pipeInterface); return TRUE; } // 没有管件连接 pipeInterface.SetOutDir(vtStart); pipeInterface.SetOwnerId(m_pOwnerEnt->objectId()); pipeInterface.SetPosition(ptStart); GetInterfaceSizeData(0, pipeInterface); return TRUE; } // 位于末尾点 if (dDist2 < 1.e-3) { // 如果末尾接口和第一个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT1, id) && MakesureInterfaceValidate(id, ptEnd, vtEnd, pipeInterface)) { GetInterfaceSizeData(1, pipeInterface); return TRUE; } // 如果末尾接口和第二个管件连接 if (m_pXDataMap->GetAt(KEY_IDCNT2, id) && MakesureInterfaceValidate(id, ptEnd, vtEnd, pipeInterface)) { GetInterfaceSizeData(1, pipeInterface); return TRUE; } // 没有管件连接 pipeInterface.SetOutDir(vtEnd); pipeInterface.SetOwnerId(m_pOwnerEnt->objectId()); pipeInterface.SetPosition(ptEnd); GetInterfaceSizeData(1, pipeInterface); return TRUE; } return FALSE; } BOOL THImpHvacDuct::HasInterface(const AcGePoint3d& ptConnect, const AcGeVector3d& vtDir) { ASSERT(NULL != m_pXDataMap); // 获得风管参数 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); // 获得始末方向向量 AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); // 计算测试点到始末点的距离 double dDist1 = ptConnect.distanceTo(ptStart); double dDist2 = ptConnect.distanceTo(ptEnd); // 位于起始点 if (dDist1 < 1.e-3) return (vtDir.isParallelTo(vtStart)); // 位于末尾点 if (dDist2 < 1.e-3) return (vtDir.isParallelTo(vtEnd)); return FALSE; } BOOL THImpHvacDuct::NotifyInterfaceToModify(const TInterfaceModifyMsg& iModiMsg, TInterfaceModifyMsgs& iModiMsgs) { if (NULL == m_pXDataMap) return FALSE; BOOL bMsgTranslate = FALSE; // 获得消息类型, 根据消息类型处理 InterfaceOper eOper = iModiMsg.GetInterfaceOper(); switch (eOper) { case eMoveGripPoint: // 夹点移动消息处理 bMsgTranslate = OnMoveGripPointMsgNotify(iModiMsg, iModiMsgs); break; case eTransformBy: // 对象移动消息处理 bMsgTranslate = OnTransformMsgNotify(iModiMsg, iModiMsgs); break; case eSize: // 尺寸调整消息处理 bMsgTranslate = OnSizeMsgNotify(iModiMsg, iModiMsgs); break; default: return bMsgTranslate; } // 记录修改标识 if (m_pOwnerEnt != NULL) m_pOwnerEnt->recordGraphicsModified(); return bMsgTranslate; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDraw3d(XExplodeDraw &mode) const { if (NULL == m_pXDataMap) return Acad::eNotImplementedYet; if (GetModeType() == eSystem) return Acad::eNotImplementedYet; // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return ExplodeOrDrawStraight3d(mode); case eSoft: // 软风管 return ExplodeOrDrawSoft3d(mode); default: break; } return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDraw2d( XExplodeDraw &mode ) const { if (m_pOwnerEnt != NULL) { //边界实体 TComplexCurve cplCurve; MakeCurves(cplCurve); TDbExtentsEdge edage; edage.SetEdage(cplCurve); AcDbObjectId idReal = ((TDbInterfacesObj*)m_pOwnerEnt)->layerId(); AcDbObjectId idDash = ((TDbInterfacesObj*)m_pOwnerEnt)->DashLayer(); AcDbObjectId idCent = ((TDbInterfacesObj*)m_pOwnerEnt)->CenterLayer(); edage.ExplodeOrDraw2d(mode, idReal, idDash, idCent, NULL, FALSE, FALSE); } return Acad::eOk; } BOOL THImpHvacDuct::MakeCurves(TComplexCurve& cplCurve) const { if (NULL == m_pXDataMap) return FALSE; // 如果管子水平放置 if (IsHorzAlignment()) return MakeHorz2DCurves(cplCurve, 0); // 如果管子垂直放置 if (IsVertAlignment()) return MakeVert2DCurves(cplCurve, 0); // 如果管子倾斜放置 return MakeIncl2DCurves(cplCurve, 0); } BOOL THImpHvacDuct::GetCurvesInSide(TComplexCurve& compCurve) const { if (NULL == m_pXDataMap) return FALSE; // 如果管子水平放置 if (IsHorzAlignment()) return MakeHorz2DCurves(compCurve, 1); // 如果管子垂直放置 if (IsVertAlignment()) return MakeVert2DCurves(compCurve, 1); // 如果管子倾斜放置 return MakeIncl2DCurves(compCurve, 1); } AcDbPolyline* THImpHvacDuct::MakePolyCurve() const { if (NULL == m_pXDataMap) return NULL; // 如果管子水平放置 if (IsHorzAlignment()) return MakeHorzPolyCurve(); // 如果管子垂直放置 if (IsVertAlignment()) return MakeVertPolyCurve(); // 如果管子倾斜放置 return MakeInclPolyCurve(); } BOOL THImpHvacDuct::MakePolyCurveFaces(AcDbVoidPtrArray& arFaces) { if (NULL == m_pXDataMap) return NULL; // 如果管子水平放置 if (IsHorzAlignment()) return MakeHorzPolyCurveFaces(arFaces); // 如果管子垂直放置 if (IsVertAlignment()) return MakeVertPolyCurveFaces(arFaces); // 如果管子倾斜放置 return MakeInclPolyCurveFaces(arFaces); } BOOL THImpHvacDuct::IsHorzAlignment() const { // // 获得法向量 // AcGeVector3d vtNormal(normal()); // // // 获得UCS坐标Z向量 // AcDbDatabase* pDb = acdbCurDwg(); // AcGeVector3d vtZAxis(pDb->ucsxdir().crossProduct(pDb->ucsydir())); // // return vtNormal.isParallelTo(vtZAxis); // 获得UCS坐标Z向量 AcGeVector3d vtZAxis(TAuxTools::GetUcsZvt()); // 获得方向 AcGeVector3d vtDirect = EndPoint() - StartPoint(); return vtDirect.isPerpendicularTo(vtZAxis); } BOOL THImpHvacDuct::IsVertAlignment() const { // // 获得法向量 // AcGeVector3d vtNormal(normal()); // // // 获得UCS坐标Z向量 // AcDbDatabase* pDb = acdbCurDwg(); // AcGeVector3d vtZAxis(pDb->ucsxdir().crossProduct(pDb->ucsydir())); // // return vtNormal.isPerpendicularTo(vtZAxis); // 获得UCS坐标Z向量 AcGeVector3d vtZAxis(TAuxTools::GetUcsZvt()); // 获得方向 AcGeVector3d vtDirect = EndPoint() - StartPoint(); return vtDirect.isParallelTo(vtZAxis); } BOOL THImpHvacDuct::IsSingleLine() const { ASSERT(NULL != m_pXDataMap); BOOL bSingleLine = FALSE; m_pXDataMap->GetAt(HVAC_IsSingleLine, (int&)bSingleLine); return bSingleLine; } HvacModelType THImpHvacDuct::GetModeType() const { ASSERT(NULL != m_pXDataMap); HvacModelType eType = eModel; m_pXDataMap->GetAt(HVAC_ModeType, (int&)eType); return eType; } BOOL THImpHvacDuct::OnMoveGripPointMsgNotify(const TInterfaceModifyMsg& iModiMsg, TInterfaceModifyMsgs& iModiMsgs) { if (!TAuxTools::IsAutoWorkOffset()) return FALSE; ASSERT(NULL != m_pXDataMap); BOOL bMsgTranslate = FALSE; AcDbObjectId id = iModiMsg.GetMsgOperateOn(); if (id != m_pOwnerEnt->objectId()) // 消息发送目标正确 return FALSE; AcGePoint3d ptGeCon = iModiMsg.GetMsgPoint(); AcGePoint3d ptGeSta = StartPoint(); AcGePoint3d ptGeEnd = EndPoint(); AcGePoint3d ptGeOldSta = ptGeSta; AcGePoint3d ptGeOldEnd = ptGeEnd; AcGeVector3d vtLine = ptGeEnd - ptGeSta; AcGeVector3d vtOffset = iModiMsg.GetMoveGripOffset(); AcGeTol tol; tol.setEqualVector(1e-1); if (vtLine.isParallelTo(vtOffset, tol)) //平行 { if (ptGeOldSta.distanceTo(ptGeCon) < 1.e-3 )//关联有效 { ptGeSta += vtOffset; SetStartPoint(ptGeSta); //更新自身模型空间的扩展字典的接口信息 AcGeMatrix3d xform; xform.setToTranslation(vtOffset); UpdateInterfaceRec(m_pOwnerEnt->objectId(),xform,&ptGeOldSta); //不在往下传递 } if (ptGeOldEnd.distanceTo(ptGeCon) < 1.e-3)//关联有效 { ptGeEnd += vtOffset; SetEndPoint(ptGeEnd); //更新自身模型空间的扩展字典的接口信息 AcGeMatrix3d xform; xform.setToTranslation(vtOffset); UpdateInterfaceRec(m_pOwnerEnt->objectId(),xform,&ptGeOldEnd); //不在往下传递 } } else if (vtLine.isPerpendicularTo(vtOffset, tol)) // 垂直 { // 处理风管壁连接的风口联动情况 暂 ((TDbHvacDuct*)m_pOwnerEnt)->MoveNextToAirLet(vtOffset); //接口更改 ptGeSta += vtOffset; ptGeEnd += vtOffset; //更新自身模型空间的扩展字典的接口信息 SetStartPoint(ptGeSta); SetEndPoint(ptGeEnd); AcGeMatrix3d xform; xform.setToTranslation(vtOffset); AcDbObjectId id1,id2; m_pXDataMap->GetAt(KEY_IDCNT1,id1); m_pXDataMap->GetAt(KEY_IDCNT2,id2); // 构造新的接口传递消息,接口对象的均为Fitting基类派生 AcDbObjectId idT; // 弧管纠正为弧管断点切线方向 AcGeVector3d vtSoftEnd; if (IsArcDuct()) GetDirect(vtLine, vtSoftEnd); //sta 端 if (FindConnect(ptGeOldSta,vtLine,m_pOwnerEnt->objectId(),idT)) // sta 点的接口 { TInterfaceModifyMsg msg; msg.SetMsgPoint(ptGeOldSta); msg.SetTransform(xform); msg.SetMoveGripOffset(iModiMsg.GetMoveGripOffset()); msg.SetGripPosition(TDb::eStart); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } if (IsArcDuct()) vtLine = vtSoftEnd; //end 端 if (FindConnect(ptGeOldEnd,vtLine, m_pOwnerEnt->objectId(), idT)) // end 点的接口 { TInterfaceModifyMsg msg; msg.SetMsgPoint(ptGeOldEnd); msg.SetTransform(xform); msg.SetMoveGripOffset(iModiMsg.GetMoveGripOffset()); msg.SetGripPosition(TDb::eEnd); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } UpdateInterfaceRec(m_pOwnerEnt->objectId(),xform); UpdateDimInReactor(TDb::eMid, vtOffset); } else // 倾斜情况,根据已有向量,求三角形斜边向量,并按此向量延伸 { AcDbEntity* pEnt = NULL; int nRet = acdbOpenAcDbEntity(pEnt, id, AcDb::kForRead); if (NULL != pEnt && pEnt->isKindOf(TDbHvacEquipment::desc())) { pEnt->close(); return bMsgTranslate; } //求斜边的向量 double dAngle = vtOffset.angleTo(vtLine); double dLen = fabs(cos(dAngle)); dLen = vtOffset.length() / dLen; vtLine.normalize(); AcGeVector3d vtOffsetExtend = vtOffset.orthoProject(vtLine.perpVector()); vtOffsetExtend.normalize(); vtOffsetExtend *= dLen; AcGeVector3d vtOffsetReBack; AcDbObjectId idT; if (ptGeOldSta.distanceTo(ptGeCon) < 1.e-3 ) // 关联有效 { ptGeSta += vtOffsetExtend; SetStartPoint(ptGeSta); //更新自身模型空间的扩展字典的接口信息 AcGeMatrix3d xform; xform.setToTranslation(vtOffsetExtend); UpdateInterfaceRec(m_pOwnerEnt->objectId(),xform, &ptGeOldSta); //sta 端 if (FindConnect(ptGeSta,vtLine,m_pOwnerEnt->objectId(),idT)) // sta 点的接口 { vtOffsetReBack = vtOffsetExtend - vtOffset; //设置消息回溯标记,表示处理过的对象二次再接收消息处理 iModiMsgs.SetFlowBackFlag(TRUE); TInterfaceModifyMsg msg; ptGeSta = ptGeOldSta + vtOffset; msg.SetMsgPoint(ptGeSta); msg.SetGripPosition(TDb::eStart); msg.SetMoveGripOffset(vtOffsetReBack); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } } if (ptGeOldEnd.distanceTo(ptGeCon) < 1.e-3)//关联有效 { ptGeEnd += vtOffsetExtend; SetEndPoint(ptGeEnd); //更新自身模型空间的扩展字典的接口信息 AcGeMatrix3d xform; xform.setToTranslation(vtOffsetExtend); UpdateInterfaceRec(m_pOwnerEnt->objectId(),xform, &ptGeOldEnd); //end 端 if (FindConnect(ptGeEnd, vtLine, m_pOwnerEnt->objectId(), idT)) // end 点的接口 { vtOffsetReBack = vtOffsetExtend - vtOffset; //设置消息回溯标记,表示处理过的对象二次再接收消息处理 iModiMsgs.SetFlowBackFlag(TRUE); TInterfaceModifyMsg msg; ptGeEnd = ptGeOldEnd + vtOffset; msg.SetMsgPoint(ptGeEnd); msg.SetGripPosition(TDb::eEnd); msg.SetMoveGripOffset(vtOffsetReBack); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } } } // add by hh 2011-07-11 更新尺寸标注 if(NULL != m_pOwnerEnt) ((TDbHvacDuct*)m_pOwnerEnt)->UpdateDimData(); return bMsgTranslate; } BOOL THImpHvacDuct::OnTransformMsgNotify(const TInterfaceModifyMsg& iModiMsg, TInterfaceModifyMsgs& iModiMsgs) { if (!TAuxTools::IsAutoWorkOffset()) return FALSE; if (m_pXDataMap == NULL) return FALSE; AcDbObjectId id = iModiMsg.GetMsgOperateOn(); AcGePoint3d ptGeSta = StartPoint(); AcGePoint3d ptGeEnd = EndPoint(); AcGePoint3d ptGeOldSta = ptGeSta; AcGePoint3d ptGeOldEnd = ptGeEnd; AcGeVector3d vtLine = ptGeEnd - ptGeSta; //接口位置更改 AcGeMatrix3d matTrans = iModiMsg.GetTransform(); ptGeSta.transformBy(matTrans); ptGeEnd.transformBy(matTrans); AcGePoint3d ptGeMsgOn = iModiMsg.GetMsgPoint(); AcGeVector3d vtLineE = ptGeEnd - ptGeOldEnd; AcGeVector3d vtLineS = ptGeSta - ptGeOldSta; // 平行 拉伸S端,不再传递新消息 if (vtLineS.isParallelTo(vtLine) && ptGeMsgOn.distanceTo(ptGeOldSta) < 1.e-3) { SetStartPoint(ptGeSta); //更新自身命名字典的接口信息 UpdateInterfaceRec(m_pOwnerEnt->objectId(),ptGeOldSta,ptGeSta); return TRUE; } // 平行 拉伸E端,不再传递新消息 if (vtLineE.isParallelTo(vtLine) && ptGeMsgOn.distanceTo(ptGeOldEnd) < 1.e-3) { SetEndPoint(ptGeEnd); //更新自身命名字典的接口信息 UpdateInterfaceRec(m_pOwnerEnt->objectId(),ptGeOldEnd,ptGeEnd); return TRUE; } BOOL bMsgTranslate = FALSE; if (vtLineS.isPerpendicularTo(vtLine)) { SetStartPoint(ptGeSta); SetEndPoint(ptGeEnd); AcDbObjectId id1,id2; m_pXDataMap->GetAt(KEY_IDCNT1,id1); m_pXDataMap->GetAt(KEY_IDCNT2,id2); AcDbObjectId idT; // 构造接口消息传递 开始端检查 if (FindConnect(ptGeOldSta, vtLine, m_pOwnerEnt->objectId(), idT)) // sta 点的接口 { TInterfaceModifyMsg msg; msg.SetMsgPoint(ptGeOldSta); msg.SetTransform(matTrans); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } // 构造接口消息传递 末端检查 if (FindConnect(ptGeOldEnd, -vtLine, m_pOwnerEnt->objectId(), idT)) // sta 点的接口 { TInterfaceModifyMsg msg; msg.SetMsgPoint(ptGeOldEnd); msg.SetTransform(matTrans); msg.SetMsgOperateOn(idT); iModiMsgs.append(msg); bMsgTranslate = TRUE; } //更新自身的接口信息 UpdateInterfaceRec(m_pOwnerEnt->objectId(),iModiMsg.GetTransform()); AcGeVector3d vtOff = matTrans.translation(); if (vtOff.isPerpendicularTo(vtLine)) UpdateDimInReactor(TDb::eMid, vtOff); } return bMsgTranslate; } BOOL THImpHvacDuct::OnSizeMsgNotify(const TInterfaceModifyMsg& iModiMsg, TInterfaceModifyMsgs& iModiMsgs) { ASSERT(NULL != m_pXDataMap); // add by hh 2011-01-21 判断消息点是否存在接口信息, // 用于处理风管打断时写入的错误接口数据问题(暂定方案) TInterface ifTemp; if(!GetInterface(iModiMsg.GetMsgPoint(), ifTemp)) return FALSE; // add end AcGePoint3d ptOrigStart = StartPoint(); AcGePoint3d ptOrigEnd = EndPoint(); double dNewWidth(0.0), dNewHeigh(0.0); iModiMsg.GetSize(dNewWidth, dNewHeigh); AcGeVector3d vtOff = iModiMsg.GetMoveGripOffset(); AcGePoint3d ptNewStart = ptOrigStart + vtOff; AcGePoint3d ptNewEnd = ptOrigEnd + vtOff; m_pXDataMap->SetAt(HDCT_Width, dNewWidth); m_pXDataMap->SetAt(HDCT_Thick, dNewHeigh); m_pXDataMap->SetAt(HDCT_START, ptNewStart); m_pXDataMap->SetAt(HDCT_END, ptNewEnd); // add by hh 2011-04-21 更新尺寸标注 ((TDbHvacDuct*)m_pOwnerEnt)->UpdateDimData(); // 消息传递 AcGeVector3d vtLine = ptOrigEnd - ptOrigStart; AcDbObjectId idFind; if (FindConnect(ptOrigStart, vtLine, m_pOwnerEnt->objectId(), idFind)) // sta 点的接口 { TInterfaceModifyMsg iMsg = iModiMsg; iMsg.SetMsgOperateOn(idFind); iMsg.SetMsgPoint(ptOrigStart); iModiMsgs.append(iMsg); } if (FindConnect(ptOrigEnd, vtLine, m_pOwnerEnt->objectId(), idFind)) // End 点的接口 { TInterfaceModifyMsg iMsg = iModiMsg; iMsg.SetMsgOperateOn(idFind); iMsg.SetMsgPoint(ptOrigEnd); iModiMsgs.append(iMsg); } ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptOrigStart, ptNewStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptOrigEnd, ptNewEnd); return TRUE; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawStraight3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); // 截面类型 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); switch (eSectType) { case eRectangular: return ExplodeOrDrawRectStraight3d(mode); case eCircular: return ExplodeOrDrawCircStraight3d(mode); case eOblate: return ExplodeOrDrawOblateStraight3d(mode); default: break; } return Acad::eNotImplementedYet; } // 具体绘制三维矩形直风管 /* ↑默认法向 起始端 6━━━━━4 侧壁面 1━━3━━━5━━7━━9 ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 起始端 ┃ ┃ ┃ ┃ ┃ ┃ 8 ┃ ┃ ┃ ┃ ┃ 0━━━━━2 0━━2━━━4━━6━━8 */ Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawRectStraight3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); double dWidth(0.0), dThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; AcGeVector3d vtLevel = vtDirect; vtLevel.normalize(); vtLevel.rotateBy(PI * 0.5, vtNormal); // 四面管壁,5×2顶点 AcGePoint3d ptArrSide[5*2]; ptArrSide[0] = ptS - dThick * 0.5 * vtNormal + dWidth * 0.5 * vtLevel; ptArrSide[2] = ptArrSide[0] - dWidth * vtLevel; ptArrSide[4] = ptArrSide[2] + dThick * vtNormal; ptArrSide[6] = ptArrSide[0] + dThick * vtNormal; ptArrSide[8] = ptArrSide[0]; ptArrSide[1] = ptArrSide[0] + vtDirect; ptArrSide[3] = ptArrSide[2] + vtDirect; ptArrSide[5] = ptArrSide[4] + vtDirect; ptArrSide[7] = ptArrSide[6] + vtDirect; ptArrSide[9] = ptArrSide[1]; mode.DrawMesh(5, 2, ptArrSide); return Acad::eOk; } // 具体绘制三维圆形直风管 // 侧壁分解为矩形网格,采用mesh()顶点, 主视图及顶点顺序类似于矩形风管 // 两端采用polygon()绘制多边形 /* ↑默认法向 ┏━8━┓ 起始端 10 6 侧壁面 1━━3━━━5━━7━━9... ┃ ┃ ┃ ┃ ┃ ┃ 12 起始端 4 ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 14 2 0━━2━━━4━━6━━8... ┗━0━┛ */ Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawCircStraight3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); double dMinAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(PI * 2 / dMinAngle); dMinAngle = PI * 2 / nPartNum; double dDiaMet(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dDiaMet); AcGePoint3dArray ptArr; // 修改为,三维最外轮廓跟返回Polylinje一致 // AcGeVector3d vtNow = vtNormal * -1; // 每组顶点法向 AcGeVector3d vtNow = vtNormal.crossProduct(vtDirect); // 每组顶点法向 int i(0); for (i = 0; i < nPartNum * 2; i += 2) { ptArr.append(ptS + dDiaMet * 0.5 * vtNow); ptArr.append(ptE + dDiaMet * 0.5 * vtNow); vtNow.rotateBy(dMinAngle, vtDirect); } // 单独设置末点,防止误差 ptArr.append(ptArr.at(0)); ptArr.append(ptArr.at(1)); mode.DrawMesh(nPartNum + 1, 2, ptArr.asArrayPtr()); return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawOblateStraight3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawSoft3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); // mcl add, 排除弧度极限值 double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs((dBulge)); if (dPosiBulge < 1e-6) return ExplodeOrDrawStraight3d(mode); // 截面类型 HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (!IsCanDrawSoft()) return Acad::eNotImplementedYet; switch (eSectType) { case eRectangular: return ExplodeOrDrawRectSoft3d(mode); case eCircular: ExplodeOrDrawCircSoft3d(mode); case eOblate: return ExplodeOrDrawOblateSoft3d(mode); default: break; } return Acad::eNotImplementedYet; } // 矩形软风管绘制,网格序列方式如下: /* ↑默认法向 起始端 2━━━━━1 剖开后网格 0━━1━━━2━━3━━4 ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 5━━6━━━7━━8━━9 ┃ 起始端 ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 3━━━━━40 */ Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawRectSoft3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); double dWidth(0.0), dThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs(dBulge); double dSignAngle = atan(dBulge) * 4; double dAngle = fabs(dSignAngle); double dMinAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(dAngle / dMinAngle) + 1; dMinAngle = dSignAngle / nPartNum; // 实际间隔角度 AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtEvery = ptS - ptCenter; vtEvery.normalize(); AcGePoint3dArray ptArr; AcGePoint3d ptFirst[5]; ptFirst[0] = ptS + dWidth * 0.5 * vtEvery - dThick * 0.5 * vtNormal; ptFirst[1] = ptFirst[0] + dThick * vtNormal; ptFirst[2] = ptFirst[1] - dWidth * vtEvery; ptFirst[3] = ptFirst[0] - dWidth * vtEvery; ptFirst[4] = ptFirst[0]; int i(0), j(0); for (i = 0; i < nPartNum + 1; i++) { for (j = 0; j < 5; j++) { ptArr.append(ptFirst[j]); ptFirst[j].rotateBy(dMinAngle, vtNormal, ptCenter); } } mode.DrawMesh(nPartNum + 1, 5, ptArr.asArrayPtr()); return Acad::eOk; } // 圆形软风管 /* ↑默认法向 ┏━4━┓ 侧壁面 7━━15━━..... 起始端 3 5 ┃ ┃ ┃ ┃ . . ..... 2 起始端6 ┃ ┃ ┃ ┃ 0━━8━━━..... 1 7... ┗━0━┛ */ Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawCircSoft3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); double dBulge(0.0), dAngle(0.0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dAngle = atan(dBulge) * 4; vtDirect.rotateBy(-dAngle * 0.5, vtNormal); // 得到起始端界面垂直的法向 // 先绘制起始端网点 double dMinCirAngle(TAuxTools::GetMinDiffAngle()); int nColNum = int(PI * 2 / dMinCirAngle) + 1; dMinCirAngle = PI * 2 / nColNum; double dRadius(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadius); dRadius /= 2; AcGePoint3dArray ptArr; AcGeVector3d vtNow = vtNormal * -1; // 每组顶点法向 int i(0); for (i = 0; i < nColNum; i++) { ptArr.append(ptS + dRadius * vtNow); vtNow.rotateBy(dMinCirAngle, vtDirect); } if (ptArr.length() < 1) return Acad::eNotImplementedYet; // 单独设置末点,防止误差 ptArr.append(ptArr.at(0)); // 绘制弧度上各个网格 int nRowNum = int(fabs(dAngle) / dMinCirAngle) + 1; dMinCirAngle = dAngle / nRowNum; AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtEvery = ptS - ptCenter; double dEveryAngle = dMinCirAngle; AcGePoint3d ptEvery; int j(0); int nOrigLen = ptArr.length(); for (i = 0; i < nRowNum + 1; i++) { for (j = 0; j < nOrigLen; j++) { ptEvery = ptArr[j]; ptEvery.rotateBy(dEveryAngle, vtNormal, ptCenter); ptArr.append(ptEvery); } dEveryAngle += dMinCirAngle; } mode.DrawMesh(nRowNum + 1, nColNum + 1, ptArr.asArrayPtr()); return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::ExplodeOrDrawOblateSoft3d( XExplodeDraw &mode ) const { ASSERT(NULL != m_pXDataMap); return Acad::eOk; } // 构件风管内衬图形 add by hh 2013-9-2 BOOL THImpHvacDuct::MakeDuctLiningCurves(TComplexCurve& cplCurve) const { if(NULL == m_pXDataMap) return FALSE; // 不处理垂直风管 if(IsVertAlignment()) return FALSE; // 风管样式 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); // 凸度 double dBulge = 0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); // 风管宽度 double dWidth = 0; m_pXDataMap->GetAt(HDCT_Width, dWidth); // 内衬线的位置为风管宽度的1/10 double dLining = dWidth * 0.4; // 起点终点 AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); // 投影面 AcGePoint3d ptStd = ptE.z > ptS.z ? ptE:ptS; AcGePlane planStd = GetStdPrjPlan(ptStd); // 图层&线型 AcDbObjectId idLayer,idLine; m_pXDataMap->GetAt(HVAC_LiningLayer, idLayer); m_pXDataMap->GetAt(HVAC_LiningLine, idLine); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.idSubLay = idLayer; tCurveEle.idSubLty = idLine; // Z AcGeVector3d vtZAxis = TAuxTools::GetUcsZvt(); // 软风管 if(eSoft == eDuctType && fabs(dBulge) > 1e-6) { if(IsHorzAlignment()) // 仅处理水平放置的软风管 { AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtStaDir = ptS - ptCenter; AcGeVector3d vtEndDir = ptE - ptCenter; vtStaDir.normalize(); vtEndDir.normalize(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); AcGeVector3d vtLevel = (ptE - ptS) * 0.5; vtLevel.rotateBy(-PI * 0.5, vtZAxis); vtLevel *= dBulge; AcGePoint3d ptMid = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; AcGePoint3d ptArc = ptMid + vtLevel; vtLevel.normalize(); tCurveEle.ptGe[0] = (ptS + dLining * vtStaDir).orthoProject(planStd); tCurveEle.ptGe[1] = (ptArc + dLining * vtLevel).orthoProject(planStd); tCurveEle.ptGe[2] = (ptE + dLining * vtEndDir).orthoProject(planStd); cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = (ptS - dLining * vtStaDir).orthoProject(planStd); tCurveEle.ptGe[1] = (ptArc - dLining * vtLevel).orthoProject(planStd); tCurveEle.ptGe[2] = (ptE - dLining * vtEndDir).orthoProject(planStd); cplCurve.append(tCurveEle); } } // 直风管 else { AcGeVector3d vtSide = AcGeVector3d::kZAxis; AcGePlane plan(ptS, AcGeVector3d::kZAxis); AcGePoint3d ptSS = ptS.orthoProject(plan); AcGePoint3d ptEE = ptE.orthoProject(plan); AcGeVector3d vtDirect = ptEE - ptSS; vtDirect.normalize(); vtSide.rotateBy(-PI * 0.5, vtDirect); if(!IsHorzAlignment()) // 倾斜绘制时 需修正一下起终点 { HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); double dThick = 0; AcGeVector3d vtExt = ptE - ptS; vtExt.normalize(); double dExtend = 0; if(eSectType == eRectangular) // 方形 { m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGePlane plan(ptS, TAuxTools::GetUcsZvt()); AcGePoint3d ptPrj = ptE.orthoProject(plan); double dAngle = asin(ptE.distanceTo(ptPrj) / ptS.distanceTo(ptE)); dExtend = dThick * 0.5 * tan(dAngle); } else if(eSectType == eCircular) // 圆形 { m_pXDataMap->GetAt(HDCT_Diameter, dThick); AcDbPolyline poly; int nRet = 0; if(ptS.z > ptE.z) { nRet = TAuxTools::GetEllipseFromCircle(ptS, dThick, vtExt, vtZAxis, poly, vtExt); } else { nRet = TAuxTools::GetEllipseFromCircle(ptE, dThick, vtExt, vtZAxis, poly, -vtExt); } if(2 == nRet) { // 计算交点 AcGePoint3d pt1 = (ptS - dLining * vtSide).orthoProject(planStd); AcGePoint3d pt2 = (ptE - dLining * vtSide).orthoProject(planStd); AcDbLine line(pt1, pt2); AcGePoint3dArray arInter; poly.intersectWith(&line, AcDb::kExtendArg, planStd, arInter); if(1 == arInter.length()) { dExtend = min(arInter[0].distanceTo(pt1), arInter[0].distanceTo(pt2)); vtExt = vtExt.orthoProject(planStd.normal()); vtExt.normalize(); } } } if(ptS.z < ptE.z) { ptS = ptS - dExtend * vtExt; ptE = ptE - dExtend * vtExt; } else { ptS = ptS + dExtend * vtExt; ptE = ptE + dExtend * vtExt; } } tCurveEle.ptGe[0] = (ptS - dLining * vtSide).orthoProject(planStd); tCurveEle.ptGe[1] = (ptE - dLining * vtSide).orthoProject(planStd); tCurveEle.ptGe[2] = (ptE - dLining * vtSide).orthoProject(planStd); cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = (ptS + dLining * vtSide).orthoProject(planStd); tCurveEle.ptGe[1] = (ptE + dLining * vtSide).orthoProject(planStd); tCurveEle.ptGe[2] = (ptE + dLining * vtSide).orthoProject(planStd); cplCurve.append(tCurveEle); } return TRUE; } BOOL THImpHvacDuct::MakeHorz2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeHorzStraight2DCurves(cplCurve, nOutOrIn); case eSoft: // 软风管 return MakeHorzSoft2DCurves(cplCurve, nOutOrIn); default: return FALSE; } } BOOL THImpHvacDuct::MakeHorzStraight2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); // add by zh 2013-7-5 BOOL bSoft(FALSE); m_pXDataMap->GetAt(HDCT_Soft, bSoft); if (bSoft) { return MakeRealHorzSoft2DCurves(cplCurve, nOutOrIn); } // TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = 0.0; tCurveEle.gsMark = 0; AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); BOOL bBaseLine(FALSE); double dWidth(0.0); // m_pXDataMap->GetAt(HVAC_HasBaseLine, bBaseLine); // add by hh 2013-08-30 内衬 BOOL bLining = FALSE; m_pXDataMap->GetAt(HVAC_HasLining, bLining); if(!IsSingleLine() && bLining && nOutOrIn == 1) { MakeDuctLiningCurves(cplCurve); } // add end double dEdgeWidth = GetEdgeLineWidth(); if (IsSingleLine() || (bBaseLine && nOutOrIn == 1)) { tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptE; tCurveEle.ptGe[2] = ptE; if (IsSingleLine()) { tCurveEle.dWidth = dEdgeWidth; } else { double dCentWidth = GetCentLineWidth(); tCurveEle.dWidth = dCentWidth; tCurveEle.idSubLay = GetBaseLayerId(); } cplCurve.append(tCurveEle); } else if (nOutOrIn == 0) // 四边 { double dEndWidth = GetEndLineWidth(); tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; AcDbObjectId idSideLayer(NULL); m_pXDataMap->GetAt(HVAC_EndLayer, idSideLayer); AcGePoint3dArray ptArr; // 各线起始点 GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArr[1]; tCurveEle.ptGe[2] = ptArr[1]; cplCurve.append(tCurveEle); int nEndDrawType(0); GetGlobalContext(HVAC_DuctEndDrawType, nEndDrawType); // change by hh 2011-09-09 避免风管拖动预览时频繁访问接口 if(!m_pOwnerEnt->objectId().isValid()) { tCurveEle.ptGe[0] = ptArr[1]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); } else { if (!IsEndConnect() && nEndDrawType == 0) { tCurveEle.ptGe[0] = ptArr[1]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); } else if (!IsHideEnd()) { tCurveEle.ptGe[0] = ptArr[1]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } } // if (!IsHideEnd()) // { // tCurveEle.ptGe[0] = ptArr[1]; // tCurveEle.ptGe[1] = ptArr[2]; // tCurveEle.ptGe[2] = ptArr[2]; // // if (IsEndConnect()) // { // tCurveEle.idSubLay = idSideLayer; // tCurveEle.dWidth = dEndWidth; // } // cplCurve.append(tCurveEle); // } tCurveEle.ptGe[0] = ptArr[2]; tCurveEle.ptGe[1] = ptArr[3]; tCurveEle.ptGe[2] = ptArr[3]; tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; cplCurve.append(tCurveEle); // change by hh 2011-09-09 避免风管拖动预览时频繁访问接口 if(!m_pOwnerEnt->objectId().isValid()) { tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[0]; tCurveEle.ptGe[2] = ptArr[0]; cplCurve.append(tCurveEle); } else { if (!IsStartConnect() && nEndDrawType == 0) { tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[0]; tCurveEle.ptGe[2] = ptArr[0]; cplCurve.append(tCurveEle); } else if (!IsHideStart()) { tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[0]; tCurveEle.ptGe[2] = ptArr[0]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } } // if (!IsHideStart()) // { // tCurveEle.ptGe[0] = ptArr[3]; // tCurveEle.ptGe[1] = ptArr[0]; // tCurveEle.ptGe[2] = ptArr[0]; // if (IsStartConnect()) // { // tCurveEle.idSubLay = idSideLayer; // tCurveEle.dWidth = dEndWidth; // } // cplCurve.append(tCurveEle); // } } return TRUE; } BOOL THImpHvacDuct::MakeHorzSoft2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); // add by zh 2013-7-5 BOOL bSoft(FALSE); m_pXDataMap->GetAt(HDCT_Soft, bSoft); if (bSoft) return MakeRealHorzSoft2DCurves(cplCurve, nOutOrIn); // if (!IsSingleLine() && !IsCanDrawSoft()) return FALSE; double dBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); if (fabs(dBulge) < 1e-6) return MakeHorzStraight2DCurves(cplCurve, nOutOrIn); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = 0.0; tCurveEle.gsMark = 0; double dWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE - ptS; AcGeVector3d vtNormal = TAuxTools::GetUcsZvt(); vtDirect.normalize(); AcGeVector3d vtLevel = (ptE - ptS) * 0.5; // 水平法向辅助求点用 vtLevel.rotateBy(-PI * 0.5, vtNormal); vtLevel *= dBulge; AcGePoint3d ptMid = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; AcGePoint3d ptArcMid = ptMid + vtLevel; // 圆弧中点 double dEdgeWidth = GetEdgeLineWidth(); if (IsSingleLine()) { tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptArcMid; tCurveEle.ptGe[2] = ptE; tCurveEle.dWidth = dEdgeWidth; cplCurve.append(tCurveEle); return TRUE; } BOOL bBaseLine(FALSE); m_pXDataMap->GetAt(HVAC_HasBaseLine, bBaseLine); // add by hh 2013-08-30 内衬 BOOL bLining = FALSE; m_pXDataMap->GetAt(HVAC_HasLining, bLining); if(!IsSingleLine() && bLining && nOutOrIn == 1) { MakeDuctLiningCurves(cplCurve); } // add end if (nOutOrIn == 1 && bBaseLine) { double dCentWidth = GetCentLineWidth(); tCurveEle.dWidth = dCentWidth; tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptArcMid; tCurveEle.ptGe[2] = ptE; tCurveEle.idSubLay = GetBaseLayerId(); cplCurve.append(tCurveEle); } else if (nOutOrIn == 0) // 边线及两端 { double dEndWidth = GetEndLineWidth(); AcDbObjectId idSideLayer(NULL); m_pXDataMap->GetAt(HVAC_EndLayer, idSideLayer); AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; ConverFourKeyPts(ptArr);// 转换为实际边界点Lixl add 2012-2-28 vtLevel.normalize(); AcGePoint3d ptArcMidUp = ptArcMid - dWidth * 0.5 * vtLevel; AcGePoint3d ptArcMidDown = ptArcMidUp + dWidth * vtLevel; tCurveEle.dWidth = dEdgeWidth; tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArcMidDown; tCurveEle.ptGe[2] = ptArr[1]; cplCurve.append(tCurveEle); if (!IsHideEnd()) { tCurveEle.ptGe[0] = ptArr[1]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } tCurveEle.idSubLay.setNull(); tCurveEle.ptGe[0] = ptArr[2]; tCurveEle.ptGe[1] = ptArcMidUp; tCurveEle.ptGe[2] = ptArr[3]; tCurveEle.dWidth = dEdgeWidth; cplCurve.append(tCurveEle); if (!IsHideStart()) { tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[0]; tCurveEle.ptGe[2] = ptArr[0]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } } return TRUE; } BOOL THImpHvacDuct::MakeVert2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); if (IsSingleLine()) return FALSE; // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeVertStraight2DCurves(cplCurve, nOutOrIn); case eSoft: // 软风管 return MakeVertSoft2DCurves(cplCurve, nOutOrIn); default: return FALSE; } } // 直立管平面绘制, LU:左上 /* 3━━━━━2    ┃ ┃ ┃ ┃ ┃ ┃ ┃ ptCenter┃ heigh ┃ ┃ ┃ ┃ ┃ ┃ 0━━━━━1 ┃ ------width---- */ BOOL THImpHvacDuct::MakeVertStraight2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = GetEdgeLineWidth(); tCurveEle.gsMark = 0; AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; HvacSectType eSectType = eRectangular; HvacDrawType eDrawType = eOldStyle; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); m_pXDataMap->GetAt(HVAC_DrawType, (int&)eDrawType); if (eSectType == eRectangular) { if (nOutOrIn == 0) { tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArr[1]; tCurveEle.ptGe[2] = ptArr[1]; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptArr[1]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptArr[2]; tCurveEle.ptGe[1] = ptArr[3]; tCurveEle.ptGe[2] = ptArr[3]; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[0]; tCurveEle.ptGe[2] = ptArr[0]; cplCurve.append(tCurveEle); } else if (nOutOrIn == 1) { m_pXDataMap->GetAt(HVAC_EndLayer, tCurveEle.idSubLay); tCurveEle.dWidth = GetEndLineWidth(); if (eDrawType == eOldStyle) { AcGePoint3d ptCenter = TAuxTools::Mid(ptArr[0], ptArr[2]); AcGePoint3d ptLineMid = TAuxTools::Mid(ptCenter, ptArr[3]); tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptLineMid; tCurveEle.ptGe[2] = ptLineMid; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptLineMid; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); } else if (eDrawType == eNewImmit || eDrawType == eNewEject) { tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArr[2]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); if (eDrawType == eNewImmit) { tCurveEle.ptGe[0] = ptArr[3]; tCurveEle.ptGe[1] = ptArr[1]; tCurveEle.ptGe[2] = ptArr[1]; cplCurve.append(tCurveEle); } } } } else if (eSectType == eCircular) { if (nOutOrIn == 0) { tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArr[1]; tCurveEle.ptGe[2] = ptArr[2]; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptArr[2]; tCurveEle.ptGe[1] = ptArr[3]; tCurveEle.ptGe[2] = ptArr[0]; cplCurve.append(tCurveEle); } else if (nOutOrIn == 1) { m_pXDataMap->GetAt(HVAC_EndLayer, tCurveEle.idSubLay); tCurveEle.dWidth = GetEndLineWidth(); double dRadiu(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadiu); dRadiu /= 2; AcGeVector3d vtNormal = normal(); AcGePoint3d ptCenter = TAuxTools::Mid(ptArr[0], ptArr[2]); AcGeVector3d vtPerDir = TAuxTools::GetUcsZvt(); // 该面垂直向上的法向 double dBulge(0.0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); if (fabs(dBulge) > 1e-6) { AcGePoint3d ptCirCt = GetCirCenter(); AcGeVector3d vtRad = ptCenter - ptCirCt; vtPerDir = vtRad.crossProduct(vtNormal); if (vtPerDir.z < 0) vtPerDir *= -1; } AcGeVector3d vtSide = normal(); vtSide.rotateBy(-PI/4, vtPerDir); if (eDrawType == eOldStyle) { AcGePoint3d ptArcS, ptArcMid, ptArcE; ptArcS = ptCenter - dRadiu * vtSide; ptArcE = ptCenter + dRadiu * vtSide; vtSide.rotateBy(PI * 0.5, vtPerDir); ptArcMid = ptCenter + dRadiu * 0.5 * vtSide; tCurveEle.ptGe[0] = ptArcS; tCurveEle.ptGe[1] = ptArcMid; tCurveEle.ptGe[2] = ptArcE; cplCurve.append(tCurveEle); } else if (eDrawType == eNewImmit || eDrawType == eNewEject) { AcGePoint3d ptS, ptE; ptS = ptCenter - dRadiu * vtSide; ptE = ptCenter + dRadiu * vtSide; tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptE; tCurveEle.ptGe[2] = ptE; cplCurve.append(tCurveEle); if (eDrawType == eNewImmit) { vtSide.rotateBy(PI * 0.5, vtPerDir); ptS = ptCenter - dRadiu * vtSide; ptE = ptCenter + dRadiu * vtSide; tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptE; tCurveEle.ptGe[2] = ptE; cplCurve.append(tCurveEle); } } } } return TRUE; } // 直立管平面绘制, LU:左上, 在直管位置点基础上,先旋转相应角度,再投影在水平面上即可 /* LU━━━━━RU    ┃ ┃ ┃ ┃ ┃ ┃ ┃ ptStd ┃ heigh ┃ ┃ ┃ ┃ ┃ ┃ LD━━━━━RD ┃ ------width---- */ BOOL THImpHvacDuct::MakeVertSoft2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = GetEdgeLineWidth(); tCurveEle.gsMark = 0; double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs((dBulge)); if (dPosiBulge < 1e-6) return MakeVertStraight2DCurves(cplCurve, nOutOrIn); if (!IsCanDrawSoft()) return FALSE; AcGePoint3d ptSta = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptStd = ptEnd.z > ptSta.z ? ptEnd:ptSta; AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtStdToCenter = ptStd - ptCenter; // 标准点到圆心点向量 vtStdToCenter.normalize(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtSide = vtNormal; HvacSectType eSectType = eRectangular; HvacDrawType eDrawType = eOldStyle; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); m_pXDataMap->GetAt(HVAC_DrawType, (int&)eDrawType); AcGeVector3d vtUserZAixs = TAuxTools::GetUcsZvt(); AcGePlane planStd = GetStdPrjPlan(ptStd); // 倾斜角度 double dRotAngle = atan(dPosiBulge) * 2; if (eSectType == eRectangular) { vtSide.rotateBy(PI * 0.5, vtUserZAixs); double dWidth(0.0), dHeigh(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dHeigh); AcGePoint3d ptLD, ptRD, ptRU, ptLU; ptLD = ptStd + dWidth * 0.5 * vtStdToCenter - dHeigh * 0.5 * vtNormal; ptLU = ptLD + dHeigh * vtNormal; ptRU = ptLU - dWidth * vtStdToCenter; ptRD = ptRU - dHeigh * vtNormal; ptLD = ptLD.orthoProject(planStd); ptLU = ptLU.orthoProject(planStd); ptRU = ptRU.orthoProject(planStd); ptRD = ptRD.orthoProject(planStd); if (nOutOrIn == 0) { tCurveEle.ptGe[0] = ptLD; tCurveEle.ptGe[1] = ptRD; tCurveEle.ptGe[2] = ptRD; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptRD; tCurveEle.ptGe[1] = ptRU; tCurveEle.ptGe[2] = ptRU; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptRU; tCurveEle.ptGe[1] = ptLU; tCurveEle.ptGe[2] = ptLU; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptLU; tCurveEle.ptGe[1] = ptLD; tCurveEle.ptGe[2] = ptLD; cplCurve.append(tCurveEle); } else if (nOutOrIn == 1) { m_pXDataMap->GetAt(HVAC_EndLayer, tCurveEle.idSubLay); tCurveEle.dWidth = GetEndLineWidth(); if (eDrawType == eOldStyle) { AcGePoint3d ptLineMid = TAuxTools::Mid(ptStd, ptLU); tCurveEle.ptGe[0] = ptLD; tCurveEle.ptGe[1] = ptLineMid; tCurveEle.ptGe[2] = ptLineMid; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptLineMid; tCurveEle.ptGe[1] = ptRU; tCurveEle.ptGe[2] = ptRU; cplCurve.append(tCurveEle); } else if (eDrawType == eNewImmit || eDrawType == eNewEject) { tCurveEle.ptGe[0] = ptLD; tCurveEle.ptGe[1] = ptRU; tCurveEle.ptGe[2] = ptRU; cplCurve.append(tCurveEle); if (eDrawType == eNewImmit) { tCurveEle.ptGe[0] = ptLU; tCurveEle.ptGe[1] = ptRD; tCurveEle.ptGe[2] = ptRD; cplCurve.append(tCurveEle); } } } } else if (eSectType == eCircular) { if (nOutOrIn == 0) { double dDia(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dDia); AcGeVector3d vtOrigCir = vtStdToCenter.crossProduct(vtNormal); AcDbPolyline pPolyLine; AcGePoint3dArray ptArcArr; int nRet = TAuxTools::GetEllipseFromCircle(ptStd, dDia, vtOrigCir, vtUserZAixs, pPolyLine); if (nRet == 2) { TAuxTools::GetArcPoint(pPolyLine, ptArcArr); int i(0); // for (i = 0; i < ptArcArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcArr[i-2]; // tCurveEle.ptGe[1] = ptArcArr[i-1]; // tCurveEle.ptGe[2] = ptArcArr[i]; // cplCurve.append(tCurveEle); // } // } for (i = 0; i < ptArcArr.length()-1; i++) { tCurveEle.ptGe[0] = ptArcArr[i]; tCurveEle.ptGe[1] = ptArcArr[i+1]; tCurveEle.ptGe[2] = ptArcArr[i+1]; cplCurve.append(tCurveEle); } } } else if (nOutOrIn == 1) { m_pXDataMap->GetAt(HVAC_EndLayer, tCurveEle.idSubLay); tCurveEle.dWidth = GetEndLineWidth(); vtSide.rotateBy(-PI/4, vtUserZAixs); double dRadiu(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadiu); dRadiu /= 2; if (eDrawType == eOldStyle) { AcGePoint3d ptArcS, ptArcMid, ptArcE; ptArcS = ptStd - dRadiu * vtSide; ptArcE = ptStd + dRadiu * vtSide; vtSide.rotateBy(PI * 0.5, vtUserZAixs); ptArcMid = ptStd + dRadiu * 0.5 * vtSide; ptArcS.rotateBy(dRotAngle, vtNormal, ptStd); ptArcE.rotateBy(dRotAngle, vtNormal, ptStd); ptArcMid.rotateBy(dRotAngle, vtNormal, ptStd); tCurveEle.ptGe[0] = ptArcS.orthoProject(planStd); tCurveEle.ptGe[1] = ptArcMid.orthoProject(planStd); tCurveEle.ptGe[2] =ptArcE.orthoProject(planStd); cplCurve.append(tCurveEle); } else if (eDrawType == eNewImmit || eDrawType == eNewEject) { AcGePoint3d ptS, ptE; ptS = ptStd - dRadiu * vtSide; ptE = ptStd + dRadiu * vtSide; AcGeMatrix3d matRot; matRot.setToRotation(dRotAngle, vtNormal, ptStd); ptS.transformBy(matRot); ptE.transformBy(matRot); tCurveEle.ptGe[0] = ptS.orthoProject(planStd); tCurveEle.ptGe[1] = ptE.orthoProject(planStd); tCurveEle.ptGe[2] =ptE.orthoProject(planStd); cplCurve.append(tCurveEle); if (eDrawType == eNewImmit) { vtSide.rotateBy(PI * 0.5, vtUserZAixs); ptS = ptStd - dRadiu * vtSide; ptE = ptStd + dRadiu * vtSide; ptS.transformBy(matRot); ptE.transformBy(matRot); tCurveEle.ptGe[0] = ptS.orthoProject(planStd); tCurveEle.ptGe[1] = ptE.orthoProject(planStd); tCurveEle.ptGe[2] =ptE.orthoProject(planStd); cplCurve.append(tCurveEle); } } } } return TRUE; } BOOL THImpHvacDuct::MakeIncl2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeInclStraight2DCurves(cplCurve, nOutOrIn); case eSoft: // 软风管 return MakeInclSoft2DCurves(cplCurve, nOutOrIn); default: return FALSE; } } // 绘制直风管,倾斜时状态,求出两端延长部分,加在中截面延长方向上 BOOL THImpHvacDuct::MakeInclStraight2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = 0.0; tCurveEle.gsMark = 0; AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcDbObjectId idBaseLayer(GetBaseLayerId()), idSideLayer(NULL); m_pXDataMap->GetAt(HVAC_EndLayer, idSideLayer); double dEdgeWidth = GetEdgeLineWidth(); // add by hh 2013-08-30 内衬 BOOL bLining = FALSE; m_pXDataMap->GetAt(HVAC_HasLining, bLining); if(!IsSingleLine() && bLining && nOutOrIn == 1) { MakeDuctLiningCurves(cplCurve); } // add end int nEndDrawType(0); GetGlobalContext(HVAC_DuctEndDrawType, nEndDrawType); if (IsSingleLine()) { tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptE; tCurveEle.ptGe[2] = ptE; tCurveEle.dWidth = dEdgeWidth; cplCurve.append(tCurveEle); return TRUE; } double dWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); AcGePoint3dArray ptArr; // 各线起始点 GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcDbDatabase* pDb = acdbCurDwg(); AcGeVector3d vtZAxis(pDb->ucsxdir().crossProduct(pDb->ucsydir())); double dEle(0.0); AcGePlane planStd = GetHidePlane(ptArr[0], ptArr[1], ptArr[2], vtZAxis, dEle); double dExtend(0); // vtDirect 方向上的延伸距离 AcGePlane plan(ptS, TAuxTools::GetUcsZvt()); AcGePoint3d ptPrj = ptE.orthoProject(plan); double dAngle = asin(ptE.distanceTo(ptPrj) / ptS.distanceTo(ptE)); HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); double dThick(0.0); if (eSectType == eRectangular) m_pXDataMap->GetAt(HDCT_Thick, dThick); else if (eSectType == eCircular) m_pXDataMap->GetAt(HDCT_Diameter, dThick); dExtend = dThick * 0.5 * tan(dAngle); double dEndWidth = GetEndLineWidth(); if (eSectType == eRectangular) { if (nOutOrIn == 1) { BOOL bBaseLine(FALSE); m_pXDataMap->GetAt(HVAC_HasBaseLine, bBaseLine); if (bBaseLine) { AcGePoint3d ptStaMidExten = ptS; AcGePoint3d ptEndMidExten = ptE; if (ptS.z < ptE.z) { ptStaMidExten = ptS - dExtend * vtDirect; ptEndMidExten = ptE - dExtend * vtDirect; } else { ptStaMidExten = ptS + dExtend * vtDirect; ptEndMidExten = ptE + dExtend * vtDirect; } double dCentWidth = GetCentLineWidth(); tCurveEle.dWidth = dCentWidth; tCurveEle.ptGe[0] = ptStaMidExten.orthoProject(planStd); tCurveEle.ptGe[1] = ptEndMidExten.orthoProject(planStd); tCurveEle.ptGe[2] = ptEndMidExten.orthoProject(planStd); tCurveEle.idSubLay = idBaseLayer; cplCurve.append(tCurveEle); } tCurveEle.dWidth = dEndWidth; tCurveEle.idSubLay = idSideLayer; if (ptS.z > ptE.z) // 被遮挡的不绘制 { ptArr[0] += dExtend * vtDirect; ptArr[3] += dExtend * vtDirect; tCurveEle.ptGe[0] = ptArr[0].orthoProject(planStd); tCurveEle.ptGe[1] = ptArr[3].orthoProject(planStd); tCurveEle.ptGe[2] = ptArr[3].orthoProject(planStd); //BEGIN=========================================== if (nEndDrawType == 0) //0为随风管壁,1为随端线设置 { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } else { tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; } //修改时间:2010-05-06 //修改人 :王亚东 //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 //END============================================= cplCurve.append(tCurveEle); } else { ptArr[1] -= dExtend * vtDirect; ptArr[2] -= dExtend * vtDirect; tCurveEle.ptGe[0] = ptArr[1].orthoProject(planStd); tCurveEle.ptGe[1] = ptArr[2].orthoProject(planStd); tCurveEle.ptGe[2] = ptArr[2].orthoProject(planStd); //BEGIN=========================================== if (nEndDrawType == 0) { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } else { tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; } //修改时间:2010-05-06 //修改人 :王亚东 //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 //END============================================= cplCurve.append(tCurveEle); } } else if (nOutOrIn == 0) // 四边 { tCurveEle.dWidth = dEndWidth; tCurveEle.idSubLay = idSideLayer; ptArr[0] = ptArr[0] - dExtend * vtDirect; ptArr[3] = ptArr[3] - dExtend * vtDirect; ptArr[1] = ptArr[1] + dExtend * vtDirect; ptArr[2] = ptArr[2] + dExtend * vtDirect; int i(0); for (i = 0; i < 3; i++) { tCurveEle.ptGe[0] = ptArr[i].orthoProject(planStd); tCurveEle.ptGe[1] = ptArr[i+1].orthoProject(planStd); tCurveEle.ptGe[2] = ptArr[i+1].orthoProject(planStd); if (i == 1) { //BEGIN===================================== if (nEndDrawType == 0) { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } else { tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; } //修改时间:2010-05-06 //修改人 :王亚东 //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 //END======================================= } else { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } cplCurve.append(tCurveEle); } tCurveEle.ptGe[0] = ptArr[3].orthoProject(planStd); tCurveEle.ptGe[1] = ptArr[0].orthoProject(planStd); tCurveEle.ptGe[2] = ptArr[0].orthoProject(planStd); //BEGIN================================================ if (nEndDrawType == 0) { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } else { tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; } //修改时间:2010-05-06 //修改人 :王亚东 //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 //END================================================== cplCurve.append(tCurveEle); } } else if (eSectType == eCircular) { AcGePoint3d ptEllEnd = ptE/*.orthoProject(planStd)*/; AcGePoint3d ptEllStart = ptS/*.orthoProject(planStd)*/; // AcGeVector3d vtStaOffSet = ptEllStart.asVector(); // AcGeVector3d vtEndOffSet = ptEllEnd.asVector(); AcGePoint3dArray ptArcStaArr, ptArcEndArr; // 弧上的各点 AcDbPolyline polyLineSta; AcDbPolyline polyLineEnd; if (nOutOrIn == 1) { BOOL bBaseLine(FALSE); m_pXDataMap->GetAt(HVAC_HasBaseLine, bBaseLine); if (bBaseLine) { AcGePoint3d ptStaMidExten = ptS; AcGePoint3d ptEndMidExten = ptE; if (ptS.z < ptE.z) { ptStaMidExten = ptS - dExtend * vtDirect; ptEndMidExten = ptE - dExtend * vtDirect; } else { ptStaMidExten = ptS + dExtend * vtDirect; ptEndMidExten = ptE + dExtend * vtDirect; } double dCentWidth = GetCentLineWidth(); tCurveEle.dWidth = dCentWidth; tCurveEle.ptGe[0] = ptStaMidExten.orthoProject(planStd); tCurveEle.ptGe[1] = ptEndMidExten.orthoProject(planStd); tCurveEle.ptGe[2] = ptEndMidExten.orthoProject(planStd); tCurveEle.idSubLay = idBaseLayer; cplCurve.append(tCurveEle); } // Begin---Lixl---Modify---2011-11-22----- // 修改说明: 内部的边线,在nOutOrIn=0时候绘制 // 修改原因: 内部的边线,在nOutOrIn=1时候绘制,遮挡不住椭圆边线的中间的弧线(原因不明) // tCurveEle.idSubLay = idSideLayer; // tCurveEle.dWidth = dEndWidth; // if (ptS.z > ptE.z) // 被遮挡的不绘制 // { // // 起始端半个椭圆 // int nRet = TAuxTools::GetEllipseFromCircle(ptEllStart, dWidth, vtDirect, vtZAxis, // polyLineSta, vtDirect); // if (nRet == 2) // { // GetArcPoint(polyLineSta, ptArcStaArr); // int i(0); // for (i = 0; i < ptArcStaArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcStaArr[i-2]; // tCurveEle.ptGe[1] = ptArcStaArr[i-1]; // tCurveEle.ptGe[2] = ptArcStaArr[i]; // // //BEGIN======================================= // if (nEndDrawType == 0) // { // tCurveEle.idSubLay.setNull(); // tCurveEle.dWidth = dEdgeWidth; // } // else // { // tCurveEle.idSubLay = idSideLayer; // tCurveEle.dWidth = dEndWidth; // } // //修改时间:2010-05-06 // //修改人 :王亚东 // //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 // //END========================================= // // cplCurve.append(tCurveEle); // } // } // } // } // else // { // // 末端半个椭圆 // int nRet = TAuxTools::GetEllipseFromCircle(ptEllEnd, dWidth, vtDirect, vtZAxis, // polyLineEnd, -vtDirect); // if (nRet == 2) // { // GetArcPoint(polyLineEnd, ptArcEndArr); // // int i(0); // for (i = 0; i < ptArcEndArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcEndArr[i-2]; // tCurveEle.ptGe[1] = ptArcEndArr[i-1]; // tCurveEle.ptGe[2] = ptArcEndArr[i]; // // //BEGIN========================================== // if (nEndDrawType == 0) // { // tCurveEle.idSubLay.setNull(); // tCurveEle.dWidth = dEdgeWidth; // } // else // { // tCurveEle.idSubLay = idSideLayer; // tCurveEle.dWidth = dEndWidth; // } // //修改时间:2010-05-06 // //修改人 :王亚东 // //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 // //END============================================ // // cplCurve.append(tCurveEle); // } // } // } // } // End--------------------------------------------------------------------- } else if (nOutOrIn == 0) // 四边轮廓 { // 两边 tCurveEle.dWidth = dEdgeWidth; tCurveEle.idSubLay.setNull(); tCurveEle.ptGe[0] = ptArr[0]; tCurveEle.ptGe[1] = ptArr[1]; tCurveEle.ptGe[2] = ptArr[1]; cplCurve.append(tCurveEle); tCurveEle.ptGe[0] = ptArr[2]; tCurveEle.ptGe[1] = ptArr[3]; tCurveEle.ptGe[2] = ptArr[3]; cplCurve.append(tCurveEle); // 末端半个椭圆 //BEGIN================================================= if (nEndDrawType == 0) { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; } else { tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; } //修改时间:2010-05-06 //修改人 :王亚东 //修改原因:支持倾斜风管在按风管壁和端线设置时,线宽与图层对应 //END=================================================== int i(0); //tCurveEle.dWidth = dEndWidth; AcDbPolyline polyLineEnd; int nRet = TAuxTools::GetEllipseFromCircle(ptEllEnd, dWidth, vtDirect, vtZAxis, polyLineEnd, vtDirect); if (nRet == 2) { TAuxTools::GetArcPoint(polyLineEnd, ptArcEndArr); // for (i = 0; i < ptArcEndArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcEndArr[i-2]; // tCurveEle.ptGe[1] = ptArcEndArr[i-1]; // tCurveEle.ptGe[2] = ptArcEndArr[i]; // cplCurve.append(tCurveEle); // } // } for (i = 0; i < ptArcEndArr.length()-1; i++) { tCurveEle.ptGe[0] = ptArcEndArr[i]; tCurveEle.ptGe[1] = ptArcEndArr[i+1]; tCurveEle.ptGe[2] = ptArcEndArr[i+1]; cplCurve.append(tCurveEle); } } // 起始端半个椭圆 nRet = TAuxTools::GetEllipseFromCircle(ptEllStart, dWidth, -vtDirect, vtZAxis, polyLineSta, -vtDirect); if (nRet == 2) { TAuxTools::GetArcPoint(polyLineSta, ptArcStaArr); int i(0); // for (i = 0; i < ptArcStaArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcStaArr[i-2]; // tCurveEle.ptGe[1] = ptArcStaArr[i-1]; // tCurveEle.ptGe[2] = ptArcStaArr[i]; // cplCurve.append(tCurveEle); // } // } for (i = 0; i < ptArcStaArr.length()-1; i++) { tCurveEle.ptGe[0] = ptArcStaArr[i]; tCurveEle.ptGe[1] = ptArcStaArr[i+1]; tCurveEle.ptGe[2] = ptArcStaArr[i+1]; cplCurve.append(tCurveEle); } } // Begin---Lixl---Modify---2011-11-22----- // 修改说明: 内部的边线,在nOutOrIn=0时候绘制 // 修改原因: 内部的边线,在nOutOrIn=1时候绘制,遮挡不住椭圆边线的中间的弧线(原因不明) AcDbPolyline polyline1,polyLine2; ptArcStaArr.setLogicalLength(0); ptArcEndArr.setLogicalLength(0); if (ptS.z > ptE.z) // 被遮挡的不绘制 { // 起始端半个椭圆 int nRet = TAuxTools::GetEllipseFromCircle(ptEllStart, dWidth, vtDirect, vtZAxis, polyline1, vtDirect); if (nRet == 2) { TAuxTools::GetArcPoint(polyline1, ptArcStaArr); // for (int i = 0; i < ptArcStaArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcStaArr[i-2]; // tCurveEle.ptGe[1] = ptArcStaArr[i-1]; // tCurveEle.ptGe[2] = ptArcStaArr[i]; // cplCurve.append(tCurveEle); // } // } for (i = 0; i < ptArcStaArr.length()-1; i++) { tCurveEle.ptGe[0] = ptArcStaArr[i]; tCurveEle.ptGe[1] = ptArcStaArr[i+1]; tCurveEle.ptGe[2] = ptArcStaArr[i+1]; cplCurve.append(tCurveEle); } } } else { // 末端半个椭圆 int nRet = TAuxTools::GetEllipseFromCircle(ptEllEnd, dWidth, vtDirect, vtZAxis, polyLine2, -vtDirect); if (nRet == 2) { TAuxTools::GetArcPoint(polyLine2, ptArcEndArr); // for (int i = 0; i < ptArcEndArr.length(); i++) // { // if (i > 1 && i%2 == 0) // { // tCurveEle.ptGe[0] = ptArcEndArr[i-2]; // tCurveEle.ptGe[1] = ptArcEndArr[i-1]; // tCurveEle.ptGe[2] = ptArcEndArr[i]; // cplCurve.append(tCurveEle); // } // } for (i = 0; i < ptArcEndArr.length()-1; i++) { tCurveEle.ptGe[0] = ptArcEndArr[i]; tCurveEle.ptGe[1] = ptArcEndArr[i+1]; tCurveEle.ptGe[2] = ptArcEndArr[i+1]; cplCurve.append(tCurveEle); } } } // End-------------------------------------------------------------------------------- } } return TRUE; } // 倾斜软风管 change by hh 2011-07-15 BOOL THImpHvacDuct::MakeInclSoft2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { if(NULL == m_pXDataMap) return FALSE; // 数据转换后 直接调用水平软风管的方法 后再恢复数据 TDbXDataMap dataMap; BOOL bTrans = TransInclSoftDuct(dataMap); BOOL bRes = MakeHorzSoft2DCurves(cplCurve, nOutOrIn); if(bTrans) m_pXDataMap->CopyFrom(&dataMap); return bRes; } AcDbPolyline* THImpHvacDuct::MakeHorzPolyCurve() const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeHorzStraightPolyCurve(); case eSoft: // 软风管 return MakeHorzSoftPolyCurve(); default: return NULL; } } AcDbPolyline* THImpHvacDuct::MakeHorzStraightPolyCurve() const { ASSERT(NULL != m_pXDataMap); AcGePoint3dArray ptArr; // 各线起始点 if (IsSingleLine()) GetSingleKeyPoints(ptArr); else GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; double dEl(0.0); AcGePlane plan = GetHidePlane(ptArr[0], ptArr[1], ptArr[2], normal(), dEl); AcDbPolyline* pPolyLine = new AcDbPolyline; pPolyLine->addVertexAt(0, ptArr[0].convert2d(plan)); pPolyLine->addVertexAt(1, ptArr[1].convert2d(plan)); pPolyLine->addVertexAt(2,ptArr[2].convert2d(plan)); pPolyLine->addVertexAt(3, ptArr[3].convert2d(plan)); pPolyLine->setNormal(plan.normal()); pPolyLine->setElevation(dEl); pPolyLine->setClosed(Adesk::kTrue); return pPolyLine; } AcDbPolyline* THImpHvacDuct::MakeHorzSoftPolyCurve() const { ASSERT(NULL != m_pXDataMap); double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs((dBulge)); if (dPosiBulge < 1e-6) return MakeHorzStraightPolyCurve(); if (!IsCanDrawSoft()) return NULL; AcGePoint3dArray ptArr; if (IsSingleLine()) GetSingleKeyPoints(ptArr); else GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcGePlane plan = GetStdPrjPlan(ptArr[0]); AcDbPolyline* pPolyLine = new AcDbPolyline; pPolyLine->addVertexAt(0, ptArr[0].convert2d(plan), dBulge); pPolyLine->addVertexAt(1, ptArr[1].convert2d(plan)); pPolyLine->addVertexAt(2, ptArr[2].convert2d(plan), -dBulge); pPolyLine->addVertexAt(3, ptArr[3].convert2d(plan)); pPolyLine->setNormal(plan.normal()); pPolyLine->setElevation(TAuxTools::GetPlaneEle(plan)); pPolyLine->setClosed(Adesk::kTrue); return pPolyLine; } AcDbPolyline* THImpHvacDuct::MakeVertPolyCurve() const { ASSERT(NULL != m_pXDataMap); if (IsSingleLine()) return NULL; // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeVertStraightPolyCurve(); case eSoft: // 软风管 return MakeVertSoftPolyCurve(); default: return NULL; } } AcDbPolyline* THImpHvacDuct::MakeVertStraightPolyCurve() const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE.z > ptS.z ? (ptE - ptS) : (ptS - ptE); if (vtDirect.length() < 1e-9) vtDirect = TAuxTools::GetUcsZvt(); HvacSectType eSectType = eRectangular; HvacDrawType eDrawType = eOldStyle; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); m_pXDataMap->GetAt(HVAC_DrawType, (int&)eDrawType); AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return NULL; double dEl(0.0); AcGePlane plan = GetHidePlane(ptArr[0], ptArr[1], ptArr[2], vtDirect, dEl); if (eSectType == eRectangular) { AcDbPolyline* pPolyLineAround = new AcDbPolyline; pPolyLineAround->addVertexAt(0, ptArr[0].convert2d(plan)); pPolyLineAround->addVertexAt(1, ptArr[1].convert2d(plan)); pPolyLineAround->addVertexAt(2, ptArr[2].convert2d(plan)); pPolyLineAround->addVertexAt(3, ptArr[3].convert2d(plan)); pPolyLineAround->setNormal(vtDirect); pPolyLineAround->setElevation(dEl); pPolyLineAround->setClosed(Adesk::kTrue); return pPolyLineAround; } else if (eSectType == eCircular) { AcDbPolyline* pPolyCir = new AcDbPolyline; pPolyCir->addVertexAt(0, ptArr[0].convert2d(plan), 1); pPolyCir->addVertexAt(1, ptArr[2].convert2d(plan), 1); pPolyCir->setNormal(vtDirect); pPolyCir->setElevation(dEl); pPolyCir->setClosed(Adesk::kTrue); return pPolyCir; } return NULL; } AcDbPolyline* THImpHvacDuct::MakeVertSoftPolyCurve() const { ASSERT(NULL != m_pXDataMap); AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return NULL; AcGePoint3d ptStart(StartPoint()), ptEnd(EndPoint()); AcGePoint3d ptCenter = GetCirCenter(); AcGePoint3d ptStd = TAuxTools::Mid(ptArr[0], ptArr[2]); AcGeVector3d vtStdToCenter = ptStd - ptCenter; AcGeVector3d vtStd = vtStdToCenter.crossProduct(normal()); AcGePlane plan = GetStdPrjPlan(ptStd); HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eRectangular) { AcDbPolyline* pPolyLine = new AcDbPolyline; pPolyLine->addVertexAt(0, ptArr[0].convert2d(plan)); pPolyLine->addVertexAt(1, ptArr[1].convert2d(plan)); pPolyLine->addVertexAt(2, ptArr[2].convert2d(plan)); pPolyLine->addVertexAt(3, ptArr[3].convert2d(plan)); pPolyLine->setNormal(plan.normal()); pPolyLine->setElevation(TAuxTools::GetPlaneEle(plan)); pPolyLine->setClosed(Adesk::kTrue); return pPolyLine; } else if (eSectType == eCircular) { AcDbPolyline pPolyLine; double dDia(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dDia); AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtStdToCenter = ptStd - ptCenter; AcGeVector3d vtNormal = normal(); AcGeVector3d vtStd = vtStdToCenter.crossProduct(vtNormal); TAuxTools::GetEllipseFromCircle(ptStd, dDia, vtStd, TAuxTools::GetUcsZvt(), pPolyLine); AcDbPolyline* pNewPolyLine = (AcDbPolyline*)pPolyLine.clone(); return pNewPolyLine; } return NULL; } AcDbPolyline* THImpHvacDuct::MakeInclPolyCurve() const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeInclStraightPolyCurve(); case eSoft: // 软风管 return MakeInclSoftPolyCurve(); default: return NULL; } } AcDbPolyline* THImpHvacDuct::MakeInclStraightPolyCurve() const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGePoint3dArray ptArr; // 中心面四个点 double dWidth(0.0), dThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); if (IsSingleLine()) { GetSingleKeyPoints(ptArr); GetGlobalContext()->GetAt(KEY_HIDEWIDTH, dWidth); } else GetFourKeyPoints(ptArr); HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eCircular) dThick = dWidth; //BEGIN============================================= int nLength = ptArr.length(); //END=============================================== AcGePlane plan = GetStdPrjPlan(ptArr[0]); AcGeVector3d vtDirect = ptE - ptS; AcGeVector3d vtNormal = normal(); AcGeVector3d vtUseZAix(TAuxTools::GetUcsZvt()); double dExtend(0); // direct方向上延长或缩短的距离 AcGePlane planHor(ptS, vtUseZAix); AcGePoint3d ptPrj = ptE.orthoProject(planHor); double dPerCen = ptE.distanceTo(ptPrj) / ptS.distanceTo(ptE); dExtend = dThick * 0.5 * dPerCen; AcDbPolyline* pPolyLine = NULL; if (eSectType == eRectangular) { vtDirect = vtDirect.orthoProject(plan.normal()); vtDirect.normalize(); ptArr[0] -= dExtend * vtDirect; ptArr[1] += dExtend * vtDirect; ptArr[2] += dExtend * vtDirect; ptArr[3] -= dExtend * vtDirect; pPolyLine = new AcDbPolyline; pPolyLine->addVertexAt(0, ptArr[0].convert2d(plan)); pPolyLine->addVertexAt(1, ptArr[1].convert2d(plan)); pPolyLine->addVertexAt(2, ptArr[2].convert2d(plan)); pPolyLine->addVertexAt(3, ptArr[3].convert2d(plan)); pPolyLine->setNormal(plan.normal()); pPolyLine->setElevation(TAuxTools::GetPlaneEle(plan)); pPolyLine->setClosed(Adesk::kTrue); } else if (eSectType == eCircular) { AcDbPolyline polyLineStart, polyLineEnd; TAuxTools::GetEllipseFromCircle(ptS, dWidth, -vtDirect, vtUseZAix, polyLineStart,-vtDirect); TAuxTools::GetEllipseFromCircle(ptE, dWidth, vtDirect, vtUseZAix, polyLineEnd, vtDirect); pPolyLine = new AcDbPolyline; AcGePoint3d ptNow; double dBulge(0.0); for (int i = 0; i < (int)polyLineEnd.numVerts(); i++) { polyLineEnd.getBulgeAt(i, dBulge); polyLineEnd.getPointAt(i, ptNow); pPolyLine->addVertexAt(i, ptNow.convert2d(plan), dBulge); } int nNowMax = i; int nStartNum = polyLineStart.numVerts(); for (i = nStartNum - 1; i > -1; i--) { polyLineStart.getBulgeAt(nStartNum - 1 - i, dBulge); polyLineStart.getPointAt(i, ptNow); pPolyLine->addVertexAt(nStartNum - 1 - i + nNowMax , ptNow.convert2d(plan), -dBulge); } // Begin---Lixl---Modify---2011-11-22--调整PolyCurve,画出内部椭圆线 polyLineEnd.getPointAt(0, ptNow); pPolyLine->addVertexAt(pPolyLine->numVerts(), ptNow.convert2d(plan)); AcDbPolyline pLine; if (ptS.z > ptE.z) { polyLineStart.getPointAt(0, ptNow); pPolyLine->addVertexAt(pPolyLine->numVerts(), ptNow.convert2d(plan)); TAuxTools::GetEllipseFromCircle(ptS, dWidth, vtDirect, vtUseZAix, pLine, vtDirect); TAuxTools::MergerPline(pPolyLine, &pLine); } else { TAuxTools::GetEllipseFromCircle(ptE, dWidth, vtDirect, vtUseZAix, pLine, -vtDirect); TAuxTools::MergerPline(pPolyLine, &pLine); } // pPolyLine->setClosed(Adesk::kTrue); // End--------------------------------------------------------------------- pPolyLine->setElevation(TAuxTools::GetPlaneEle(plan)); pPolyLine->setNormal(plan.normal()); } return pPolyLine; } // 倾斜软风管 change by hh 2011-07-15 AcDbPolyline* THImpHvacDuct::MakeInclSoftPolyCurve() const { if(NULL == m_pXDataMap) return NULL; // 数据转换后 直接调用水平软风管的方法 后再恢复数据 TDbXDataMap dataMap; BOOL bTrans = TransInclSoftDuct(dataMap); AcDbPolyline* pPolyLine = MakeHorzSoftPolyCurve(); if(bTrans) m_pXDataMap->CopyFrom(&dataMap); return pPolyLine; } BOOL THImpHvacDuct::MakeHorzPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeHorzStraightPolyCurveFaces(arFaces); case eSoft: // 软风管 return MakeHorzSoftPolyCurveFaces(arFaces); default: return NULL; } } BOOL THImpHvacDuct::MakeHorzStraightPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); AcGePoint3dArray ptArr; // 各线起始点 if (IsSingleLine()) GetSingleKeyPoints(ptArr); // 单线模式,按遮挡宽度要求返回宽度 else GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptArr[0]); pFace->setVertexAt(1, ptArr[1]); pFace->setVertexAt(2, ptArr[2]); pFace->setVertexAt(3, ptArr[3]); arFaces.append(pFace); return arFaces.length() > 0; } BOOL THImpHvacDuct::MakeHorzSoftPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); if (!IsCanDrawSoft()) return FALSE; double dMinAngle(TAuxTools::GetMinDiffAngle()); double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs(dBulge); double dSignAngle = atan(dBulge) * 4; double dAngle = fabs(dSignAngle); int nPartNum = int(dAngle / dMinAngle) + 1; dMinAngle = dSignAngle / nPartNum; // 实际间隔角度 AcGePoint3dArray ptUpArr, ptDownArr; AcGePoint3d ptUpNow, ptDownNow; AcGePoint3dArray ptArr; if (IsSingleLine()) GetSingleKeyPoints(ptArr); else GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; ptUpNow = ptArr[3]; ptDownNow = ptArr[0]; AcGePlane planStd = GetStdPrjPlan(ptUpNow); AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtRotAix = TAuxTools::GetUcsZvt(); int i(0); for (i = 0; i < nPartNum + 1; i++) { ptUpArr.append(ptUpNow); ptDownArr.append(ptDownNow); ptUpNow.rotateBy(dMinAngle, vtRotAix, ptCenter); ptDownNow.rotateBy(dMinAngle, vtRotAix, ptCenter); if (i > 0) { AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptDownArr.at(i)); pFace->setVertexAt(1, ptUpArr.at(i)); pFace->setVertexAt(2, ptUpArr.at(i-1)); pFace->setVertexAt(3, ptDownArr.at(i-1)); arFaces.append(pFace); } } return arFaces.length() > 0; } BOOL THImpHvacDuct::MakeVertPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); if (IsSingleLine()) return FALSE; // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeVertStraightPolyCurveFaces(arFaces); case eSoft: // 软风管 return MakeVertSoftPolyCurveFaces(arFaces); default: return NULL; } } BOOL THImpHvacDuct::MakeVertStraightPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); if (IsSingleLine()) return FALSE; HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eRectangular) { AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptArr[0]); pFace->setVertexAt(1, ptArr[1]); pFace->setVertexAt(2, ptArr[2]); pFace->setVertexAt(3, ptArr[3]); arFaces.append(pFace); } else if (eSectType == eCircular) { AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE - ptS; AcGePoint3d ptCenter = ptE.z > ptS.z ? ptE:ptS; AcGeVector3d vtNormal = normal(); AcGeVector3d vtSide = vtNormal; vtSide.rotateBy(PI * 0.5, vtDirect); double dRadius(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadius); dRadius /= 2; double dMinAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(PI * 2 / dMinAngle) + 1; dMinAngle = PI * 2 / nPartNum; AcGePoint3d ptEvery = ptCenter + dRadius * vtSide; AcGePoint3dArray ptArr; int i(0); for (i = 0; i < nPartNum + 1; i++) { ptArr.append(ptEvery); ptEvery.rotateBy(dMinAngle, vtDirect, ptCenter); if (i > 0) { AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptCenter); pFace->setVertexAt(1, ptArr.at(i)); pFace->setVertexAt(2, ptArr.at(i-1)); pFace->setVertexAt(3, ptCenter); arFaces.append(pFace); } } } return arFaces.length() > 0; } BOOL THImpHvacDuct::MakeVertSoftPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eRectangular) { AcGePoint3dArray ptArr; GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcDbFace *pFace = new AcDbFace; pFace->setVertexAt(0, ptArr[0]); pFace->setVertexAt(1, ptArr[1]); pFace->setVertexAt(2, ptArr[2]); pFace->setVertexAt(3, ptArr[3]); arFaces.append(pFace); } else if (eSectType == eCircular) { AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGePoint3d ptStd = ptE.z > ptS.z ? ptE:ptS; // 上面起起遮挡作用的端点 AcGeVector3d vtNormal = normal(); AcGePlane planStd = GetStdPrjPlan(ptStd); double dRadius(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadius); dRadius /= 2; double dMinAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(PI * 2 / dMinAngle) + 1; dMinAngle = PI * 2 / nPartNum; // 得到高端界面垂直的法向 AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtStdToCenter = ptStd - ptCenter; AcGeVector3d vtHighPer = vtStdToCenter.crossProduct(vtNormal); vtHighPer.normalize(); AcGePoint3dArray ptArr; AcGeVector3d vtEvery = vtNormal; AcGePoint3d ptEvery; int i(0); for (i = 0; i < nPartNum + 1; i++) { ptEvery = ptStd + dRadius * vtEvery; ptArr.append(ptEvery); vtEvery.rotateBy(dMinAngle, vtHighPer); if (i > 0) { AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptStd); pFace->setVertexAt(1, ptArr[i].orthoProject(planStd)); pFace->setVertexAt(2, ptArr[i-1].orthoProject(planStd)); pFace->setVertexAt(3, ptStd); arFaces.append(pFace); } } } return arFaces.length() > 0; } BOOL THImpHvacDuct::MakeInclPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); // 风管类型 HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); switch (eDuctType) { case eStraight: // 直风管 return MakeInclStraightPolyCurveFaces(arFaces); case eSoft: // 软风管 return MakeInclSoftPolyCurveFaces(arFaces); default: return NULL; } } BOOL THImpHvacDuct::MakeInclStraightPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); double dWidth(0.0), dThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGePoint3dArray ptArr; // 各线起始点 if (IsSingleLine()) { GetSingleKeyPoints(ptArr); m_pXDataMap->GetAt(KEY_HIDEWIDTH, dWidth); } else GetFourKeyPoints(ptArr); if (ptArr.length() != 4) return FALSE; AcGePlane planStd = GetStdPrjPlan(ptArr[0]); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = (ptE - ptS).orthoProject(planStd.normal()); vtDirect.normalize(); AcGeVector3d vtLeve = vtNormal; vtLeve.rotateBy(PI * 0.5, vtDirect); HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eCircular) dThick = dWidth; double dExtend(0); // direct方向上延长或缩短的距离 AcGePlane planHor(ptS, TAuxTools::GetUcsZvt()); AcGePoint3d ptPrj = ptE.orthoProject(planHor); double dPerCen = ptE.distanceTo(ptPrj) / ptS.distanceTo(ptE); dExtend = dThick * 0.5 * dPerCen; if (eSectType == eRectangular) { ptArr[0] -= dExtend * vtDirect; ptArr[1] += dExtend * vtDirect; ptArr[2] += dExtend * vtDirect; ptArr[3] -= dExtend * vtDirect; AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptArr[0]); pFace->setVertexAt(1, ptArr[1]); pFace->setVertexAt(2, ptArr[2]); pFace->setVertexAt(3, ptArr[3]); arFaces.append(pFace); } else if (eSectType == eCircular) { dExtend = dWidth * 0.5 * dPerCen; // 中间矩形面 AcDbFace* pFace = new AcDbFace; pFace->setVertexAt(0, ptArr[0]); pFace->setVertexAt(1, ptArr[1]); pFace->setVertexAt(2, ptArr[2]); pFace->setVertexAt(3, ptArr[3]); arFaces.append(pFace); // 两端半圆 double dMinAngle(TAuxTools::GetMinDiffAngle()); // 修改内容: 倾斜圆风管消隐面由原来的半圆改为稍微精确的椭圆Lixlmodify // dMinAngle *= 0.5; int nPartNum = int(PI / dMinAngle) + 1; dMinAngle = PI / nPartNum; // ptS = ptS.orthoProject(planStd); // ptE = ptE.orthoProject(planStd); AcGeVector3d vtStaEvery = vtLeve; AcGeVector3d vtEndEvery = vtLeve; AcGePoint3dArray ptArrSta, ptArrEnd; AcGePoint3d ptStaNow = ptArr[0]; AcGePoint3d ptEndNow = ptArr[1]; vtDirect = ptE - ptS; vtDirect.normalize(); // vtStaEvery = vtNormal; // vtStaEvery.rotateBy(PI * 0.5, vtDirect); // vtStaEvery.normalize(); // vtEndEvery = vtNormal; // vtEndEvery.rotateBy(PI * 0.5, vtDirect); // vtEndEvery.normalize(); // ptStaNow = ptS + vtStaEvery * dWidth * 0.5; // ptEndNow = ptE + vtEndEvery * dWidth * 0.5; // Lixl modifyfor修正风管消隐面 AcGeVector3d vtZAxis(TAuxTools::GetUcsZvt()); vtStaEvery = vtDirect.crossProduct(vtZAxis); ptStaNow = ptS + vtStaEvery.normalize() * dWidth * 0.5; ptEndNow = ptE + vtStaEvery * dWidth * 0.5; int i(0); for (i = 0; i < nPartNum + 1; i++) { ptArrSta.append(ptStaNow.orthoProject(planStd)); ptArrEnd.append(ptEndNow.orthoProject(planStd)); // ptStaNow.rotateBy(-dMinAngle, vtNormal, ptS); // ptEndNow.rotateBy(dMinAngle, vtNormal, ptE); if (ptS.z > ptE.z) { ptStaNow.rotateBy(-dMinAngle, -vtDirect, ptS); ptEndNow.rotateBy(dMinAngle, -vtDirect, ptE); } else { ptStaNow.rotateBy(-dMinAngle, vtDirect, ptS); ptEndNow.rotateBy(dMinAngle, vtDirect, ptE); } if (i > 0) { AcDbFace* pStaFace = new AcDbFace; pStaFace->setVertexAt(0, ptS.orthoProject(planStd)); pStaFace->setVertexAt(1, ptArrSta[i]); pStaFace->setVertexAt(2, ptArrSta[i-1]); pStaFace->setVertexAt(3, ptS.orthoProject(planStd)); arFaces.append(pStaFace); AcDbFace* pEndFace = new AcDbFace; pEndFace->setVertexAt(0, ptE.orthoProject(planStd)); pEndFace->setVertexAt(1, ptArrEnd[i]); pEndFace->setVertexAt(2, ptArrEnd[i-1]); pEndFace->setVertexAt(3, ptE.orthoProject(planStd)); arFaces.append(pEndFace); } } } return arFaces.length() > 0; } // 倾斜软风管 change by hh 2011-07-15 BOOL THImpHvacDuct::MakeInclSoftPolyCurveFaces(AcDbVoidPtrArray& arFaces) const { if(NULL == m_pXDataMap) return FALSE; // 数据转换后 直接调用水平软风管的方法 后再恢复数据 TDbXDataMap dataMap; BOOL bTrans = TransInclSoftDuct(dataMap); BOOL bRes = MakeHorzSoftPolyCurveFaces(arFaces); if(bTrans) m_pXDataMap->CopyFrom(&dataMap); return bRes; } Acad::ErrorStatus THImpHvacDuct::transformBy(const AcGeMatrix3d& xform) { if (NULL == m_pXDataMap) return Acad::eNotImplementedYet; // 获得点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGeVector3d vtNormal = normal(); // add by hh 2013-9-17 处理弧形管在镜像时曲率错误的问题 AcGePoint3d ptArc; double dBulge = 0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); HvacDuctType eType = eSoft; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); if(eType == eSoft && !EQUAL_ZERO(dBulge)) { // 计算圆弧的中点 AcGeVector3d vtDir = ptEnd - ptStart; vtDir.normalize(); AcGeVector3d vtLevel = (ptEnd - ptStart) * 0.5; vtLevel.rotateBy(-PI * 0.5, TAuxTools::GetUcsZvt()); vtLevel *= dBulge; AcGePoint3d ptMid = ptStart + ptStart.distanceTo(ptEnd) * 0.5 * vtDir; ptArc = ptMid + vtLevel; // 变换位置 ptArc.transformBy(xform); ptStart.transformBy(xform); ptEnd.transformBy(xform); // 变换向量 vtNormal = vtNormal.transformBy(xform).normalize(); // 重新计算曲率 dBulge = TAuxTools::CalCurvature(ptStart, ptArc, ptEnd, &vtNormal); m_pXDataMap->SetAt(HDCT_Bulge, dBulge); } else { // 变换位置 ptStart.transformBy(xform); ptEnd.transformBy(xform); // 变换向量 vtNormal = vtNormal.transformBy(xform).normalize(); } // 更新点 SetStartPoint(ptStart); SetEndPoint(ptEnd); setNormal(vtNormal); // 设置尺寸 double dScale = xform.scale(); double dWidth(0.0), dHeigh(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dHeigh); dWidth *= dScale; dHeigh *= dScale; m_pXDataMap->SetAt(HDCT_Width, dWidth); m_pXDataMap->SetAt(HDCT_Thick, dHeigh); if (m_pOwnerEnt != NULL && m_pOwnerEnt->objectId().isValid()) { // 传递消息 AcGeVector3d vtDirect = ptEnd - ptStart; AcGeVector3d vtOff = xform.translation(); // 如果实体不是在当前模型空间中,不做写消息,更新接口处理 AcDbDatabase* pDb = m_pOwnerEnt->database(); if (pDb == NULL) pDb = acdbCurDwg(); AcDbObjectId idModel; AcDbBlockTable* pTable = NULL; pDb->getBlockTable(pTable, AcDb::kForRead); if (pTable != NULL) { pTable->getAt(ACDB_MODEL_SPACE, idModel); pTable->close(); } // 如果实体不是在当前模型空间中,不做写消息,更新接口处理 if (idModel == m_pOwnerEnt->blockId()) { // 写入接口更改消息 TInterfaceModifyMsg iMsg; iMsg.SetMsgValidate(TRUE); iMsg.SetTransform(xform); iMsg.SetGripPosition(TDb::eMid); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); //更新接口记录接口信息 UpdateInterfaceRec(m_pOwnerEnt->objectId(), xform); } } return Acad::eOk; } Position THImpHvacDuct::ExplainGripIndex(int nIndex) const { Position ePos = eStart; if (IsVertAlignment()) { HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (eSectType == eRectangular) { switch(nIndex) { case 0: ePos = eMid; break; case 1: ePos = eSizeMid0; break; case 2: ePos = eSizeMid1; break; case 3: ePos = eSizeMid2; break; case 4: ePos = eSizeMid3; break; case 5: ePos = eCommand0; break; default: break; } } else if (eSectType == eCircular) { switch(nIndex) { case 0: ePos = eMid; break; case 1: ePos = eSizeMid0; break; case 2: ePos = eCommand0; break; default: break; } } } else { HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); switch(nIndex) { case 0: ePos = eStart; break; case 1: ePos = eEnd; break; case 2: ePos = eMid; break; // case 3: // ePos = eDim0; // break; case 3: ePos = eSizeMid0; break; case 4: ePos = eSizeMid1; break; case 5: ePos = eCommand0; break; case 6: ePos = eCommand1; break; case 7: if (eStraight == eType) ePos = eCommand2; else if (eSoft == eType) ePos = eAdjust0; break; case 8: case 9: case 10: case 11: ePos = eMid; break; default: break; } } return ePos; } Acad::ErrorStatus THImpHvacDuct::getStretchPoints( AcGePoint3dArray& stretchPoints ) const { stretchPoints.append(StartPoint()); stretchPoints.append(EndPoint()); return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::getGripPoints(AcGePoint3dArray& gripPoints, AcDbIntArray& osnapModes, AcDbIntArray& geomIds) const { if (NULL == m_pXDataMap) return Acad::eOk; // 获得始末点和重点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptMid = TAuxTools::Mid(ptStart, ptEnd); // 获得方向向量 AcGeVector3d vtDirect = (ptMid - ptStart); // 方向向量单位化 vtDirect.normalize(); // 获得垂直向量 AcGeVector3d vtNormal = normal(); AcGeVector3d vtPerp = vtNormal.crossProduct(vtDirect); // 初始化参数默认值 HvacDuctType eDuctType = eStraight; HvacSectType eSectType = eRectangular; double dSizeMain = 0.0; // 获取参数 m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); m_pXDataMap->GetAt(HDCT_Width, dSizeMain); // 获得软风管的曲率 double dBulge = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); // double dCmdOff = ::PixelToWcs(10); // 取得10个像素点在世界坐标系下的长度,距两端距离 AcGeVector3d vtCmd(vtNormal); // 命令点与中心点法向 vtCmd.rotateBy(-PI*0.25, vtDirect); vtCmd *= g_dCmdOff; AcGePoint3d ptCommand = ptMid + vtCmd; // 命令点 if (IsVertAlignment()) { if (eDuctType == eSoft) { double dAngle = atan(dBulge) * 4; vtDirect.rotateBy(dAngle * 0.5, vtNormal); // 得到末端界面垂直的法向 } AcGeVector3d vtSide = vtNormal; vtSide.rotateBy(PI * 0.5, vtDirect); if (eSectType == eRectangular) { double dThick = 0.0; m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGePoint3d ptUp, ptDown, ptLeft, ptRight; // 四个尺寸点 ptUp = ptMid + dThick * 0.5 * vtNormal; ptDown = ptUp - dThick * vtNormal; ptLeft = ptMid + dSizeMain * 0.5 * vtSide; ptRight = ptLeft - dSizeMain * vtSide; gripPoints.append(ptMid); gripPoints.append(ptUp); gripPoints.append(ptDown); gripPoints.append(ptLeft); gripPoints.append(ptRight); gripPoints.append(ptCommand); } if (eSectType == eCircular) { double dRadius(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadius); dRadius /= 2; AcGePoint3d ptUp; ptUp = ptMid + dRadius * vtNormal; AcGePoint3d ptRight = GetAVertCirSizePt(); gripPoints.append(ptMid); gripPoints.append(ptRight); gripPoints.append(ptCommand); } } else { AcGePoint3d ptCmdSta = ptStart - g_dCmdOff * vtDirect; AcGePoint3d ptCmdEnd = ptEnd + g_dCmdOff * vtDirect; AcGePoint3d ptCenter = GetCirCenter(); // 软风管时调整中点位置 if (eSoft == eDuctType && (fabs(dBulge) > 1e-6)) { // 调整中心点 double dHight = ptStart.distanceTo(ptEnd) * 0.5 * dBulge; ptMid -= (vtPerp * dHight); // 命令点调整 AcGeVector3d vtSta = ptStart - ptCenter; AcGeVector3d vtEnd = ptEnd - ptCenter; AcGeVector3d vtPerSta = vtNormal.crossProduct(vtSta); AcGeVector3d vtPerEnd = vtNormal.crossProduct(vtEnd); vtPerSta.normalize(); vtPerEnd.normalize(); if (dBulge < 0) { vtPerSta *= -1; vtPerEnd *= -1; } ptCmdSta = ptStart - g_dCmdOff * vtPerSta; ptCmdEnd = ptEnd + g_dCmdOff * vtPerEnd; } // // 获得默认标注点 // AcGePoint3d ptDimPos; // m_pXDataMap->GetAt(HVAC_DimBasePos, ptDimPos); // if (ptDimPos == AcGePoint3d::kOrigin) // { // ReSetDimPoint(); // m_pXDataMap->GetAt(HVAC_DimBasePos, ptDimPos); // } // 计算尺寸点到中点的距离值 double dSizeEdge = dSizeMain * 0.5; // 添加夹点 // 始末点 gripPoints.append(ptStart); gripPoints.append(ptEnd); // 中点 gripPoints.append(ptMid); // 标注点 // gripPoints.append(ptDimPos); // 尺寸点 gripPoints.append(ptMid + vtPerp * dSizeEdge); gripPoints.append(ptMid - vtPerp * dSizeEdge); // 增加三个命令夹点 gripPoints.append(ptCmdSta); gripPoints.append(ptCmdEnd); // 软风管没有中间命令点 if (eSoft == eDuctType) { gripPoints.append(GetAdjustPt()); // 辅助定位点,效果等同于中点 AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtCentToStart = (ptStart - ptCenter).normalize(); AcGeVector3d vtCentToEnd = (ptEnd - ptCenter).normalize(); gripPoints.append(ptStart + vtCentToStart * dSizeEdge); gripPoints.append(ptStart - vtCentToStart * dSizeEdge); gripPoints.append(ptEnd + vtCentToEnd * dSizeEdge); gripPoints.append(ptEnd - vtCentToEnd * dSizeEdge); } else { gripPoints.append(ptMid + vtPerp * (dSizeEdge + g_dCmdOff)); // 辅助定位点,效果等同于中点 gripPoints.append(ptStart + vtPerp * dSizeEdge); gripPoints.append(ptStart - vtPerp * dSizeEdge); gripPoints.append(ptEnd + vtPerp * dSizeEdge); gripPoints.append(ptEnd - vtPerp * dSizeEdge); } } return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::getOsnapPoints( AcDb::OsnapMode osnapMode, INT_PTR gsSelectionMark, const AcGePoint3d& pickPoint, const AcGePoint3d& lastPoint, const AcGeMatrix3d& viewXform, AcGePoint3dArray& snapPoints, AcDbIntArray& geomIds ) const { if (NULL == m_pXDataMap) return Acad::eNotApplicable; HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); if (eType == eStraight) { AcDbLine line(StartPoint(),EndPoint()); line.getOsnapPoints(osnapMode,gsSelectionMark,pickPoint,lastPoint,viewXform, snapPoints,geomIds); } else if (eType == eSoft) { AcDbArc arc; if (InitArc(arc)) arc.getOsnapPoints(osnapMode, gsSelectionMark, pickPoint, lastPoint, viewXform, snapPoints, geomIds); else return Acad::eNotImplementedYet; } // 外壁捕捉 AcDbPolyline* pPolyLine = MakePolyCurve(); if (NULL == pPolyLine) return Acad::eOk; AcDbVoidPtrArray arrPolyLine; arrPolyLine.append(pPolyLine); // 矩形管,三维视图,增加上下边捕捉,便于选中 struct resbuf rb = {NULL, RT3DPOINT, 0}; acedGetVar(_T("VIEWDIR"), &rb); AcGeVector3d vtDir = asVec3d(rb.resval.rpoint); if (!vtDir.isCodirectionalTo(TAuxTools::GetUcsZvt())) { HvacSectType eSect = TDb::eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSect); if (TDb::eRectangular == eSect) { double dHeigh(0.0); m_pXDataMap->GetAt(HDCT_Thick, dHeigh); dHeigh *= 0.5; AcGeVector3d vtOff = normal(); vtOff *= dHeigh; AcDbPolyline* pUpLine = (AcDbPolyline*)pPolyLine->clone(); if (NULL != pUpLine) { pUpLine->transformBy(vtOff); arrPolyLine.append(pUpLine); } AcDbPolyline* pDwLine = (AcDbPolyline*)pPolyLine->clone(); if (NULL != pDwLine) { pDwLine->transformBy(-vtOff); arrPolyLine.append(pDwLine); } } } int i(0); for (i = 0; i < arrPolyLine.length(); i++) { AcDbEntity* pEnt = (AcDbEntity*)arrPolyLine[i]; if (NULL == pEnt) continue; AcDbPolyline* pPolyLine = AcDbPolyline::cast(pEnt); if (NULL == pPolyLine) { delete pEnt; continue; } AcDbVoidPtrArray arrLine; pPolyLine->explode(arrLine); int i(0); for (i = 0; i < arrLine.length(); i++) { AcDbObject* pObj = (AcDbObject*)arrLine[i]; if (NULL == pObj) continue; AcDbCurve* pCurve = AcDbCurve::cast(pObj); if (NULL != pCurve) { pCurve->getOsnapPoints(osnapMode, gsSelectionMark, pickPoint, lastPoint, viewXform, snapPoints, geomIds); } delete pObj; } delete pPolyLine; } return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::moveStretchPointsAt( const AcDbIntArray& indices, const AcGeVector3d& offset ) { if (NULL == m_pXDataMap || offset.length() < 1e-6) return Acad::eNotImplementedYet; if (indices.length() == 1) { // 单个夹点 Position ePos = ExplainGripIndex(indices[0]); if (ePos == TDb::eStart || ePos == TDb::eEnd) MoveExtendGripPointsAt(ePos, offset, FALSE); } else { // 多个夹点 MoveTransGripPointsAt(TDb::eMid, offset, FALSE); } return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::moveGripPointsAt(const AcDbIntArray& indices, const AcGeVector3d& offset) { if (NULL == m_pXDataMap || offset.length() < 1e-6) return Acad::eNotImplementedYet; // 如果有多个点,则去除命令点后,有多个点时作为移动,单个点时使用该点类型 Position ePos; if (indices.length() == 1) { // 单个夹点 ePos = ExplainGripIndex(indices[0]); } else { // 多个夹点 int iCount = 0; Position eTemp; int iPos = indices.length(); while ((--iPos) >= 0 && iCount < 2) { eTemp = ExplainGripIndex(indices[iPos]); switch (eTemp) { case eStart: case eEnd: case eMid: case eDim1: case eSizeMid0: case eSizeMid1: ePos = eTemp; iCount++; break; } } // 多个命令夹点不处理 if (iCount == 0) return Acad::eOk; // 多个非命令夹点,移动整体 if (iCount > 1) { MoveTransGripPointsAt(eMid, offset, TRUE); return Acad::eOk; } } switch (ePos) { case eStart: case eEnd: MoveExtendGripPointsAt(ePos, offset, TRUE); break; case eMid: MoveTransGripPointsAt(ePos, offset, TRUE); break; case eDim0: case eDim1: case eDim2: // MoveDimGripPointsAt(ePos, offset); break; case eSizeMid0: case eSizeMid1: case eSizeMid2: case eSizeMid3: MoveSizeGripPointsAt(ePos, offset); break; case eCommand0: case eCommand1: case eCommand2: MoveCommandGripPointsAt(ePos, offset); break; case eAdjust0: MoveAdjustGripPointsAt(ePos, offset); break; } return Acad::eOk; } // 仅对非立管 Acad::ErrorStatus THImpHvacDuct::MoveExtendGripPointsAt( TDb::Position ePos, const AcGeVector3d& offset, BOOL bAutoWork ) { Acad::ErrorStatus eRet = Acad::eOk; ASSERT(NULL != m_pXDataMap); AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptNewStart = ptStart; AcGePoint3d ptNewEnd = ptEnd; AcGeVector3d vtDirect = ptEnd - ptStart; AcGeVector3d vtUcsZ = TAuxTools::GetUcsZvt(); AcGeVector3d vtValidOff = offset.orthoProject(vtUcsZ); HvacDuctType eDucttype = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDucttype); if (ePos == eStart) { ptNewStart += vtValidOff; if (ptNewStart != ptEnd) SetStartPoint(ptNewStart); else eRet = Acad::eNotImplementedYet; } else if (ePos == eEnd) { ptNewEnd += vtValidOff; if (ptNewEnd != ptStart) SetEndPoint(ptNewEnd); else eRet = Acad::eNotImplementedYet; } if (eSoft == eDucttype && !IsCanDrawSoft()) eRet = Acad::eNotImplementedYet; // 对于斜管或拖拽点又Z坐标变化时重新设定Normal if (eRet == Acad::eOk && (!IsHorzAlignment() || fabs(offset.z) > 1e-3)) { AcGeVector3d vtNormal(vtUcsZ); AcGePlane plane(ptStart, vtNormal); AcGePlane planeEnd(ptEnd, vtNormal); AcGePoint3d ptPrj = ptNewStart.orthoProject(plane); if (ePos == eEnd) { ptPrj = ptNewEnd.orthoProject(plane); } else if (ePos == eStart) { ptPrj = ptNewStart.orthoProject(planeEnd); } AcGeLine3d line(ptNewStart, ptNewEnd); AcGePoint3d ptOnLine = line.closestPointTo(ptPrj); vtNormal = ptOnLine - ptPrj; vtNormal.normalize(); setNormal(vtNormal); } if (eRet == Acad::eOk) { // 传递修改消息 if (m_pOwnerEnt != NULL && m_pOwnerEnt->objectId().isValid()) { //BEGIN================================================================= TDbHvacDuct *pDuctEnt = TDbHvacDuct::cast(m_pOwnerEnt); if (pDuctEnt != NULL) { pDuctEnt->UpdateDimData(); } //修改时间:2010-04-15 //修改人 :王亚东 //修改原因:风管数据修改后更新标注内容 //END=================================================================== // 水平延长拉伸时才创建接口更改消息 if (bAutoWork && vtValidOff.isParallelTo(vtDirect)) { TInterfaceModifyMsg iMsg; iMsg.SetMsgPoint(ePos == eStart ? ptNewStart:ptNewEnd); iMsg.SetGripPosition(ePos); iMsg.SetMoveGripOffset(offset); iMsg.SetMsgValidate(TRUE); iMsg.SetInterfaceOper(eMoveGripPoint); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); } AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, vtStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, vtEnd); //更新自身模型空间的扩展字典的接口信息 if (ePos == eStart) ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, ptNewStart); else if (ePos == eEnd) ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, ptNewEnd); UpdateDimInReactor(ePos, offset); } } else { SetStartPoint(ptStart); SetEndPoint(ptEnd); } return eRet; } Acad::ErrorStatus THImpHvacDuct::MoveTransGripPointsAt( TDb::Position ePos, const AcGeVector3d& offset, BOOL bForcePer ) { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGeVector3d vtValidOff = offset; BOOL bAutoOff(FALSE); GetGlobalContext(HVAC_AUTOOFFSET, bAutoOff); if (bAutoOff) { AcGeVector3d vtDirct = ptEnd - ptStart; if (bForcePer) vtValidOff = vtValidOff.orthoProject(vtDirct); } AcGePoint3d ptNewStart = ptStart + vtValidOff; AcGePoint3d ptNewEnd = ptEnd + vtValidOff; SetStartPoint(ptNewStart); SetEndPoint(ptNewEnd); // // 位移标注夹点 // AcGePoint3d ptDim; // m_pXDataMap->GetAt(HVAC_DimBasePos, ptDim); // ptDim += offset; // m_pXDataMap->SetAt(HVAC_DimBasePos, ptDim); // 传递修改消息 if (m_pOwnerEnt != NULL && m_pOwnerEnt->objectId().isValid()) { // 处理风管壁连接的风口联动情况,暂 if (bAutoOff) { // 先复原位置,为了寻找贴壁的风口 SetStartPoint(ptStart); SetEndPoint(ptEnd); // ((TDbHvacDuct*)m_pOwnerEnt)->MoveNextToAirLet(vtValidOff); TDbHvacDuct *pDuct = TDbHvacDuct::cast(m_pOwnerEnt);//Lixl modify 2012-3-14 if (NULL != pDuct) pDuct->MoveNextToAirLet(vtValidOff); SetStartPoint(ptNewStart); SetEndPoint(ptNewEnd); } // 创建接口更改消息 AcGeMatrix3d xform; xform.setToTranslation(vtValidOff); TInterfaceModifyMsg iMsg; iMsg.SetMsgPoint(TAuxTools::Mid(ptNewStart, ptNewEnd)); iMsg.SetGripPosition(eMid); iMsg.SetMsgValidate(TRUE); iMsg.SetTransform(xform); iMsg.SetMoveGripOffset(vtValidOff); iMsg.SetInterfaceOper(eMoveGripPoint); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); // add by hh 2011-09-22 更新遮挡 解决风管移动后遮挡无法自动更新的问题 ((TDbHvacDuct*)m_pOwnerEnt)->UpdateCoverDisplay(); //更新自身模型空间的扩展字典的接口信息 UpdateInterfaceRec(m_pOwnerEnt->objectId(), xform); UpdateDimInReactor(ePos, vtValidOff); } return Acad::eOk; } Acad::ErrorStatus THImpHvacDuct::MoveAdjustGripPointsAt(Position ePos, const AcGeVector3d& offset) { ASSERT(NULL != m_pXDataMap); Acad::ErrorStatus eRet = Acad::eOk; AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); if (eSoft == eType) { double dOrigBulge(0.0); m_pXDataMap->GetAt(HDCT_Bulge, dOrigBulge); AcGeVector3d vtValid = offset; // 有效向量 vtValid.orthoProject(normal()); AcGePoint3d ptOrigAdjust = GetAdjustPt(); AcGePoint3d ptGet = ptOrigAdjust + vtValid; if (ptGet != ptStart && ptGet != ptEnd) { double dNewBulge(0.0); AcGeCircArc3d arc(ptStart, ptGet, ptEnd); double dSubAngle = arc.endAng() - arc.startAng(); dNewBulge = tan(dSubAngle*0.25); AcGeVector3d vtOrigNormal = normal(); AcGeVector3d vtNormal = arc.normal(); if (!vtNormal.isCodirectionalTo(vtOrigNormal)) dNewBulge *= -1; m_pXDataMap->SetAt(HDCT_Bulge, dNewBulge); if (!IsCanDrawSoft()) eRet = Acad::eNotImplementedYet; } if (eRet == Acad::eOk) { // ReSetDimPoint(); // 传递修改消息 if (m_pOwnerEnt != NULL && m_pOwnerEnt->objectId().isValid()) { // 创建接口更改消息 TInterfaceModifyMsg iMsg; iMsg.SetMsgPoint(ptGet); iMsg.SetGripPosition(ePos); iMsg.SetMoveGripOffset(offset); iMsg.SetMsgValidate(TRUE); iMsg.SetInterfaceOper(eMoveGripPoint); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); AcGeVector3d vtStart, vtEnd; GetDirect(vtStart, vtEnd); //更新自身模型空间的扩展字典的接口信息 ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, vtStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, vtEnd); } } else m_pXDataMap->SetAt(HDCT_Bulge, dOrigBulge); } return eRet; } // Acad::ErrorStatus THImpHvacDuct::MoveDimGripPointsAt(Position ePos, const AcGeVector3d& offset) // { // ASSERT(NULL != m_pXDataMap); // // AcGePoint3d ptDim; // m_pXDataMap->GetAt(HVAC_DimBasePos, ptDim); // ptDim += offset; // m_pXDataMap->SetAt(HVAC_DimBasePos, ptDim); // m_pXDataMap->GetAt(HVAC_DimBasePos, ptDim); // return Acad::eOk; // // return Acad::eNotImplementedYet; // } Acad::ErrorStatus THImpHvacDuct::MoveSizeGripPointsAt(Position ePos, const AcGeVector3d& offset) { ASSERT(NULL != m_pXDataMap); Acad::ErrorStatus eRet = Acad::eOk; AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptMid = TAuxTools::Mid(ptStart, ptEnd); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptEnd - ptStart; vtDirect.normalize(); AcGeVector3d vtPerp = vtDirect; vtPerp.rotateBy(PI * 0.5, vtNormal); double dSizeMain(0.0), dSizeThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dSizeMain); m_pXDataMap->GetAt(HDCT_Thick, dSizeThick); double dNewWidth(dSizeMain), dNewThick(dSizeThick); HvacDuctType eDuctType = eStraight; HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); AcGePoint3d ptNewStart; AcGePoint3d ptNewEnd; if (IsVertAlignment()) { if (eSectType == eRectangular) { AcGeVector3d vtOrthPlanNormal = vtNormal; // 要投影到的面的法向 AcGeVector3d vtLeftSide = vtNormal; vtLeftSide.rotateBy(PI * 0.5, vtDirect); if (ePos == eSizeMid0 || ePos == eSizeMid1) vtOrthPlanNormal = vtLeftSide; AcGeVector3d vtOrth = offset.orthoProject(vtOrthPlanNormal); ptNewStart = ptStart + vtOrth * 0.5; ptNewEnd = ptEnd + vtOrth * 0.5; SetStartPoint(ptNewStart); SetEndPoint(ptNewEnd); double dExtLen = vtOrth.length(); // 找出相反方向(即尺寸变小情况) if ((ePos == eSizeMid0 && !vtOrth.isCodirectionalTo(vtNormal)) || (ePos == eSizeMid1 && vtOrth.isCodirectionalTo(vtNormal)) || (ePos == eSizeMid2 && !vtOrth.isCodirectionalTo(vtLeftSide)) || (ePos == eSizeMid3 && vtOrth.isCodirectionalTo(vtLeftSide)) ) { dExtLen *= -1; } if (ePos == eSizeMid0 || ePos == eSizeMid1) { dNewThick = dSizeThick + dExtLen; if (dNewThick > 1e-6) m_pXDataMap->SetAt(HDCT_Thick, dNewThick); else eRet = Acad::eNotImplementedYet; } else if (ePos == eSizeMid2 || ePos == eSizeMid3) { dNewWidth = dSizeMain + dExtLen; if (dNewWidth > 1e-6) m_pXDataMap->SetAt(HDCT_Width, dNewWidth); else eRet = Acad::eNotImplementedYet; } } else if (eSectType == eCircular) { AcGePoint3d ptGet = GetAVertCirSizePt(); ptGet += offset; double dNewRadius = ptGet.distanceTo(ptMid); if (dNewRadius > 1e-6) m_pXDataMap->SetAt(HDCT_Diameter, dNewRadius*2); else eRet = Acad::eNotImplementedYet; } } else { AcGeVector3d vtDirectNonZ = vtDirect; // 投影到中截面(考虑到斜管,要平行Z轴)上有效向量,且用户拖拽时,要忽略Z坐标 AcGeVector3d vtUcsZ = TAuxTools::GetUcsZvt(); AcGeVector3d vtOrth = offset.orthoProject(vtUcsZ); // 要投影到风管截面垂直方向上的面 vtOrth = vtOrth.orthoProject(vtDirect); double dExtLen = vtOrth.length(); ptNewStart = ptStart + vtOrth * 0.5; ptNewEnd = ptEnd + vtOrth * 0.5; SetStartPoint(ptNewStart); SetEndPoint(ptNewEnd); // 找出相反方向(即尺寸变小情况) if (ePos == eSizeMid0 && !vtOrth.isCodirectionalTo(vtPerp) || ePos == eSizeMid1 && vtOrth.isCodirectionalTo(vtPerp)) { dExtLen *= -1; } dNewWidth = dSizeMain + dExtLen; if (dNewWidth > 1e-6) m_pXDataMap->SetAt(HDCT_Width, dNewWidth); else eRet = Acad::eNotImplementedYet; if (eDuctType == eSoft && !IsCanDrawSoft()) eRet = Acad::eNotImplementedYet; } if (eRet == Acad::eOk) { // 传递修改消息 if (m_pOwnerEnt != NULL && m_pOwnerEnt->objectId().isValid()) { //BEGIN================================================================= TDbHvacDuct *pDuctEnt = TDbHvacDuct::cast(m_pOwnerEnt); if (pDuctEnt != NULL) { pDuctEnt->UpdateDimData(); } //END=================================================================== BOOL bAutoSize(FALSE); GetGlobalContext(HVAC_AUTOSIZE, bAutoSize); if (bAutoSize) { AcGeVector3d vtUcsZ = TAuxTools::GetUcsZvt(); AcGeVector3d vtOrth = offset.orthoProject(vtUcsZ); vtOrth = vtOrth.orthoProject(vtDirect); AcGePoint3d ptDragOld; // 先/后拖拽点 if (IsVertAlignment()) { if (ePos == eSizeMid0) ptDragOld = ptMid + dSizeThick * 0.5 * vtNormal; else if (ePos == eSizeMid1) ptDragOld = ptMid - dSizeThick * 0.5 * vtNormal; else { AcGeVector3d vtLeftSide = vtNormal; vtLeftSide.rotateBy(PI * 0.5, TAuxTools::GetUcsZvt()); if (ePos == eSizeMid2) ptDragOld = ptMid + dSizeMain * 0.5 * vtLeftSide; else if (ePos == eSizeMid3) ptDragOld = ptMid - dSizeMain * 0.5 * vtLeftSide; } } else { if (ePos == eSizeMid0) ptDragOld = ptMid + dSizeMain * 0.5 * vtPerp; else if (ePos == eSizeMid1) ptDragOld = ptMid - dSizeMain * 0.5 * vtPerp; } // 创建接口更改消息 TInterfaceModifyMsg iMsg; iMsg.SetMsgPoint(ptDragOld); iMsg.SetGripPosition(ePos); iMsg.SetSize(dNewWidth, dNewThick); iMsg.SetSizeDir(vtPerp, vtNormal); iMsg.SetMsgValidate(TRUE); iMsg.SetMoveGripOffset(vtOrth*0.5); iMsg.SetInterfaceOper(eSize); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); acedPostCommand(_T("Redraw\n")); // 暂用于响应尺寸消息后,没有更新接口记录问题 } //更新自身模型空间的扩展字典的接口信息 ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptStart, ptNewStart); ((TDbInterfacesObj*)m_pOwnerEnt)->UpdateInterfaceRec(ptEnd, ptNewEnd); } } else { SetStartPoint(ptStart); SetEndPoint(ptEnd); m_pXDataMap->SetAt(HDCT_Width, dSizeMain); m_pXDataMap->SetAt(HDCT_Thick, dSizeThick); } return eRet; } Acad::ErrorStatus THImpHvacDuct::MoveCommandGripPointsAt(Position ePos, const AcGeVector3d& offset) { ASSERT(NULL != m_pXDataMap); // 获得夹点命令 CString sCmdStr; GetGlobalContext()->GetAt(KEY_HVACGRIPCMD, sCmdStr); if (sCmdStr.IsEmpty()) return Acad::eNotApplicable; // 创建接口更改消息 TInterfaceModifyMsg iMsg; AcGePoint3d ptDrag; if (ePos == eCommand0) ptDrag = StartPoint(); else if (ePos == eCommand1) ptDrag = EndPoint(); else if (ePos == eCommand2) ptDrag = (StartPoint() + EndPoint().asVector()) * 0.5; iMsg.SetMsgPoint(ptDrag); iMsg.SetGripPosition(ePos); iMsg.SetMoveGripOffset(offset); iMsg.SetMsgValidate(TRUE); iMsg.SetInterfaceOper(eNewCommand); iMsg.SetPreviewObjToCreate(ePipe, 0); // 写入接口更改消息 AcDbSoftPointerId idOwner; m_pXDataMap->GetAt(KEY_THISID, idOwner); iMsg.SetMsgOperateOn(idOwner); TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); // 发送消息 acedPostCommand(_T("\33")); acedPostCommand(sCmdStr + _T("\n")); return Acad::eOk; } AcGePoint3d THImpHvacDuct::GetCirCenter() const { ASSERT(NULL != m_pXDataMap); int nType(0); m_pXDataMap->GetAt(HDCT_Type, nType); if (HvacDuctType(nType) != eSoft) return AcGePoint3d(0,0,0); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs(dBulge); double dAngle = atan(dPosiBulge) * 4; AcGeVector3d vtLevel = ptE - ptS; vtLevel.rotateBy(-PI * 0.5, vtNormal); vtLevel.normalize(); vtLevel *= ptS.distanceTo(ptE) * 0.5 * dBulge; AcGePoint3d ptArcMid = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; ptArcMid += vtLevel; dAngle /= 4; double dDist = ptArcMid.distanceTo(ptE) * 0.5; double dRadius = dDist / sin(dAngle); vtLevel.normalize(); AcGePoint3d ptCenter = ptArcMid - dRadius * vtLevel; return ptCenter; } double THImpHvacDuct::GetRadius() const { ASSERT(NULL != m_pXDataMap); int nType(0); m_pXDataMap->GetAt(HDCT_Type, nType); if (HvacDuctType(nType) != eSoft) return 0; AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs(dBulge); double dAngle = atan(dPosiBulge) * 4; AcGeVector3d vtLevel = ptE - ptS; vtLevel.rotateBy(-PI * 0.5, vtNormal); vtLevel.normalize(); vtLevel *= ptS.distanceTo(ptE) * 0.5 * dBulge; AcGePoint3d ptArcMid = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; ptArcMid += vtLevel; dAngle /= 4; double dDist = ptArcMid.distanceTo(ptE) * 0.5; double dRadius = dDist / sin(dAngle); return dRadius; } BOOL THImpHvacDuct::IsCanDrawSoft() const { ASSERT(NULL != m_pXDataMap); double dWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); double dRadius = GetRadius(); if (dRadius - dWidth < 1e-3) return FALSE; return TRUE; } AcGePlane THImpHvacDuct::GetHidePlane(AcGePoint3d pt1, AcGePoint3d pt2, AcGePoint3d pt3, const AcGeVector3d vtNormal, double &dEle) const { ASSERT(NULL != m_pXDataMap); AcGePlane plan(pt1, pt2, pt3); AcGePoint3d ptOrth = AcGePoint3d::kOrigin.orthoProject(plan); plan.set(ptOrth, vtNormal); dEle = ptOrth.asVector().length(); if (!ptOrth.asVector().isCodirectionalTo(vtNormal)) dEle *= -1.0; return plan; } // void THImpHvacDuct::ReSetDimPoint() const // { // ASSERT(NULL != m_pXDataMap); // // AcGePoint3d ptStart = StartPoint(); // AcGePoint3d ptEnd = EndPoint(); // AcGePoint3d ptMid = TAuxTools::Mid(ptStart, ptEnd); // AcGePoint3d ptDimPos; // double dDimPercent = 0.7; // 标注点在管线起始端至中点位置百分比 // // AcGeVector3d vtNormal = normal(); // AcGeVector3d vtPerp = vtNormal.crossProduct(ptEnd - ptStart); // vtPerp.normalize(); // // HvacDuctType eDuctType = eStraight; // m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); // // // 获得软风管的曲率 // double dBulge = 0.0; // m_pXDataMap->GetAt(HDCT_Bulge, dBulge); // // if (eStraight == eDuctType || fabs(dBulge) < 1e-6) // { // ptDimPos = ptStart + (ptMid - ptStart) * dDimPercent; // } // else if(eSoft == eDuctType) // { // double dHight = ptStart.distanceTo(ptEnd) * 0.5 * dBulge; // ptMid -= (vtPerp * dHight); // // double dAngle = atan(dBulge) * 2; // AcGePoint3d ptCenter = GetCirCenter(); // ptDimPos = ptMid; // ptDimPos.rotateBy(-(dAngle * (1 - dDimPercent*2/3)), vtNormal, ptCenter); // } // // m_pXDataMap->SetAt(HVAC_DimBasePos, ptDimPos); // } // 对于水平、斜管,四个点为沿管长方向的中心截面的四个点 // 对于立管,四个点为沿起遮挡作用的最高面四个点 /* 水平管 3━━━━━━━━━━2 ┃ ──→ ┃ ┃━━━━━━━━━ ┃ ┃ ┃ 0━━━━━━━━━━1 立管 ←vtSide ↑vtNormal 矩形 圆形 3━━━━━2 /~~2~~\ ┃ ┃ / \ ┃ ┃ 3 1 ┃ ┃ \ / 0━━━━━1 \__0__/ width */ void THImpHvacDuct::GetFourKeyPoints( AcGePoint3dArray &ptArr ) const { ASSERT(NULL != m_pXDataMap); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); //BEGIN============================================ //AcGeVector3d vtNormal = normal(); AcGeVector3d vtNormal; int iRet = m_pXDataMap->GetAt(KEY_NORMAL, vtNormal); if (iRet == 0) { AfxMessageBox(_T("Get Normal Failed!")); } //NED============================================== if (vtNormal.length() < 1E-9) return; vtNormal.normalize();// Lixl add 2011-12-21 13:18防止应用层传递进来的不是标准化向量 HvacDuctType eDuctType = eStraight; HvacSectType eSectType = eRectangular; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); double dWidth(0.0), dHeigh(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dHeigh); double dBulge(0.0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); AcGePoint3d ptCenter = GetCirCenter(); if (IsVertAlignment()) { AcGeVector3d vtDirect = ptE.z > ptS.z ? (ptE - ptS):(ptS - ptE); if (vtDirect.length() < 1e-9) vtDirect = TAuxTools::GetUcsZvt(); else vtDirect.normalize(); AcGePoint3d ptStd = ptE.z > ptS.z ? ptE:ptS; AcGeVector3d vtSide = vtNormal; vtSide.rotateBy(PI * 0.5, vtDirect); if (eDuctType == eSoft && fabs(dBulge) > 1e-6) { vtSide = ptStd - ptCenter; vtSide.normalize(); if (dBulge < 0) vtSide *= -1; } if (eSectType == eRectangular) { ptArr.append(ptStd + dWidth * 0.5 * vtSide - dHeigh * 0.5 * vtNormal); ptArr.append(ptArr[0] - dWidth * vtSide); ptArr.append(ptArr[1] + dHeigh * vtNormal); ptArr.append(ptArr[2] + dWidth * vtSide); } else if (eSectType == eCircular) { ptArr.append(ptStd - dWidth * 0.5 * vtNormal); ptArr.append(ptStd - dWidth * 0.5 * vtSide); ptArr.append(ptArr[0] + dWidth * vtNormal); ptArr.append(ptArr[1] + dWidth * vtSide); } if (eDuctType == eSoft) { AcGePlane planStd = GetStdPrjPlan(ptStd); int i(0); for (i = 0; i < ptArr.length(); i++) { ptArr[i] = ptArr[i].orthoProject(planStd); } } } else { double dHalfWidth = dWidth * 0.5; if (eDuctType == eStraight) { // change by hh 2011-11-14 修正倾斜风管点计算错误的问题 // AcGeVector3d vtSide = vtNormal; // AcGeVector3d vtDirect = ptE - ptS; AcGeVector3d vtSide = AcGeVector3d::kZAxis; AcGePlane plan(ptS, AcGeVector3d::kZAxis); AcGePoint3d ptSS = ptS.orthoProject(plan); AcGePoint3d ptEE = ptE.orthoProject(plan); AcGeVector3d vtDirect = ptEE - ptSS; vtDirect.normalize(); vtSide.rotateBy(-PI * 0.5, vtDirect); ptArr.append(ptS - dHalfWidth * vtSide); ptArr.append(ptE - dHalfWidth * vtSide); ptArr.append(ptE + dHalfWidth * vtSide); ptArr.append(ptS + dHalfWidth * vtSide); } else if (eDuctType == eSoft && fabs(dBulge) > 1e-6) { AcGeVector3d vtStaDir = ptS - ptCenter; AcGeVector3d vtEndDir = ptE - ptCenter; vtStaDir.normalize(); vtEndDir.normalize(); ptArr.append(ptS + dHalfWidth * vtStaDir); ptArr.append(ptE + dHalfWidth * vtEndDir); ptArr.append(ptE - dHalfWidth * vtEndDir); ptArr.append(ptS - dHalfWidth * vtStaDir); } if (!IsHorzAlignment()) { AcGePoint3d ptCenter = TAuxTools::Mid(ptS, ptE); AcGePlane planStd = GetStdPrjPlan(ptCenter); int i(0); int nLength = ptArr.length(); for (i = 0; i < nLength; i++) { ptArr[i] = ptArr[i].orthoProject(planStd); } } } //BEGIN========================================================= int nLength = ptArr.length(); if (nLength == 0) { AfxMessageBox(_T("The pointArray returned NULL")); } //END=========================================================== } /* 3━━━━━━━2 ┃ ┃ ┃━━━━━━ ┃ ┃ ┃ 0━━━━━━━1 */ void THImpHvacDuct::GetSingleKeyPoints(AcGePoint3dArray &ptArr) const { ASSERT(NULL != m_pXDataMap); double dHideWidth(50.0); GetGlobalContext()->GetAt(KEY_HIDEWIDTH, dHideWidth); // 遮挡标高 // double dHideEle(0.0); // m_pXDataMap->GetAt(HVAC_Elevation, dHideEle); AcGePoint3dArray ptOrigArr; GetFourKeyPoints(ptOrigArr); if (4 != ptOrigArr.length()) return; double dOffset = (ptOrigArr[0].distanceTo(ptOrigArr[3]) - dHideWidth) * 0.5; AcGeVector3d vt0To3((ptOrigArr[3] - ptOrigArr[0]).normalize()); AcGeVector3d vt1To2((ptOrigArr[2] - ptOrigArr[1]).normalize()); ptArr.append(ptOrigArr[0] + dOffset * vt0To3); ptArr.append(ptOrigArr[1] + dOffset * vt1To2); ptArr.append(ptOrigArr[2] - dOffset * vt1To2); ptArr.append(ptOrigArr[3] - dOffset * vt0To3); // int i(0); // for (i = 0; i < ptArr.length(); i++) // { // ptArr[i].z = dHideEle; // } } AcGePoint3d THImpHvacDuct::GetAdjustPt() const { ASSERT(NULL != m_pXDataMap); HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); if (eDuctType != eSoft) return AcGePoint3d(0,0,0); // 获得始末点和重点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptMid = TAuxTools::Mid(ptStart, ptEnd); // 获得方向向量 AcGeVector3d vtDirect = (ptMid - ptStart); vtDirect.normalize(); // 获得垂直向量 AcGeVector3d vtNormal = normal(); AcGeVector3d vtPerp = vtNormal.crossProduct(vtDirect); // 获得软风管的曲率 double dBulge = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); double dAngle = atan(dBulge) * 2; AcGePoint3d ptCenter = GetCirCenter(); AcGePoint3d ptAdjust; double dAdjustPercent = 0.7; // 调节点在管线起始端至中点位置百分比 // 调整中心点 double dHight = ptStart.distanceTo(ptEnd) * 0.5 * dBulge; ptMid -= (vtPerp * dHight); // 找到调节点位置 ptAdjust = ptMid; ptAdjust.rotateBy(-(dAngle * (1 - dAdjustPercent)), vtNormal, ptCenter); return ptAdjust; } AcGePoint3d THImpHvacDuct::GetAVertCirSizePt() const { ASSERT(NULL != m_pXDataMap); double dRadius; m_pXDataMap->GetAt(HDCT_Width, dRadius); dRadius *= 0.5; // 获得始末点和重点 AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGePoint3d ptMid = TAuxTools::Mid(ptStart, ptEnd); // 获得方向向量 AcGeVector3d vtDirect = (ptMid - ptStart); vtDirect.normalize(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtSide = vtNormal; HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); if (eType == eSoft) { double dBulge; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); double dAngle = atan(dBulge) * 4; vtDirect.rotateBy(dAngle * 0.5, vtNormal); // 得到末端界面垂直的法向 } vtSide.rotateBy(-PI * 0.5, vtDirect); AcGePoint3d ptSize = ptMid + dRadius * vtSide; return ptSize; } void THImpHvacDuct::GetArcPoint(AcDbPolyline &polyLine, AcGePoint3dArray &ptArcArr) const { if (polyLine.numVerts() != 4) return; double dPara1(0.0), dPara2(0.0); double dPar1, dPar2; AcGePoint3d pt0, pt1, pt2, pt3, ptMid; polyLine.getPointAt(0, pt0); polyLine.getPointAt(1, pt1); polyLine.getPointAt(2, pt2); polyLine.getPointAt(3, pt3); polyLine.getParamAtPoint(pt0, dPar1); polyLine.getParamAtPoint(pt1, dPar2); polyLine.getPointAtParam((dPar1 + dPar2)*0.5, ptMid); ptArcArr.append(pt0); ptArcArr.append(ptMid); ptArcArr.append(pt1); polyLine.getParamAtPoint(pt1, dPar1); polyLine.getParamAtPoint(pt2, dPar2); polyLine.getPointAtParam((dPar1 + dPar2)*0.5, ptMid); ptArcArr.append(ptMid); ptArcArr.append(pt2); polyLine.getParamAtPoint(pt2, dPar1); polyLine.getParamAtPoint(pt3, dPar2); polyLine.getPointAtParam((dPar1 + dPar2)*0.5, ptMid); ptArcArr.append(ptMid); ptArcArr.append(pt3); if (polyLine.isClosed()) { polyLine.getParamAtPoint(pt3, dPar1); polyLine.getEndParam(dPar2); polyLine.getPointAtParam((dPar1 + dPar2)*0.5, ptMid); ptArcArr.append(ptMid); ptArcArr.append(pt0); } } BOOL THImpHvacDuct::IsValid(TDbXDataMap* pXMap) { if (NULL == m_pXDataMap) return FALSE; // 注意:pXMap == NULL表示不想得到返回值,只是判断数据是否合理 // 先取出m_pXDataMap中数据进行判断是否合理,返回判断结果 // 如果pXMap不为NULL,则将有效参数填入pXMap return FALSE; } AcDbObjectId THImpHvacDuct::GetBaseLayerId() const { AcDbObjectId idBaseLayer(AcDbObjectId::kNull); TDbPipeBase* pFit = TDbPipeBase::cast(m_pOwnerEnt); if (NULL != pFit) idBaseLayer = pFit->CenterLayer(); return idBaseLayer; } Acad::ErrorStatus THImpHvacDuct::getSplitCurves( const AcGePoint3dArray& points, AcDbVoidPtrArray& curveSegments ) const { Acad::ErrorStatus eSta = Acad::eNotImplementedYet; AcDbArc arc; if (InitArc(arc)) eSta = arc.getSplitCurves(points, curveSegments); else eSta = TDbImpPipeBase::getSplitCurves(points, curveSegments); return eSta; } Acad::ErrorStatus THImpHvacDuct::getSplitCurves( const AcGeDoubleArray& params, AcDbVoidPtrArray& curveSegments ) const { Acad::ErrorStatus eSta = Acad::eNotImplementedYet; AcDbArc arc; if (InitArc(arc)) { eSta = arc.getSplitCurves(params, curveSegments); } else eSta = TDbImpPipeBase::getSplitCurves(params, curveSegments); return eSta; } Acad::ErrorStatus THImpHvacDuct::getStartPoint( AcGePoint3d& x0 ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getStartPoint(x0); } else return TDbImpPipeBase::getStartPoint(x0); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getStartParam( double& x0 ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getStartParam(x0); } else return TDbImpPipeBase::getStartParam(x0); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getEndPoint( AcGePoint3d& x0 ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getEndPoint(x0); } else return TDbImpPipeBase::getEndPoint(x0); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getEndParam( double& x0 ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getEndParam(x0); } else return TDbImpPipeBase::getEndParam(x0); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getParamAtDist(double dist,double& param) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getParamAtDist(dist, param); } else return TDbImpPipeBase::getParamAtDist(dist, param); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getParamAtPoint(const AcGePoint3d& x0,double& x1)const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getParamAtPoint(x0, x1); } else return TDbImpPipeBase::getParamAtPoint(x0, x1); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getPointAtDist(double x0,AcGePoint3d& x1) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getPointAtDist(x0, x1); } else return TDbImpPipeBase::getPointAtDist(x0, x1); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getPointAtParam(double x0,AcGePoint3d& x1) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getPointAtParam(x0, x1); } else return TDbImpPipeBase::getPointAtParam(x0, x1); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getDistAtPoint( const AcGePoint3d& x0, double& x1 ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getDistAtPoint(x0, x1); } else return TDbImpPipeBase::getDistAtPoint(x0, x1); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getDistAtParam( double param, double& dist ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getDistAtParam(param, dist); } else return TDbImpPipeBase::getDistAtParam(param, dist); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getClosestPointTo( const AcGePoint3d& givenPnt, const AcGeVector3d& direction, AcGePoint3d& pointOnCurve, Adesk::Boolean extend) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getClosestPointTo(givenPnt,direction,pointOnCurve,extend); } else return TDbImpPipeBase::getClosestPointTo(givenPnt,direction,pointOnCurve,extend); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::getClosestPointTo( const AcGePoint3d& givenPnt, AcGePoint3d& pointOnCurve, Adesk::Boolean extend /*= Adesk::kFalse*/ ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.getClosestPointTo(givenPnt, pointOnCurve, extend); } else return TDbImpPipeBase::getClosestPointTo(givenPnt, pointOnCurve, extend); return Acad::eNotImplementedYet; } BOOL THImpHvacDuct::IsArcDuct() const { if (NULL != m_pXDataMap) { HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); return (eType == eSoft); } return FALSE; } TDbXDataMap* THImpHvacDuct::GetSpecialtyDataReadOnly() const { return m_pXDataMap; } BOOL THImpHvacDuct::InitArc(AcDbArc &arc) const { ASSERT(NULL != m_pXDataMap); HvacDuctType eType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eType); if (eType != eSoft) return FALSE; AcGePoint3d ptStart = StartPoint(); AcGePoint3d ptCenter = GetCirCenter(); double dRadius = ptCenter.distanceTo(ptStart); AcGeVector3d vtNormal = normal(); AcGeVector3d vtUcsX(TAuxTools::GetUcsXvt()), vtUcsZ(TAuxTools::GetUcsZvt()); ads_point vtAdsOcsAngle, vtAdsOcsX; acdbWcs2Ecs(asDblArray(vtUcsX), vtAdsOcsX, asDblArray(vtNormal), true); AcGeVector3d vtTX = asVec3d(vtAdsOcsX); AcGeVector3d vtAngle = ptStart - ptCenter; acdbWcs2Ecs(asDblArray(vtAngle), vtAdsOcsAngle, asDblArray(vtNormal), true); double dStaAngle = vtTX.angleTo(vtAngle, vtNormal); vtAngle = EndPoint() - ptCenter; acdbWcs2Ecs(asDblArray(vtAngle), vtAdsOcsAngle, asDblArray(vtNormal), true); double dEndAngle = vtTX.angleTo(vtAngle, vtNormal); // 负曲率时,转换起始终止角 double dBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); if (dBulge < 0) { double dTemp = dStaAngle; dStaAngle = dEndAngle; dEndAngle = dTemp; } arc.setCenter(ptCenter); arc.setNormal(vtNormal); arc.setRadius(dRadius); arc.setStartAngle(dStaAngle); arc.setEndAngle(dEndAngle); return TRUE; } Acad::ErrorStatus THImpHvacDuct::intersectWith( const AcDbEntity* pEnt, AcDb::Intersect intType, const AcGePlane& projPlane, AcGePoint3dArray& points, INT_PTR thisGsMarker /*= 0*/, INT_PTR otherGsMarker /*= 0*/ ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.intersectWith(pEnt,intType,projPlane,points,thisGsMarker,otherGsMarker); } else return TDbImpPipeBase::intersectWith(pEnt,intType,projPlane,points,thisGsMarker,otherGsMarker); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::intersectWith( const AcDbEntity* pEnt, AcDb::Intersect intType, AcGePoint3dArray& points, INT_PTR thisGsMarker /*= 0*/, INT_PTR otherGsMarker /*= 0*/ ) const { if (IsArcDuct()) { AcDbArc arc; if (InitArc(arc)) return arc.intersectWith(pEnt,intType,points,thisGsMarker,otherGsMarker); } else return TDbImpPipeBase::intersectWith(pEnt,intType,points,thisGsMarker,otherGsMarker); return Acad::eNotImplementedYet; } Acad::ErrorStatus THImpHvacDuct::extend( double newParam ) { Acad::ErrorStatus eSta = Acad::eNotImplementedYet; if (IsArcDuct()) { AcDbArc arc; if (!InitArc(arc)) return Acad::eNotImplementedYet; eSta = arc.extend(newParam); if (eSta == Acad::eOk) { AcGePoint3d ptOrigSta, ptNewSta; AcGePoint3d ptOrigEnd, ptNewEnd; getStartPoint(ptOrigSta); getEndPoint(ptOrigEnd); arc.getStartPoint(ptNewSta); arc.getEndPoint(ptNewEnd); SetStartPoint(ptNewSta); SetEndPoint(ptNewEnd); double dStaAngle = arc.startAngle(); double dEndAngle = arc.endAngle(); if (dEndAngle < dStaAngle) dEndAngle += PI*2; double dBulge = tan((dEndAngle - dStaAngle) * 0.25); if (NULL != m_pXDataMap) m_pXDataMap->SetAt(HDCT_Bulge, dBulge); if (m_pOwnerEnt != NULL && !m_pOwnerEnt->objectId().isNull()) { UpdateInterfaceRec(m_pOwnerEnt->objectId(), ptOrigSta, ptNewSta); UpdateInterfaceRec(m_pOwnerEnt->objectId(), ptOrigEnd, ptNewEnd); ((TDbPipeBase*)m_pOwnerEnt)->UpdateCoverDisplay(); } } } else { eSta = TDbImpPipeBase::extend(newParam); } return eSta; } Acad::ErrorStatus THImpHvacDuct::extend( Adesk::Boolean extendStart, const AcGePoint3d& toPoint ) { Acad::ErrorStatus eSta = Acad::eNotImplementedYet; if (IsArcDuct()) { AcDbArc arc; if (!InitArc(arc)) return Acad::eNotImplementedYet; AcGePoint3d ptOn; eSta = arc.getClosestPointTo(toPoint, ptOn, Adesk::kTrue); if (eSta != Acad::eOk) return eSta; AcGePoint3d ptOrigSta, ptNewSta; AcGePoint3d ptOrigEnd, ptNewEnd; ptOrigSta = StartPoint(); ptOrigEnd = EndPoint(); if (NULL != m_pXDataMap) { double dStaAngle = arc.startAngle(); double dEndAngle = arc.endAngle(); if (dEndAngle < dStaAngle) dEndAngle += PI*2; double dBulge = tan((dEndAngle - dStaAngle) * 0.25); m_pXDataMap->SetAt(HDCT_Bulge, dBulge); } if (extendStart) { //if (ptOn.distanceTo(ptOrigEnd) > AcGeContext::gTol.equalPoint()) if (ptOn.distanceTo(ptOrigEnd) > g_globalTol.equalPoint()) // modify by cq TFS8208 { SetStartPoint(ptOn); if (m_pOwnerEnt != NULL && !m_pOwnerEnt->objectId().isNull()) { UpdateInterfaceRec(m_pOwnerEnt->objectId(), ptOrigSta, ptOn); ((TDbPipeBase*)m_pOwnerEnt)->UpdateCoverDisplay(); } } } else { //if (ptOn.distanceTo(ptOrigSta) > AcGeContext::gTol.equalPoint()) if (ptOn.distanceTo(ptOrigSta) > g_globalTol.equalPoint()) // modify by cq TFS8208 { SetEndPoint(ptOn); if (m_pOwnerEnt != NULL && !m_pOwnerEnt->objectId().isNull()) { UpdateInterfaceRec(m_pOwnerEnt->objectId(), ptOrigEnd, ptOn); ((TDbPipeBase*)m_pOwnerEnt)->UpdateCoverDisplay(); } } } } else { eSta = TDbImpPipeBase::extend(extendStart, toPoint); } return eSta; } double THImpHvacDuct::GetEdgeLineWidth() const { BOOL bShow(FALSE); GetGlobalContext( HVAC_SHOWWIDTH, bShow); // add by hh 2011-01-05 从图纸中读取加粗标识 避免全局参数对不同的图纸间的影响 TAuxTools::GetTHvacDataFromDwg(HVAC_SHOWWIDTH, bShow); if (!bShow) return 0.0; ASSERT(NULL != m_pXDataMap); double dWidth(0.0); m_pXDataMap->GetAt(HVAC_EdgeWidth, dWidth); return dWidth; } double THImpHvacDuct::GetCentLineWidth() const { BOOL bShow(FALSE); GetGlobalContext( HVAC_SHOWWIDTH, bShow); // add by hh 2011-01-05 从图纸中读取加粗标识 避免全局参数对不同的图纸间的影响 TAuxTools::GetTHvacDataFromDwg(HVAC_SHOWWIDTH, bShow); if (!bShow) return 0.0; ASSERT(NULL != m_pXDataMap); double dWidth(0.0); m_pXDataMap->GetAt(HVAC_CentWidth, dWidth); return dWidth; } double THImpHvacDuct::GetEndLineWidth() const { BOOL bShow(FALSE); GetGlobalContext( HVAC_SHOWWIDTH, bShow); // add by hh 2011-01-05 从图纸中读取加粗标识 避免全局参数对不同的图纸间的影响 TAuxTools::GetTHvacDataFromDwg(HVAC_SHOWWIDTH, bShow); if (!bShow) return 0.0; ASSERT(NULL != m_pXDataMap); double dWidth(0.0); m_pXDataMap->GetAt(HVAC_EndWidth, dWidth); return dWidth; } // 非立管根据点计算normal后重新设置 AcGeVector3d THImpHvacDuct::ResetNormalByPt() { ASSERT(NULL != m_pXDataMap); AcGeVector3d vtUcsZ = TAuxTools::GetUcsZvt(); AcGeVector3d vtDirect = StartPoint() - EndPoint(); if (vtDirect.isParallelTo(vtUcsZ)) return AcGeVector3d(0,0,0); else if (vtDirect.length() < 1e-9) return AcGeVector3d(0,0,0); AcGeVector3d vtNormal = vtDirect.crossProduct(vtUcsZ); vtNormal.rotateBy(-PI * 0.5, vtDirect); m_pXDataMap->SetAt(HVAC_Normal, vtNormal.normalize()); return vtNormal; } BOOL THImpHvacDuct::IsHideStart() const { ASSERT(NULL != m_pXDataMap); BOOL bNoCheck(FALSE), bHide(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_HIDESTART, bHide); return bHide; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(0, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { return FALSE; m_pXDataMap->SetAt(HDCT_HIDESTART, FALSE); } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacFitting, pFit); if (NULL != pFit) { TDbXDataMap* pMap = pFit->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); ObjectKind eKind; pMap->GetAt(KEY_RUNTIME, (int&)eKind); if (eKind == eTee) { HvacTeeType eTeeType = eOrthoBranch; pMap->GetAt(HTEE_Type, (int&)eTeeType); if (eTeeType == eInsertIntubBranch || eTeeType == eArcuateIntubBranch) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HTEE_StartPoint, ptSta); pMap->GetAt(HTEE_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eCross) { HvacCrossType eCorssType = eOrthoCross; pMap->GetAt(HCRS_Type, (int &)eCorssType); if (eCorssType == eInsertIntubCross|| eCorssType == eArcuateIntubCross) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HCRS_StartPoint, ptSta); pMap->GetAt(HCRS_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } // add by zh 2013-7-24 断管符号隐藏风管边线 else if (eKind == eBroSymbol) { AcGePoint3d ptIns; pMap->GetAt(HBSM_InsertPoint, ptIns); if (ptIf == ptIns) bHide = TRUE; } } } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_HIDESTART, bHide); return bHide; } BOOL THImpHvacDuct::IsHideEnd() const { ASSERT(NULL != m_pXDataMap); BOOL bNoCheck(FALSE), bHide(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_HIDEEND, bHide); return bHide; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(1, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { m_pXDataMap->SetAt(HDCT_HIDEEND, FALSE); return FALSE; } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacFitting, pFit); if (NULL != pFit) { TDbXDataMap* pMap = pFit->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); ObjectKind eKind; pMap->GetAt(KEY_RUNTIME, (int&)eKind); if (eKind == eTee) { HvacTeeType eTeeType = eOrthoBranch; pMap->GetAt(HTEE_Type, (int&)eTeeType); if (eTeeType == eInsertIntubBranch || eTeeType == eArcuateIntubBranch) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HTEE_StartPoint, ptSta); pMap->GetAt(HTEE_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eCross) { HvacCrossType eCorssType = eOrthoCross; pMap->GetAt(HCRS_Type, (int &)eCorssType); if (eCorssType == eInsertIntubCross || eCorssType == eArcuateIntubCross) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HCRS_StartPoint, ptSta); pMap->GetAt(HCRS_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } // add by zh 2013-7-24 断管符号隐藏风管边线 else if (eKind == eBroSymbol) { AcGePoint3d ptIns; pMap->GetAt(HBSM_InsertPoint, ptIns); if (ptIf == ptIns) bHide = TRUE; } } } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_HIDEEND, bHide); return bHide; } BOOL THImpHvacDuct::IsStartConnect() const { BOOL bNoCheck(FALSE), bCon(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_STARTCONNECTED, bCon); return bCon; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(0, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { m_pXDataMap->SetAt(HDCT_STARTCONNECTED, FALSE); return FALSE; } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbInterfacesObj, pObj); if (NULL != pObj) { if (pObj->GetInterface(tIf.GetPosition(), TInterface())) bCon = TRUE; } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_STARTCONNECTED, bCon); return bCon; } BOOL THImpHvacDuct::IsEndConnect() const { BOOL bNoCheck(FALSE), bCon(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_ENDCONNECTED, bCon); return bCon; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(1, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { m_pXDataMap->SetAt(HDCT_ENDCONNECTED, FALSE); return FALSE; } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbInterfacesObj, pObj); if (NULL != pObj) { if (pObj->GetInterface(tIf.GetPosition(), TInterface())) bCon = TRUE; } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_ENDCONNECTED, bCon); return bCon; } void THImpHvacDuct::CopyPropertiesTo(AcDbObjectId& idTgr,unsigned gMatchFlag) { } void THImpHvacDuct::CopyPropertiesTo(AcDbObjectIdArray& arIds,unsigned gMatchFlag) { AcDbObjectId IdDuct = m_pOwnerEnt->objectId(); CString sText; //sText.Format(_T("%ld"), IdDuct.asOldId()); #ifdef _WIN64 sText.Format(_T("%I64u"), IdDuct.asOldId()); #else sText.Format(_T("%ld"), IdDuct.asOldId()); #endif // modify by cq 2017-09-13 支持win10保存64位数据 TFS29618 struct resbuf rbUr; rbUr.restype = RTSTR; rbUr.rbnext = NULL; rbUr.resval.rstring = (LPTSTR)(LPCTSTR)sText; acedSetVar(_T("USERS3"), &rbUr); // 发送消息 acedPostCommand(_T("\33")); acedPostCommand(_T("FGGSS\n")); } // 更新反应器中的标注(移动夹点导致的变化) void THImpHvacDuct::UpdateDimInReactor( Position eGridPos, const AcGeVector3d& vtOff ) { if (NULL == m_pOwnerEnt) return; TDbHvacDuct* pDuct = TDbHvacDuct::cast(m_pOwnerEnt); if (NULL == pDuct) return; // 移动首尾夹点情况 double dAngle(0.0); AcGeVector3d vtNormal = TAuxTools::GetUcsZvt(); AcGePoint3d ptStaic; if (eGridPos == eStart || eGridPos == eEnd) { AcGePoint3d ptSta(StartPoint()), ptEnd(EndPoint()); AcGePoint3d ptMoveOrig, ptMoveNew; // 不动点, 移动前后点 if (eGridPos == eStart) { ptStaic = ptEnd; ptMoveOrig = ptSta - vtOff; ptMoveNew = ptSta; } else { ptStaic = ptSta; ptMoveOrig = ptEnd - vtOff; ptMoveNew = ptEnd; } AcGeVector3d vtOrig = ptMoveOrig - ptStaic; AcGeVector3d vtNew = ptMoveNew - ptStaic; dAngle = vtNew.angleTo(vtOrig); if (vtOrig.crossProduct(vtNew).angleTo(vtNormal) > PI * 0.5) // 逆向角度 dAngle *= -1; } // 更新反应器中其他标注 const AcDbVoidPtrArray* pArrVoidPt = NULL; // 反应器数组 void* pReactSome = NULL; // 反应器指针 AcDbObjectId objId; // 反应器对应实体id pArrVoidPt = pDuct->reactors(); if (NULL == pArrVoidPt || pArrVoidPt->length() < 1) return; int i(0); for (i = 0; i < pArrVoidPt->length(); i++) { pReactSome = pArrVoidPt->at(i); if (acdbIsPersistentReactor(pReactSome)) { objId = acdbPersistentReactorObjectId(pReactSome); OPENOBJ_BEGIN(objId, AcDb::kForWrite, TDbHvacDimension, pDim); if (NULL != pDim) { if (eGridPos == eMid) { AcGeMatrix3d mat; mat.setTranslation(vtOff); pDim->transformBy(mat); } else if (eGridPos == eStart || eGridPos == eEnd) { AcGePoint3d ptDimBase = pDim->GetBasePoint(); ptDimBase.rotateBy(dAngle, vtNormal, ptStaic); pDim->SetBasePoint(ptDimBase); HvacDimType eType = pDim->GetType(); if (eType == eDimInnerPipe || eType == eDimAbovePipe || eType == eDimBelowPipe) { double dOrigAngle = pDim->GetTextAngle(); pDim->SetTextAngle(dOrigAngle + dAngle); } else { // 方向对调时,纠正角度 double dAngle(pDim->GetTextAngle()); AcGeVector3d vtLead(pDim->GetLeadPoint() - pDim->GetBasePoint()); XVector3D vt(cos(dAngle), sin(dAngle), 0); if (vtLead.angleTo(vt) > PI * 0.5) { dAngle += PI; // dAngle = AsStdAngle(dAngle); dAngle = AngleRangeTo2PI(dAngle); pDim->SetTextAngle(dAngle); } } } } OPENOBJ_END(); } } } int THImpHvacDuct::GetXBaseShell(TXShell& xShell) { if (NULL == m_pXDataMap) { return 0; } // 添加实体壁面 AcDbVoidPtrArray entSet; XExplodeStream dc(entSet); double dBulge = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); if (fabs(dBulge) < 1e-6) { double dMinDiffAngOLD = PI/12, dMinDiffAng = PI / 4; GetGlobalContext()->GetAt(KEY_MINDIFFANG, dMinDiffAngOLD); GetGlobalContext()->SetAt(KEY_MINDIFFANG, dMinDiffAng); ExplodeOrDraw3d(dc); GetGlobalContext()->SetAt(KEY_MINDIFFANG, dMinDiffAngOLD); } else { ExplodeOrDraw3d(dc); } int nLen=entSet.length(); for(int i = 0; i < nLen; i++) { AcDbEntity *pEnt=(AcDbEntity *)entSet[i]; if(pEnt->isKindOf(AcDbFace::desc())) { xShell.AppendFace((AcDbFace*)pEnt); } } // 添加实体端口面 HvacSectType eSectType; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (TDb::eRectangular == eSectType) { // 获得参数 double dWidth = 0.0; m_pXDataMap->GetAt(HDCT_Width, dWidth); double dThick = 0.0; m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGeVector3d vtNormal = normal(); vtNormal.normalize(); AcGePoint3d ptStart; m_pXDataMap->GetAt(HDCT_START, ptStart); AcGePoint3d ptEnd; m_pXDataMap->GetAt(HDCT_END, ptEnd); AcGeVector3d vtStart, vtEnd; if (fabs(dBulge) < 1e-6) { vtStart = ptStart - ptEnd; vtStart.normalize(); vtEnd = ptEnd - ptStart; vtEnd.normalize(); } else { AcGePoint3d ptCenter = GetCirCenter(); vtStart = ptCenter - ptStart; vtEnd = ptCenter - ptEnd; if (dBulge > 0.0) { vtStart.rotateBy(PI / 2.0, vtNormal); vtEnd.rotateBy(-PI / 2.0, vtNormal); } else { vtStart.rotateBy(-PI / 2.0, vtNormal); vtEnd.rotateBy(PI / 2.0, vtNormal); } vtStart.normalize(); vtEnd.normalize(); } // 添加端口面 TAuxTools::BuildRecFace(ptStart, dWidth, dThick, vtNormal, vtStart, xShell); TAuxTools::BuildRecFace(ptEnd, dWidth, dThick, vtNormal, vtEnd, xShell); } else if (TDb::eCircular == eSectType) { // 获得参数 double dDiameter = 0.0; m_pXDataMap->GetAt(HDCT_Diameter, dDiameter); AcGeVector3d vtNormal = normal(); vtNormal.normalize(); AcGePoint3d ptStart; m_pXDataMap->GetAt(HDCT_START, ptStart); AcGePoint3d ptEnd; m_pXDataMap->GetAt(HDCT_END, ptEnd); AcGeVector3d vtStart, vtEnd; if (fabs(dBulge) < 1e-6) { vtStart = ptStart - ptEnd; vtStart.normalize(); vtEnd = ptEnd - ptStart; vtEnd.normalize(); } else { AcGePoint3d ptCenter = GetCirCenter(); vtStart = ptCenter - ptStart; vtEnd = ptCenter - ptEnd; if (dBulge > 0.0) { vtStart.rotateBy(PI / 2.0, vtNormal); vtEnd.rotateBy(-PI / 2.0, vtNormal); } else { vtStart.rotateBy(-PI / 2.0, vtNormal); vtEnd.rotateBy(PI / 2.0, vtNormal); } vtStart.normalize(); vtEnd.normalize(); } // 添加端口面 TAuxTools::BuildCirFace(ptStart, dDiameter, vtNormal, vtStart, xShell); TAuxTools::BuildCirFace(ptEnd, dDiameter, vtNormal, vtEnd, xShell); } else { // 不做处理 } return 1; } int THImpHvacDuct::GetBodyBox(AcDbExtents& ext) { if (NULL == m_pXDataMap) { return 0; } // 获得参数 double dWidth = 0.0; m_pXDataMap->GetAt(HDCT_Width, dWidth); double dHalfWidth = dWidth / 2.0; double dThick = 0.0; m_pXDataMap->GetAt(HDCT_Thick, dThick); double dHalfThick = dThick / 2.0; HvacSectType eSectType; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSectType); if (TDb::eCircular == eSectType) { // 处理圆管数据 dHalfThick = dHalfWidth; } AcGeVector3d vtNormal; m_pXDataMap->GetAt(HVAC_Normal, vtNormal); vtNormal.normalize(); AcGePoint3d ptStart; m_pXDataMap->GetAt(HDCT_START, ptStart); AcGePoint3d ptEnd; m_pXDataMap->GetAt(HDCT_END, ptEnd); AcGeVector3d vtSide = ptEnd - ptStart; vtSide.rotateBy(PI / 2.0, vtNormal); vtSide.normalize(); double dBulge = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); // 计算端点 AcGePoint3dArray arpt; arpt.append(ptStart + vtSide * dHalfWidth + vtNormal * dHalfThick); arpt.append(ptStart + vtSide * dHalfWidth - vtNormal * dHalfThick); arpt.append(ptStart - vtSide * dHalfWidth - vtNormal * dHalfThick); arpt.append(ptStart - vtSide * dHalfWidth + vtNormal * dHalfThick); arpt.append(ptEnd + vtSide * dHalfWidth + vtNormal * dHalfThick); arpt.append(ptEnd + vtSide * dHalfWidth - vtNormal * dHalfThick); arpt.append(ptEnd - vtSide * dHalfWidth - vtNormal * dHalfThick); arpt.append(ptEnd - vtSide * dHalfWidth + vtNormal * dHalfThick); if (fabs(dBulge) > 1e-6) { // 计算方向 AcGeVector3d vt = ptEnd - ptStart; if (dBulge > 0.0) { vt.rotateBy(-PI / 2.0, vtNormal); vt.normalize(); } else { vt.rotateBy(PI / 2.0, vtNormal); vt.normalize(); } // 计算偏移距离 double dAng = 4.0 * atan(fabs(dBulge)); double dDis = ptEnd.distanceTo(ptStart); double dOffset = (dDis / 2.0) * (1.0 - cos(dAng / 2.0)) / sin(dAng / 2.0); // 计算顶点 AcGePoint3d pt; Midpoint(ptStart, ptEnd, pt); pt += vt * dOffset; arpt.append(pt); } // 构造最小包含体 TAuxTools::BuildMinRectangle(arpt, ext); return 1; } CString THImpHvacDuct::GetXml(const AcGeMatrix3d& mat) const { if (NULL == m_pXDataMap || NULL == m_pOwnerEnt) return _T(""); int nValue(0); double dValue(0.0); int nSizePreci(3), nPtPreci(6); // 尺寸、位置精度 TXmlTree xmlTree; CString csText; AcGePoint3d pt; CString csX, csY, csZ; POSITION posRoot = xmlTree.Insert(_T("ATS_DBHVACDUCT"), NULL, NULL); { xmlTree.SetAttribute(posRoot, _T("name"), _T("风管")); xmlTree.SetAttribute(posRoot, _T("comment"), _T("上华对象名称")); } POSITION posItemMaterial = xmlTree.Insert(_T("Material"),posRoot, NULL); { xmlTree.SetAttribute(posItemMaterial, _T("name"), _T("风管材料")); xmlTree.SetAttribute(posItemMaterial, _T("comment"), _T("风管使用的材料")); m_pXDataMap->GetAt(HVAC_Material, csText); xmlTree.SetItemText(posItemMaterial, csText); } POSITION posItemSect = xmlTree.Insert(_T("SectionType"),posRoot, posItemMaterial); { xmlTree.SetAttribute(posItemSect, _T("name"), _T("截面类型")); xmlTree.SetAttribute(posItemSect, _T("comment"), _T("风管截面的形状0:矩形,1:圆形")); m_pXDataMap->GetAt(HVAC_SectType, nValue); csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posItemSect, csText); } POSITION posItemWidth = xmlTree.Insert(_T("Width"),posRoot, posItemSect); { xmlTree.SetAttribute(posItemWidth, _T("name"), _T("风管宽度参数")); xmlTree.SetAttribute(posItemWidth, _T("comment"), _T("风管截面的宽度")); m_pXDataMap->GetAt(HDCT_Width, dValue); TAuxTools::DoubleToString(dValue, nSizePreci, csText); xmlTree.SetItemText(posItemWidth, csText); } POSITION posItemHeigh = xmlTree.Insert(_T("Height"),posRoot, posItemWidth); { xmlTree.SetAttribute(posItemHeigh, _T("name"), _T("风管高度参数")); xmlTree.SetAttribute(posItemHeigh, _T("comment"), _T("风管截面的高度")); m_pXDataMap->GetAt(HDCT_Thick, dValue); TAuxTools::DoubleToString(dValue, nSizePreci, csText); xmlTree.SetItemText(posItemHeigh, csText); } AcGeVector3d vt; POSITION posItemNorDir = xmlTree.Insert(_T("NormalDir"),posRoot, posItemHeigh); { xmlTree.SetAttribute(posItemNorDir, _T("name"), _T("法向量")); m_pXDataMap->GetAt(HVAC_Normal, vt); TAuxTools::DoubleToString(vt.x, nPtPreci, csX); TAuxTools::DoubleToString(vt.y, nPtPreci, csY); TAuxTools::DoubleToString(vt.z, nPtPreci, csZ); csText.Format(_T("%s,%s,%s"), csX, csY, csZ); xmlTree.SetItemText(posItemNorDir, csText); } POSITION posItemStaPt = xmlTree.Insert(_T("Start_point"),posRoot, posItemNorDir); { xmlTree.SetAttribute(posItemStaPt, _T("name"), _T("起点位置")); pt = StartPoint(); pt.transformBy(mat); TAuxTools::DoubleToString(pt.x, nPtPreci, csX); TAuxTools::DoubleToString(pt.y, nPtPreci, csY); TAuxTools::DoubleToString(pt.z, nPtPreci, csZ); csText.Format(_T("%s,%s,%s"), csX, csY, csZ); xmlTree.SetItemText(posItemStaPt, csText); } POSITION posItemEndPt = xmlTree.Insert(_T("End_point"),posRoot, posItemStaPt); { xmlTree.SetAttribute(posItemEndPt, _T("name"), _T("终点位置")); pt = EndPoint(); pt.transformBy(mat); TAuxTools::DoubleToString(pt.x, nPtPreci, csX); TAuxTools::DoubleToString(pt.y, nPtPreci, csY); TAuxTools::DoubleToString(pt.z, nPtPreci, csZ); csText.Format(_T("%s,%s,%s"), csX, csY, csZ); xmlTree.SetItemText(posItemEndPt, csText); } TDb::HvacDuctType eDuctType(TDb::eStraight); m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); if (TDb::eSoft == eDuctType) { if (m_pXDataMap->GetAt(HDCT_StartDir, vt)) { POSITION posItemStaVt = xmlTree.Insert(_T("Start_Direct"), posRoot, posItemEndPt); { xmlTree.SetAttribute(posItemStaVt, _T("name"), _T("起点方向")); TAuxTools::DoubleToString(vt.x, nPtPreci, csX); TAuxTools::DoubleToString(vt.y, nPtPreci, csY); TAuxTools::DoubleToString(vt.z, nPtPreci, csZ); csText.Format(_T("%s,%s,%s"), csX, csY, csZ); xmlTree.SetItemText(posItemStaVt, csText); } posItemEndPt = posItemStaVt; } if (m_pXDataMap->GetAt(HDCT_EndDir, vt)) { POSITION posItemEndVt = xmlTree.Insert(_T("End_Direct"), posRoot, posItemEndPt); { xmlTree.SetAttribute(posItemEndVt, _T("name"), _T("终点方向")); TAuxTools::DoubleToString(vt.x, nPtPreci, csX); TAuxTools::DoubleToString(vt.y, nPtPreci, csY); TAuxTools::DoubleToString(vt.z, nPtPreci, csZ); csText.Format(_T("%s,%s,%s"), csX, csY, csZ); xmlTree.SetItemText(posItemEndVt, csText); } posItemEndPt = posItemEndVt; } } POSITION posItemBulge = xmlTree.Insert(_T("Bulge"),posRoot, posItemEndPt); { xmlTree.SetAttribute(posItemBulge, _T("name"), _T("凸度")); xmlTree.SetAttribute(posItemBulge, _T("comment"), _T("弧管弯曲的程度(0时为直管)")); dValue = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dValue); TAuxTools::DoubleToString(dValue, nPtPreci, csText); xmlTree.SetItemText(posItemBulge, csText); } POSITION posObjId = xmlTree.Insert(_T("Object_ID"), posRoot, posItemBulge); { xmlTree.SetAttribute(posObjId, _T("name"),_T("ID")); xmlTree.SetAttribute(posObjId, _T("comment"),_T("风管ID")); csText.Format(_T("%ld"), 0x7FFFFFFF & m_pOwnerEnt->objectId().asOldId()); xmlTree.SetItemText(posObjId, csText); } // begin // add by wc 13-12-05 ///////// POSITION posAirLoadUnit = xmlTree.Insert(_T("AirLoadUnit"), posRoot, posObjId); { xmlTree.SetAttribute(posAirLoadUnit, _T("name"), _T("风量单位")); xmlTree.SetAttribute(posAirLoadUnit, _T("comment"), _T("0:kg/h, 1:kg/s, 2:m^3/h...")); m_pXDataMap->GetAt(HVAC_AirLoadUnit, nValue); csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posAirLoadUnit, csText); } POSITION posAirLoad = xmlTree.Insert(_T("AirLoad"), posRoot, posAirLoadUnit); { xmlTree.SetAttribute(posAirLoad, _T("name"), _T("风量")); xmlTree.SetAttribute(posAirLoad, _T("comment"), _T("风口风量")); m_pXDataMap->GetAt(HVAC_AirLoad, dValue); TAuxTools::DoubleToString(dValue, nSizePreci, csText); xmlTree.SetItemText(posAirLoad, csText); } POSITION posSysName = xmlTree.Insert(_T("System"), posRoot, posAirLoad); { xmlTree.SetAttribute(posSysName, _T("name"), _T("管线类型")); xmlTree.SetAttribute(posSysName, _T("comment"), _T("回风/送风/通风...")); m_pXDataMap->GetAt(HVAC_System, csText); xmlTree.SetItemText(posSysName, csText); } POSITION posSingleLine = xmlTree.Insert(_T("IsSingleLine"), posRoot, posSysName); { xmlTree.SetAttribute(posSingleLine, _T("name"), _T("单线")); xmlTree.SetAttribute(posSingleLine, _T("comment"), _T("是否是单线: 1/是, 0/不是")); csText.Format(_T("%d"), (int)IsSingleLine()); xmlTree.SetItemText(posSingleLine, csText); } POSITION posDuctType = xmlTree.Insert(_T("DuctType"), posRoot, posSingleLine); { xmlTree.SetAttribute(posDuctType, _T("name"), _T("风管类型")); xmlTree.SetAttribute(posDuctType, _T("comment"), _T(" 1/直风管, 2/软风管")); m_pXDataMap->GetAt(HDCT_Type, nValue); csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posDuctType, csText); } POSITION posSoft = xmlTree.Insert(_T("IsSoft"), posRoot, posDuctType); { xmlTree.SetAttribute(posSoft, _T("name"), _T("软风管")); xmlTree.SetAttribute(posSoft, _T("comment"), _T("是否是软风管:0/不是, 1/是")); // 绘制非软风管的 时候好像没有设置这个参数,因此默认为非软风管 if (!m_pXDataMap->GetAt(HDCT_Soft, nValue)) nValue = 0; csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posSoft, csText); } POSITION posHasLiningLine = xmlTree.Insert(_T("HasLiningLine"), posRoot, posSoft); { xmlTree.SetAttribute(posHasLiningLine, _T("name"), _T("内衬线")); xmlTree.SetAttribute(posHasLiningLine, _T("comment"), _T("是否有内衬线:0/不是, 1/是")); if (!m_pXDataMap->GetAt(HVAC_HasLining, nValue)) nValue = 0; csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posHasLiningLine, csText); } POSITION posLiningLineType = xmlTree.Insert(_T("LiningLineType"), posRoot, posHasLiningLine); { AcDbObjectId idType; AcDbObject *pObjType = NULL; ACHAR *pChar = NULL; xmlTree.SetAttribute(posLiningLineType, _T("name"), _T("内衬线型")); xmlTree.SetAttribute(posLiningLineType, _T("comment"), _T("内衬线型的名称")); m_pXDataMap->GetAt(HVAC_LiningLine, idType); if (Acad::eOk != acdbOpenObject(pObjType, idType, AcDb::kForRead)) { } if (NULL != pObjType) { AcDbLinetypeTableRecord *pRec = AcDbLinetypeTableRecord::cast(pObjType); pRec->getName(pChar); pRec->close(); pObjType->close(); csText.Format(_T("%s"), pChar); delete pChar; } else csText.Empty(); xmlTree.SetItemText(posLiningLineType, csText); } POSITION posIsEdgeWidth = xmlTree.Insert(_T("IsEdgeWidth"), posRoot, posLiningLineType); { xmlTree.SetAttribute(posIsEdgeWidth, _T("name"), _T("边线是否加粗")); xmlTree.SetAttribute(posIsEdgeWidth, _T("comment"), _T("0/不加粗, 1/加粗")); if (!m_pXDataMap->GetAt(HVAC_EdgeWeight, nValue)) nValue = 0; csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posIsEdgeWidth, csText); } POSITION posIsCentWidth = xmlTree.Insert(_T("IsCentWidth"), posRoot, posIsEdgeWidth); { xmlTree.SetAttribute(posIsCentWidth, _T("name"), _T("中线是否加粗")); xmlTree.SetAttribute(posIsCentWidth, _T("comment"), _T("0/不加粗, 1/加粗")); if (!m_pXDataMap->GetAt(HVAC_CentWeight, nValue)) nValue = 0; csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posIsCentWidth, csText); } POSITION posIsEndWidth = xmlTree.Insert(_T("IsEndWidth"), posRoot, posIsCentWidth); { xmlTree.SetAttribute(posIsEndWidth, _T("name"), _T("端线是否加粗")); xmlTree.SetAttribute(posIsEndWidth, _T("comment"), _T("0/不加粗, 1/加粗")); if (!m_pXDataMap->GetAt(HVAC_EndWeight, nValue)) nValue = 0; csText.Format(_T("%d"), nValue); xmlTree.SetItemText(posIsEndWidth, csText); } POSITION posEdgeWidth = xmlTree.Insert(_T("EdgeWidth"), posRoot, posIsEndWidth); { xmlTree.SetAttribute(posEdgeWidth, _T("name"), _T("边线加粗量")); xmlTree.SetAttribute(posEdgeWidth, _T("comment"), _T("边线加粗的数值")); m_pXDataMap->GetAt(HVAC_EdgeWidth, dValue); csText.Format(_T("%f"), dValue); xmlTree.SetItemText(posEdgeWidth, csText); } POSITION posCentWidth = xmlTree.Insert(_T("CentWidth"), posRoot, posEdgeWidth); { xmlTree.SetAttribute(posCentWidth, _T("name"), _T("中线加粗量")); xmlTree.SetAttribute(posCentWidth, _T("comment"), _T("中线加粗的数值")); m_pXDataMap->GetAt(HVAC_CentWidth, dValue); csText.Format(_T("%f"), dValue); xmlTree.SetItemText(posCentWidth, csText); } POSITION posEndWidth = xmlTree.Insert(_T("EndWidth"), posRoot, posCentWidth); { xmlTree.SetAttribute(posEndWidth, _T("name"), _T("端线加粗量")); xmlTree.SetAttribute(posEndWidth, _T("comment"), _T("端线加粗的数值")); m_pXDataMap->GetAt(HVAC_EndWidth, dValue); csText.Format(_T("%f"), dValue); xmlTree.SetItemText(posEndWidth, csText); } // end CString csXml = xmlTree.GetXml(); return csXml; } bool THImpHvacDuct::GetSection( const AcDbFace &face, const AcGeVector3d &vtPlaneSecDir, std::vector §ionRecord, AcDbVoidPtrArray& arFillPtrs ) const { if (NULL == m_pOwnerEnt || NULL == m_pXDataMap) return false; double dBulge = 0.0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); if (fabs(dBulge) < 1e-6) // 直风管 return GetStraightSection(face, vtPlaneSecDir, sectionRecord, arFillPtrs); else return GetArcSection(face, vtPlaneSecDir, sectionRecord, arFillPtrs); return false; } bool THImpHvacDuct::GetStraightSection( const AcDbFace &face, const AcGeVector3d &vtPlaneSecDir, std::vector §ionRecord, AcDbVoidPtrArray& arFillPtrs ) const { // 基本参数 AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE - ptS; HvacDrawType eDrawType = eOldStyle; m_pXDataMap->GetAt(HVAC_DrawType, (int&)eDrawType); AcGePoint3d ptTemp; TGGeLine tgLine(LS_FINITE); AcDbObjectId idObj = m_pOwnerEnt->objectId(); AcDbObjectId idLayer = m_pOwnerEnt->layerId(); TGGeSectionPlane section_pln(face, vtPlaneSecDir); // 构造一个辅助剖面 HvacSectType eSect = TDb::eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSect); if (TDb::eRectangular == eSect) { // 判断方向,如果风管轴向垂直投影面,则有填充线 if (vtDirect.isParallelTo(vtPlaneSecDir)) { // 3━━━━━2 // ┃ ┃ // ┃ ┃ // ┃ 起始端 ┃ // ┃ ┃ // ┃ ┃ // 0━━━━━1 // 离剖切线最近端标高 TGGeLine tgLine(LS_FINITE), tgLineOut(LS_FINITE); tgLine.SetPoints(ptS, ptE); short nRet = SectionUtility::Projection_line2plane(section_pln, tgLine, tgLineOut, ptTemp); AcGePoint3d ptSNew = tgLineOut.StartPoint(); AcGePoint3d ptENew = tgLineOut.EndPoint(); if (1 == nRet) // 线与面垂直 ptSNew = ptENew = ptTemp; // 最小距离即为要传入的标高参数 double dStaDist = ptSNew.distanceTo(ptS); double dEndDist = ptENew.distanceTo(ptE); double dMinDist = dStaDist < dEndDist ? dStaDist : dEndDist; dMinDist *= -1; // 基本点 AcGePoint3d ptBase(ptS); // 端部基点,要投影方向那一端 if (vtDirect.isCodirectionalTo(vtPlaneSecDir)) // 为了多根重合风管剖切填充线一致 { ptBase = ptE; vtDirect *= -1; } double dWidth(0.0), dThick(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); AcGeVector3d vtNormal = normal(); AcGeVector3d vtLevel = vtDirect; vtLevel.normalize(); vtLevel.rotateBy(PI * 0.5, vtNormal); AcGePoint3d ptArrSide[4]; ptArrSide[0] = ptBase - dThick * 0.5 * vtNormal + dWidth * 0.5 * vtLevel; ptArrSide[1] = ptArrSide[0] - dWidth * vtLevel; ptArrSide[2] = ptArrSide[1] + dThick * vtNormal; ptArrSide[3] = ptArrSide[0] + dThick * vtNormal; // 端部面,构造端部面才有遮挡 TGGePoly2D poly2d; poly2d.AppendNode(ptArrSide[0]); poly2d.AppendNode(ptArrSide[1]); poly2d.AppendNode(ptArrSide[2]); poly2d.AppendNode(ptArrSide[3]); poly2d.SetClosed(); if (!!poly2d) sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2d)); TSectionFill* pFill = new TSectionFill; pFill->SetBlockRef(false); pFill->SetElevation(dMinDist); pFill->SetLayer(idLayer); // 内部填充样式 if (eDrawType == eOldStyle) { AcGePoint3d ptCenter = TAuxTools::Mid(ptArrSide[0], ptArrSide[2]); AcGePoint3d ptLineMid = TAuxTools::Mid(ptCenter, ptArrSide[3]); tgLine.SetPoints(ptArrSide[0], ptLineMid); SectionUtility::Projection_line2plane(section_pln, tgLine, tgLine, ptTemp); pFill->InsertLine(tgLine); tgLine.SetPoints(ptLineMid, ptArrSide[2]); SectionUtility::Projection_line2plane(section_pln, tgLine, tgLine, ptTemp); pFill->InsertLine(tgLine); } else { tgLine.SetPoints(ptArrSide[0], ptArrSide[2]); SectionUtility::Projection_line2plane(section_pln, tgLine, tgLine, ptTemp); pFill->InsertLine(tgLine); if (eDrawType == eNewImmit) { tgLine.SetPoints(ptArrSide[3], ptArrSide[1]); SectionUtility::Projection_line2plane(section_pln, tgLine, tgLine, ptTemp); pFill->InsertLine(tgLine); } } arFillPtrs.append(pFill); } else { AcDbVoidPtrArray arFaces; XExplodeStream dc(arFaces); ExplodeOrDraw3d(dc); double dElevation(0.0); AcDbEntity* pEnt = NULL; AcDbFace* pFace = NULL; int i(0); for (i = 0; i < arFaces.length(); ++i) { pEnt = (AcDbEntity*)arFaces[i]; if (NULL == pEnt) continue; pFace = AcDbFace::cast(pEnt); if (pFace) { TGGeSectionPlane pln(*pFace, vtPlaneSecDir); TGGePoly2D poly; dElevation = SectionUtility::Projection_plane2plane(section_pln, pln, poly); if(!!poly) // add by hh 2011-03-11 增加投影后的Poly2D有效型判断 sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dElevation, poly)); } delete pEnt; } } } else if (TDb::eCircular == eSect) // 圆管时 { double dRadius(0.0); m_pXDataMap->GetAt(HDCT_Diameter, dRadius); dRadius *= 0.5; TGGeLine tgLine(LS_FINITE), tgLineOut(LS_FINITE); tgLine.SetPoints(ptS, ptE); short nRet = SectionUtility::Projection_line2plane(section_pln, tgLine, tgLineOut, ptTemp); AcGePoint3d ptSNew = tgLineOut.StartPoint(); AcGePoint3d ptENew = tgLineOut.EndPoint(); if (1 == nRet) // 线与面垂直 ptSNew = ptENew = ptTemp; // 最小距离即为要传入的标高参数 double dStaDist = ptSNew.distanceTo(ptS); double dEndDist = ptENew.distanceTo(ptE); double dMinDist = dStaDist < dEndDist ? dStaDist : dEndDist; dMinDist *= -1; // 判断方向,如果风管轴向不垂直投影面,做一个投影到剖切面上的poly2d即可 if (!vtDirect.isParallelTo(vtPlaneSecDir)) { // 求出投影后的矩形四点 AcGePoint3d ptSUp, ptSDown, ptEUp, ptEDown; AcGeVector3d vtDirect = ptE - ptS; // AcGeVector3d vtUp = (vtDirect.rotateBy(PI*0.5, vtPlaneSecDir)).normalize(); AcGeVector3d vtUp = normal(); if(IsVertAlignment()) // 立管 vtUp = (vtDirect.rotateBy(PI*0.5, vtPlaneSecDir)).normalize(); ptSUp = ptS + vtUp * dRadius; ptSDown = ptS - vtUp * dRadius; ptEUp = ptE + vtUp * dRadius; ptEDown = ptE - vtUp * dRadius; // 设置Poly2d后 传入参数 TGGePoly2D poly2d; poly2d.AppendNode(ptSUp); poly2d.AppendNode(ptEUp); poly2d.AppendNode(ptEDown); poly2d.AppendNode(ptSDown); poly2d.SetClosed(); if(!!poly2d) // add by hh 2011-03-11 增加投影后的Poly2D有效型判断 sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2d)); } else // 风管轴向垂直投影面时,把截面圆分解为多边形,并填充内部线 { int i(0); double dRotAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(PI * 2 / dRotAngle); if (nPartNum%2 != 0) // 边数要为偶数,才能和填充线准确接合 nPartNum += 1; dRotAngle = PI * 2 / nPartNum; AcGePoint3d ptNow; AcGeVector3d vtNow = vtPlaneSecDir.crossProduct(normal()); // 各实体统一开始点,接口处多边形才吻合 vtNow.normalize(); vtNow *= dRadius; TGGePoly2D poly2d; for (i = 0; i < nPartNum; i++) { ptNow = ptSNew + vtNow; poly2d.AppendNode(ptNow); vtNow.rotateBy(dRotAngle, vtPlaneSecDir); } poly2d.SetClosed(); if(!!poly2d) // add by hh 2011-03-11 增加投影后的Poly2D有效型判断 sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2d)); // 内部填充线 int nLen = poly2d.Length(); if (nLen < 8) // 边数小于8时,填充线接合会不吻合,不绘制 return true; // 求出两条填充线的首尾点 int nStat1, nStat2; nStat1 = nLen/8; nStat2 = nStat1 + nLen/4; AcGePoint3d ptStat1 = *poly2d.GetAt(nStat1); AcGePoint3d ptEnd1 = ptStat1; ptEnd1.rotateBy(PI, vtPlaneSecDir, ptSNew); AcGePoint3d ptStat2 = *poly2d.GetAt(nStat2); AcGePoint3d ptEnd2 = ptStat2; ptEnd2.rotateBy(PI, vtPlaneSecDir, ptSNew); TSectionFill* pFill = new TSectionFill; pFill->SetBlockRef(false); pFill->SetElevation(dMinDist); pFill->SetLayer(idLayer); if (eDrawType == eOldStyle) // 老式填充方式中的弧分为多个支线段 { AcGePoint3d ptArc = ptEnd1; AcGeVector3d vtOff = ptStat1 - ptEnd1; ptArc += vtOff * 0.25; int nPartLine = 10; // 分为10段 AcGeCircArc3d geArc(ptStat2, ptArc, ptEnd2); double dRadius = geArc.radius(); AcGePoint3d ptCenter = geArc.center(); double dAngle = geArc.endAng() - geArc.startAng(); double dEveAng = dAngle / nPartLine; AcGeVector3d vtEnd = ptStat2 - ptCenter; AcGeVector3d vtSta = ptEnd2 - ptCenter; AcGePoint3d ptNow(ptEnd2) ,ptNext; if (vtDirect.isCodirectionalTo(vtPlaneSecDir)) ptNow = ptStat2; int i(0); for (i = 0; i < nPartLine; i++) { ptNext = ptNow; ptNext.rotateBy(dEveAng, vtDirect, ptCenter); tgLine.SetPoints(ptNow, ptNext); pFill->InsertLine(tgLine); ptNow.rotateBy(dEveAng, vtDirect, ptCenter); } } else { tgLine.SetPoints(ptStat2, ptEnd2); pFill->InsertLine(tgLine); if (eDrawType == eNewImmit) { tgLine.SetPoints(ptStat1, ptEnd1); pFill->InsertLine(tgLine); } } arFillPtrs.append(pFill); } } else { return false; } return true; } // 求出风管边壁四角线上的点数组,组成四个poly2d,(圆形时两段单独处理下) /* ↑默认法向 起始端 ptFirst[2] 3━━━━━2列 剖开后网格 0━━1━━━2━━3━━4━━5... ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 0━━1━━━2━━3━━4━━5... ┃ 起始端 ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ 0━━1━━━2━━3━━4━━5... ┃ ┃ ┃ ┃ ┃ ┃ ┃ 4━━━━━1列 ptFirst[0] 0━━1━━━2━━3━━4━━5... */ bool THImpHvacDuct::GetArcSection( const AcDbFace &face, const AcGeVector3d &vtPlaneSecDir, std::vector §ionRecord, AcDbVoidPtrArray& arFillPtrs ) const { AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); HvacSectType eSect = TDb::eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSect); double dWidth(0.0), dThick(0.0); if (TDb::eRectangular == eSect) { m_pXDataMap->GetAt(HDCT_Width, dWidth); m_pXDataMap->GetAt(HDCT_Thick, dThick); } else { m_pXDataMap->GetAt(HDCT_Diameter, dWidth); dThick = dWidth; } double dBulge(0), dPosiBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); dPosiBulge = fabs(dBulge); double dSignAngle = atan(dBulge) * 4; double dAngle = fabs(dSignAngle); double dMinAngle(TAuxTools::GetMinDiffAngle()); int nPartNum = int(dAngle / dMinAngle) + 1; dMinAngle = dSignAngle / nPartNum; // 实际间隔角度 AcGePoint3d ptCenter = GetCirCenter(); AcGeVector3d vtEvery = ptCenter - ptS; vtEvery.normalize(); AcGePoint3dArray ptArr1, ptArr2, ptArr3, ptArr4; AcGePoint3d ptFirst[4]; ptFirst[0] = ptS + dWidth * 0.5 * vtEvery - dThick * 0.5 * vtNormal; ptFirst[1] = ptFirst[0] + dThick * vtNormal; ptFirst[2] = ptFirst[1] - dWidth * vtEvery; ptFirst[3] = ptFirst[0] - dWidth * vtEvery; ptArr1.append(ptFirst[0]); ptArr2.append(ptFirst[1]); ptArr3.append(ptFirst[2]); ptArr4.append(ptFirst[3]); int i(0); for (i = 0; i < nPartNum; i++) { ptArr1.append(ptArr1.last()); ptArr1.last().rotateBy(dMinAngle, vtNormal, ptCenter); ptArr2.append(ptArr2.last()); ptArr2.last().rotateBy(dMinAngle, vtNormal, ptCenter); ptArr3.append(ptArr3.last()); ptArr3.last().rotateBy(dMinAngle, vtNormal, ptCenter); ptArr4.append(ptArr4.last()); ptArr4.last().rotateBy(dMinAngle, vtNormal, ptCenter); } // 前后上下四边面 TGGePoly2D poly2dForce, poly2dBack, poly2dUp, poly2dDown; for (i = 0; i < ptArr1.length(); i++) { poly2dForce.AppendNode(ptArr1[i]); poly2dDown.AppendNode(ptArr1[i]); } for (i = ptArr2.length() - 1; i > -1; i--) { poly2dForce.AppendNode(ptArr2[i]); poly2dUp.AppendNode(ptArr2[i]); } for (i = 0; i < ptArr3.length(); i++) { poly2dUp.AppendNode(ptArr3[i]); poly2dBack.AppendNode(ptArr3[i]); } for (i = ptArr4.length() - 1; i > -1; i--) { poly2dBack.AppendNode(ptArr4[i]); poly2dDown.AppendNode(ptArr4[i]); } poly2dForce.SetClosed(); poly2dBack.SetClosed(); poly2dUp.SetClosed(); poly2dDown.SetClosed(); // test for (i = 0; i < poly2dForce.Length()-1; i++) { AcDbLine* pLine = new AcDbLine(*poly2dForce.GetPointListAt(i), *poly2dForce.GetPointListAt(i+1)); AddToCurrentSpace(pLine, Adesk::kTrue); } for (i = 0; i < poly2dBack.Length()-1; i++) { AcDbLine* pLine = new AcDbLine(*poly2dBack.GetPointListAt(i), *poly2dBack.GetPointListAt(i+1)); AddToCurrentSpace(pLine, Adesk::kTrue); } for (i = 0; i < poly2dUp.Length()-1; i++) { AcDbLine* pLine = new AcDbLine(*poly2dUp.GetPointListAt(i), *poly2dUp.GetPointListAt(i+1)); AddToCurrentSpace(pLine, Adesk::kTrue); } for (i = 0; i < poly2dDown.Length()-1; i++) { AcDbLine* pLine = new AcDbLine(*poly2dDown.GetPointListAt(i), *poly2dDown.GetPointListAt(i+1)); AddToCurrentSpace(pLine, Adesk::kTrue); } AcDbObjectId idObj = m_pOwnerEnt->objectId(); AcDbObjectId idLayer = m_pOwnerEnt->layerId(); TGGeSectionPlane section_pln(face, vtPlaneSecDir); TGGePoly2D poly2Out; double dMinDist = SectionUtility::Projection_poly2plane(section_pln, poly2dForce, poly2Out); sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2Out)); poly2Out.Reset(); dMinDist = SectionUtility::Projection_poly2plane(section_pln, poly2dBack, poly2Out); sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2Out)); poly2Out.Reset(); dMinDist = SectionUtility::Projection_poly2plane(section_pln, poly2dUp, poly2Out); sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2Out)); poly2Out.Reset(); dMinDist = SectionUtility::Projection_poly2plane(section_pln, poly2dDown, poly2Out); sectionRecord.push_back(TObjSectionRecord(idObj, idLayer, TObjSectionRecord::eTCH_DBHVACDUCT, dMinDist, poly2Out)); return true; } Acad::ErrorStatus THImpHvacDuct::GetExtents( TADSGePoint3d &ptLow, TADSGePoint3d &ptUp ) const { if (NULL == m_pXDataMap) return Acad::eNotImplementedYet; double dHalfHeigh(0.0); HvacSectType eSect = TDb::eRectangular; m_pXDataMap->GetAt(HVAC_SectType, (int&)eSect); if (eSect == eRectangular) m_pXDataMap->GetAt(HDCT_Thick, dHalfHeigh); else m_pXDataMap->GetAt(HDCT_Diameter, dHalfHeigh); dHalfHeigh *= 0.5; AcGePoint3d ptSta = StartPoint(); AcGePoint3d ptEnd = EndPoint(); AcGeVector3d vtNormal = normal(); AcGeVector3d vtUcsZ = TAuxTools::GetUcsZvt(); if (ptSta.z < ptEnd.z) { ptLow = ptSta; ptUp = ptEnd; } else { ptLow = ptEnd; ptUp = ptSta; } if (vtNormal.isParallelTo(vtUcsZ)) { ptLow -= vtNormal * dHalfHeigh; ptUp += vtNormal * dHalfHeigh; } else /*if (vtNormal.isPerpendicularTo(vtUcsZ))*/ // 立管不用修正,暂不考虑斜管 { } return Acad::eOk; } BOOL THImpHvacDuct::TransInclSoftDuct(TDbXDataMap& dataMap) const { if(NULL == m_pXDataMap) return FALSE; // 拷贝原有数据 用于恢复 dataMap.CopyFrom(m_pXDataMap); // 取得计算数据 double dBulge = 0; m_pXDataMap->GetAt(HDCT_Bulge, dBulge); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE - ptS; vtDirect.normalize(); // 计算弧管中点 AcGeVector3d vtLevel = vtDirect; vtLevel.rotateBy(-PI * 0.5, normal()); vtLevel.normalize(); vtLevel *= ptS.distanceTo(ptE) * 0.5 * dBulge; AcGePoint3d ptM = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; ptM += vtLevel; AcGeVector3d vtZ = TAuxTools::GetUcsZvt(); AcGePlane plan(ptM, vtZ); // 投影弧管三个点到中点所在平面 AcGePoint3d ptPlS = ptS.project(plan, vtZ); AcGePoint3d ptPlM = ptM.project(plan, vtZ); AcGePoint3d ptPlE = ptE.project(plan, vtZ); // 计算投影后平面弧管的曲率 AcGeCircArc3d cirArc(ptPlS, ptPlM, ptPlE); AcGePoint3d ptccc = cirArc.center(); dBulge = tan((cirArc.endAng() - cirArc.startAng()) * 0.25); AcGeVector3d vtMid = ptPlM - ptS; AcGeVector3d vtEnd = ptPlE - ptS; AcGeVector3d vtCross = vtMid.crossProduct(vtEnd); if(!vtCross.isCodirectionalTo(TAuxTools::GetUcsZvt())) dBulge *= -1; // 倾斜弧管修正为平面弧管 m_pXDataMap->SetAt(HVAC_Normal, vtZ); m_pXDataMap->SetAt(HDCT_Bulge, dBulge); m_pXDataMap->SetAt(HDCT_START, ptPlS); m_pXDataMap->SetAt(HDCT_END, ptPlE); return TRUE; } Acad::ErrorStatus THImpHvacDuct::GetClipBoundary(TGGePoly2D& poly) const { AcDbPolyline* pLine = MakePolyCurve(); if(NULL == pLine) return Acad::eNotImplementedYet; double dBrWidth = 0; if(!TAuxTools::GetTHvacDataFromDwg(HVAC_PIPEHIDEWIDTH, dBrWidth)) GetGlobalContext()->GetAt(HVAC_PIPEHIDEWIDTH, dBrWidth); if(EQUAL_ZERO(dBrWidth)) { PolyConvert(*pLine, poly); } else { AcDbVoidPtrArray arPLines; pLine->getOffsetCurves(dBrWidth, arPLines); if(0 == arPLines.length()) { PolyConvert(*pLine, poly); } else { PolyConvert(*((AcDbPolyline*)arPLines[0]), poly); for(int i = 0; i < arPLines.length(); i++) { if(NULL != arPLines[i]) delete (AcDbEntity*)arPLines[i]; } } } delete pLine; return Acad::eOk; } bool THImpHvacDuct::IsMeClip() const { return true; } bool THImpHvacDuct::IsClipMe(const TEntityBase* pEnt)const//ok是否被裁剪 { if(NULL == pEnt) return true; //add by dyw 20150409 当图纸复杂时,遮挡的更改影响水管的绘制速度,暂时屏蔽掉 return false; //add end CString sClassName = pEnt->GetMe()->isA()->name(); if(0 == sClassName.Compare(_T("TDbPipe"))) // 水管 { TInterfaceModifyMsg iMsg; iMsg.SetInterfaceOper(TDb::eUpdateCover); iMsg.SetMsgOperateOn(m_pOwnerEnt->objectId()); // 写入接口更改消息 TDbInterfaceMsgWrite msgWrite; msgWrite.WriteInterfaceMsg(iMsg); return true; } return false; } // 得到arc和line的交点中,距离pt近的点 bool GetInterPt(AcDbArc &arc, AcDbLine &line, AcGePoint3d &pt) { AcGePoint3dArray arPts; Acad::ErrorStatus es = arc.intersectWith(&line, AcDb::kExtendBoth, arPts); if (Acad::eOk != es) return false; if (arPts.length() == 1) pt = arPts[0]; else if (2 == arPts.length()) { if (pt.distanceTo(arPts[0]) < pt.distanceTo(arPts[1])) pt = arPts[0]; else pt = arPts[1]; } else return false; return true; } // 根据弧管的方向,修正关键的4个点 void THImpHvacDuct::ConverFourKeyPts( AcGePoint3dArray &ptArr) const { if(NULL == m_pXDataMap) return ; if (!IsArcDuct()) return; AcGeVector3d vtStaDir, vtEndDir, vtNor(normal()); GetDirect(vtStaDir, vtEndDir); // 将起止端点方向旋转,得到实际弧管边界方向 vtStaDir.rotateBy(PI*0.5, vtNor); vtEndDir.rotateBy(PI*0.5, vtNor); AcGePoint3d ptStart(StartPoint()), ptEnd(EndPoint()), ptInter; AcDbLine staline(ptStart, ptStart+vtStaDir); AcDbLine endline(ptEnd, ptEnd+vtEndDir); AcDbArc arc; InitArc(arc); double dWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); double dOrgRadius = arc.radius(); // 原风管外边线 arc.setRadius(dOrgRadius + dWidth*0.5); // 纠正ptArr[0] if (!GetInterPt(arc, staline, ptArr[0])) return; // 纠正ptArr[1] if (!GetInterPt(arc, endline, ptArr[1])) return; // 原风管内边线 arc.setRadius(dOrgRadius - dWidth*0.5); // 纠正ptArr[2] if (!GetInterPt(arc, endline, ptArr[2])) return; // 纠正ptArr[3] if (!GetInterPt(arc, staline, ptArr[3])) return; } void THImpHvacDuct::DisPoseArcPoint(AcGePoint3dArray& ptArr, AcGePoint3d ptC, AcGeVector3d vtNor) const { AcGePoint3d ptOne, ptOther; AcGeVector3d vtOne,vtOther; AcGePoint3dArray ptArrTemp; AcGePoint3d ptIns,ptM; HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); for (int i = 0; i < ptArr.length()-1; ++i) { ptOne = ptArr[i]; ptOther = ptArr[i+1]; if (eDuctType == eStraight) { Midpoint(ptOne, ptOther, ptIns); // 将起止端点方向旋转,得到实际弧管边界方向 AcGeVector3d vtTemp = ptOther - ptOne; vtTemp.rotateBy(PI/2, vtNor); vtTemp.normalize(); if (i%2 == 0) ptM = ptIns + ptIns.distanceTo(ptOne)*vtTemp; else ptM = ptIns - ptIns.distanceTo(ptOne)*vtTemp; } else { vtOne = ptOne - ptC; vtOther = ptOther - ptC; double dA = vtOne.angleTo(vtOther, vtNor); AcGeVector3d vtTemp(vtOne); // 将起止端点方向旋转,得到实际弧管边界方向 vtOne.rotateBy(PI*0.5, vtNor); vtOther.rotateBy(PI*0.5, vtNor); vtOne.normalize(); vtOther.normalize(); AcDbLine staline(ptOne, ptOne + vtOne); AcDbLine endline(ptOther, ptOther + vtOther); AcGePoint3dArray arPts; Acad::ErrorStatus es = staline.intersectWith(&endline, AcDb::kExtendBoth, arPts); if (Acad::eOk != es) return; if (arPts.length() == 1) ptIns = arPts[0]; vtTemp = vtTemp.rotateBy(dA/2, vtNor); vtTemp.normalize(); if (i%2 != 0) ptM = ptIns + ptIns.distanceTo(ptOne)*vtTemp; else ptM = ptIns - ptIns.distanceTo(ptOne)*vtTemp; } ptArrTemp.append(ptOne); ptArrTemp.append(ptM); } ptArrTemp.append(ptOther); ptArr = ptArrTemp; } BOOL THImpHvacDuct::MakeRealHorzSoft2DCurves( TComplexCurve& cplCurve, int nOutOrIn ) const { ASSERT(NULL != m_pXDataMap); double dBulge(0); m_pXDataMap->GetAt(HDCT_Bulge, dBulge); TCurveElement tCurveEle; memset(&tCurveEle, 0, sizeof(TCurveElement)); tCurveEle.bHided = FALSE; tCurveEle.dWidth = 0.0; tCurveEle.gsMark = 0; double dWidth(0.0); m_pXDataMap->GetAt(HDCT_Width, dWidth); AcGePoint3d ptS = StartPoint(); AcGePoint3d ptE = EndPoint(); AcGeVector3d vtDirect = ptE - ptS; AcGeVector3d vtNormal = TAuxTools::GetUcsZvt(); vtDirect.normalize(); AcGeVector3d vtLevel = (ptE - ptS) * 0.5; // 水平法向辅助求点用 vtLevel.rotateBy(-PI * 0.5, vtNormal); vtLevel *= dBulge; AcGePoint3d ptMid = ptS + ptS.distanceTo(ptE) * 0.5 * vtDirect; AcGePoint3d ptArcMid = ptMid + vtLevel; // 圆弧中点 double dEdgeWidth = GetEdgeLineWidth(); BOOL bBaseLine(FALSE); m_pXDataMap->GetAt(HVAC_HasBaseLine, bBaseLine); // AcGePoint3dArray ptArrTop, ptArrBott; double dPara = 100.0; // 按距离100划分 int i(0),nNum(0); HvacDuctType eDuctType = eStraight; m_pXDataMap->GetAt(HDCT_Type, (int&)eDuctType); AcGePoint3d ptC; if (eDuctType == eStraight) { ptArcMid = ptE; double dLen = ptS.distanceTo(ptE); nNum = int(dLen/dPara); AcGeVector3d vecTemp = ptE-ptS; vecTemp.normalize(); AcGeVector3d vt(vecTemp); AcGeVector3d vtN = vecTemp.rotateBy(PI/2.0, vtNormal); vtN.normalize(); AcGePoint3d ptTemp; ptTemp = ptS + vtN * (dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptS + vtN * (-dWidth/2); ptArrBott.append(ptTemp); AcGePoint3d ptTemp1; for (i = 0; i < nNum; i++) { ptTemp1 = ptS + vt * dPara * (i+1); ptTemp = ptTemp1 + vtN * (dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptTemp1 + vtN * (-dWidth/2); ptArrBott.append(ptTemp); } if (dLen - nNum*dPara != 0) { ptTemp1 = ptS + vt * dLen; ptTemp = ptTemp1+ vecTemp * (dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptTemp1 + vecTemp * (-dWidth/2); ptArrBott.append(ptTemp); } } else { ptC = GetCirCenter(); double dR = GetRadius(); double dAngle = atan(dBulge) * 4;; double dArcLen = fabs(dAngle*dR); nNum = int(dArcLen/dPara); double dPerA = dPara*dAngle/dArcLen; AcGeVector3d vecTemp = ptS - ptC; vecTemp.normalize(); AcGePoint3d ptTemp; ptTemp = ptC + vecTemp * (dR+dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptC + vecTemp * (dR-dWidth/2); ptArrBott.append(ptTemp); for (i = 0; i < nNum; i++) { vecTemp = vecTemp.rotateBy(dPerA, vtNormal); vecTemp.normalize(); ptTemp = ptC + vecTemp * (dR+dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptC + vecTemp * (dR-dWidth/2); ptArrBott.append(ptTemp); } if (dArcLen - nNum*dPara != 0) { double dLast = dArcLen - nNum*dPara; dPerA = dLast*dAngle/dArcLen; vecTemp = vecTemp.rotateBy(dPerA, vtNormal); vecTemp.normalize(); ptTemp = ptC + vecTemp * (dR+dWidth/2); ptArrTop.append(ptTemp); ptTemp = ptC + vecTemp * (dR-dWidth/2); ptArrBott.append(ptTemp); } } DisPoseArcPoint(ptArrTop, ptC, vtNormal); DisPoseArcPoint(ptArrBott, ptC, vtNormal); // if (IsSingleLine()) { tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptArcMid; tCurveEle.ptGe[2] = ptE; tCurveEle.dWidth = dEdgeWidth; cplCurve.append(tCurveEle); return TRUE; } if (nOutOrIn == 1 && bBaseLine) { int n = 3; while(n < ptArrTop.length()) { tCurveEle.dWidth = GetCentLineWidth(); if (dBulge > 0) { tCurveEle.ptGe[0] = ptArrBott[n]; tCurveEle.ptGe[1] = ptArrTop[n-2]; tCurveEle.ptGe[2] = ptArrTop[n-2]; } else { tCurveEle.ptGe[0] = ptArrTop[n]; tCurveEle.ptGe[1] = ptArrBott[n-2]; tCurveEle.ptGe[2] = ptArrBott[n-2]; } cplCurve.append(tCurveEle); n = n+4; } if (bBaseLine) { double dCentWidth = GetCentLineWidth(); tCurveEle.dWidth = dCentWidth; tCurveEle.ptGe[0] = ptS; tCurveEle.ptGe[1] = ptArcMid; tCurveEle.ptGe[2] = ptE; tCurveEle.idSubLay = GetBaseLayerId(); cplCurve.append(tCurveEle); } } else if (nOutOrIn == 0) // 边线及两端 { double dEndWidth = GetEndLineWidth(); AcDbObjectId idSideLayer(NULL); m_pXDataMap->GetAt(HVAC_EndLayer, idSideLayer); for (i = 0; i < ptArrTop.length()- 2; ++i) { tCurveEle.dWidth = dEdgeWidth; tCurveEle.ptGe[0] = ptArrTop[i]; tCurveEle.ptGe[1] = ptArrTop[i+1]; tCurveEle.ptGe[2] = ptArrTop[i+2]; cplCurve.append(tCurveEle); i = i+1; } if (!IsEdgeEnd()) { tCurveEle.ptGe[0] = ptArrTop[ptArrTop.length()-1]; tCurveEle.ptGe[1] = ptArrBott[ptArrBott.length()-1]; tCurveEle.ptGe[2] = ptArrBott[ptArrBott.length()-1]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } for (i = 0; i < ptArrBott.length()- 2; ++i) { tCurveEle.idSubLay.setNull(); tCurveEle.dWidth = dEdgeWidth; tCurveEle.ptGe[0] = ptArrBott[i]; tCurveEle.ptGe[1] = ptArrBott[i+1]; tCurveEle.ptGe[2] = ptArrBott[i+2]; cplCurve.append(tCurveEle); i = i+1; } if (!IsEdgeStart()) { tCurveEle.ptGe[0] = ptArrTop[0]; tCurveEle.ptGe[1] = ptArrBott[0]; tCurveEle.ptGe[2] = ptArrBott[0]; tCurveEle.idSubLay = idSideLayer; tCurveEle.dWidth = dEndWidth; cplCurve.append(tCurveEle); } } return TRUE; } BOOL THImpHvacDuct::IsEdgeStart() const { ASSERT(NULL != m_pXDataMap); BOOL bNoCheck(FALSE), bHide(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_HIDEEND, bHide); return bHide; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(0, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { m_pXDataMap->SetAt(HDCT_HIDEEND, FALSE); return FALSE; } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacDuct, pDuct); if (NULL != pDuct) { TDbXDataMap* pMap = pDuct->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); AcGePoint3d ptSta, ptEnd; pMap->GetAt(KEY_START, ptSta); pMap->GetAt(KEY_END, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } OPENOBJ_END(); OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacDuct, pDuct); if (NULL != pDuct) { TDbXDataMap* pMap = pDuct->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); AcGePoint3d ptSta, ptEnd; pMap->GetAt(KEY_START, ptSta); pMap->GetAt(KEY_END, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } OPENOBJ_END(); OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacFitting, pFit); if (NULL != pFit) { TDbXDataMap* pMap = pFit->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); ObjectKind eKind; pMap->GetAt(KEY_RUNTIME, (int&)eKind); if (eKind == eTee) { HvacTeeType eTeeType = eOrthoBranch; pMap->GetAt(HTEE_Type, (int&)eTeeType); if (eTeeType == eInsertIntubBranch || eTeeType == eArcuateIntubBranch) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HTEE_StartPoint, ptSta); pMap->GetAt(HTEE_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eCross) { HvacCrossType eCorssType = eOrthoCross; pMap->GetAt(HCRS_Type, (int &)eCorssType); if (eCorssType == eInsertIntubCross|| eCorssType == eArcuateIntubCross) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HCRS_StartPoint, ptSta); pMap->GetAt(HCRS_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eBroSymbol) { AcGePoint3d ptIns; pMap->GetAt(HBSM_InsertPoint, ptIns); if (ptIf == ptIns) bHide = TRUE; } } } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_HIDEEND, bHide); return bHide; } BOOL THImpHvacDuct::IsEdgeEnd() const { ASSERT(NULL != m_pXDataMap); BOOL bNoCheck(FALSE), bHide(FALSE); GetGlobalContext()->GetAt(HVAC_IsExplodeDraw, bNoCheck); if (bNoCheck) { m_pXDataMap->GetAt(HDCT_HIDEEND, bHide); return bHide; } TInterface tIf; AcDbObjectId idCon(AcDbObjectId::kNull); if (GetInterface(1, tIf)) { idCon = tIf.GetConnectObject(); if (!idCon.isValid()) { m_pXDataMap->SetAt(HDCT_HIDEEND, FALSE); return FALSE; } } OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacDuct, pDuct); if (NULL != pDuct) { TDbXDataMap* pMap = pDuct->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); AcGePoint3d ptSta, ptEnd; pMap->GetAt(KEY_START, ptSta); pMap->GetAt(KEY_END, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } OPENOBJ_END(); OPENOBJ_BEGIN(idCon, AcDb::kForRead, TDbHvacFitting, pFit); if (NULL != pFit) { TDbXDataMap* pMap = pFit->GetSpecialtyData(); if (NULL != pMap) { AcGePoint3d ptIf = tIf.GetPosition(); ObjectKind eKind; pMap->GetAt(KEY_RUNTIME, (int&)eKind); if (eKind == eTee) { HvacTeeType eTeeType = eOrthoBranch; pMap->GetAt(HTEE_Type, (int&)eTeeType); if (eTeeType == eInsertIntubBranch || eTeeType == eArcuateIntubBranch) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HTEE_StartPoint, ptSta); pMap->GetAt(HTEE_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eCross) { HvacCrossType eCorssType = eOrthoCross; pMap->GetAt(HCRS_Type, (int &)eCorssType); if (eCorssType == eInsertIntubCross|| eCorssType == eArcuateIntubCross) { AcGePoint3d ptSta, ptEnd; pMap->GetAt(HCRS_StartPoint, ptSta); pMap->GetAt(HCRS_EndPoint, ptEnd); if (ptIf == ptSta || ptIf == ptEnd) bHide = TRUE; } } else if (eKind == eBroSymbol) { AcGePoint3d ptIns; pMap->GetAt(HBSM_InsertPoint, ptIns); if (ptIf == ptIns) bHide = TRUE; } } } OPENOBJ_END(); m_pXDataMap->SetAt(HDCT_HIDEEND, bHide); return bHide; }