/******************************************************************** created: 2004/02/24 created: 24:2:2004 14:27 filename: f:\tg_dev\telecdev\twtkernal\editpipe.cpp file path: f:\tg_dev\telecdev\twtkernal file base: editpipe file ext: cpp author: 沈睿 purpose: edit pipe *********************************************************************/ #include "stdafx.h" #include #include #include #include #include #include #include #include "jig.h" #include "DrawStandPipeDlg.h" void GetPipeFPickSet(Entity ent, PickSet &ss, BOOL bIsEqElevation = FALSE) { RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); double nElevation(0); OPENOBJ_BEGIN(ent, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ XPoint p1 = pPipe->StartPoint(); XPoint p2 = pPipe->EndPoint(); nElevation = p1.z; p1 = Wcs2Ucs(p1); p2 = Wcs2Ucs(p2); ads_polar(p1, ads_angle(p1, p2), 50, p1); ads_polar(p2, ads_angle(p2, p1), 50, p2); XPoint pt1, pt2, pt3, pt4; ads_polar(p1, ads_angle(p1, p2)+ PI/2, g_nBreakPipeWidth*DocGetPScale(), pt1); ads_polar(p2, ads_angle(p1, p2)- PI/2, g_nBreakPipeWidth*DocGetPScale(), pt2); ads_polar(p1, ads_angle(p2, p1)+ PI/2, g_nBreakPipeWidth*DocGetPScale(), pt3); ads_polar(p2, ads_angle(p2, p1)- PI/2, g_nBreakPipeWidth*DocGetPScale(), pt4); PickSet ssF(SS_FREE); struct resbuf *pointlist; pointlist = ads_buildlist(RTPOINT, &pt1, RTPOINT, &pt3, RTPOINT, &pt2, RTPOINT, &pt4, NULL); ss.Get(_T("F"), pointlist, NULL, rbMask); ads_relrb(pointlist); } OPENOBJ_END(); long len = ss.Length(); if(ss.Length() == 0) return; if(bIsEqElevation){ PickSet ssDel(SS_FREE); for(long i=0;iIsVertical()){ if(fabs(pPipe->StartPoint().z - nElevation) > 0.1) ssDel += entTmp; } OPENOBJ_END(); } ss -= ssDel; } } void GetPipeFPickSet(XPoint p1, XPoint p2, PickSet &ss) { RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); ads_polar(p1, ads_angle(p1, p2), 50, p1); ads_polar(p2, ads_angle(p2, p1), 50, p2); XPoint pt1, pt2, pt3, pt4; ads_polar(p1, ads_angle(p1, p2)+ PI/2, g_nBreakPipeWidth*DocGetPScale(), pt1); ads_polar(p2, ads_angle(p1, p2)- PI/2, g_nBreakPipeWidth*DocGetPScale(), pt2); ads_polar(p1, ads_angle(p2, p1)+ PI/2, g_nBreakPipeWidth*DocGetPScale(), pt3); ads_polar(p2, ads_angle(p2, p1)- PI/2, g_nBreakPipeWidth*DocGetPScale(), pt4); XRectAngle rect(pt1, pt2); // rect.Make(); PickSet ssF(SS_FREE); struct resbuf *pointlist; pointlist = ads_buildlist(RTPOINT, &pt1, RTPOINT, &pt3, RTPOINT, &pt2, RTPOINT, &pt4, RTPOINT, &pt1, NULL); // ss.Get(_T("F"), pointlist, NULL, rbMask); ss.Get(_T("CP"), pointlist, NULL, rbMask); // 2008-7-1 sr 改为cp,F有时候选不中 int len = ss.Length(); ads_relrb(pointlist); } //*************************************************************************************************** // 删除管线 //*************************************************************************************************** void ErasePipeCmd() { g_ssPickFirst.Free(); RBList rbMaskPipe(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); PickSet ss(SS_FREE); while(1){ if(SelectEntities(_T("\n请选择要删除的管线<退出>:"), ss, rbMaskPipe) != RTNORM) break; for(long i=0;iGetNode(0); nodeId2 = pPipe->GetNode(1); ss += nodeId1; ss += nodeId2; } OPENOBJ_END(); } ss.Erase(); } } //*************************************************************************************************** // 图块加粗 //*************************************************************************************************** void ThickBlkPLine(const TCHAR* szBlkName, double dWidth = 0) { AcDbBlockTableRecord *pRecord = NULL; AcDbBlockTable* pBlockTable = NULL; acdbCurDwg()->getBlockTable(pBlockTable, AcDb::kForRead); if(!pBlockTable) return; if(Acad::eOk != pBlockTable->getAt(szBlkName, pRecord, AcDb::kForRead)){ pBlockTable->close(); return; } pBlockTable->close(); if(!pRecord) return; AcDbBlockTableRecordIterator *pIterator; pRecord->newIterator(pIterator); pRecord->close(); if(!pIterator) return; for(pIterator->start(); !pIterator->done(); pIterator->step()){ AcDbEntity *pEnt = NULL; pIterator->getEntity(pEnt, AcDb::kForWrite); if(pEnt){ AcDbPolyline *pll = NULL; if(pll = AcDbPolyline::cast(pEnt)){ pll->setConstantWidth(dWidth*DocGetPScale()); } pEnt->close(); } } delete pIterator; } void SetBlockWidth() { RBList rbMask = ads_buildlist( -4, _T(""), -4, _T(""), -4, _T("or>"), NULL); Entity ent; if(SelectEntity(_T("\n请选择要设定宽度的图块或上华设备<退出>"), ent, rbMask) != RTNORM) return; double nDist(0); if(ads_getdist(NULL, _T("\n请输入图块的宽度 (0 ~ 1)<退出>:"), &nDist) != RTNORM) return; if(nDist > 1 || nDist < 0) return; CString csBlkName; TCHAR szBlkName[256]; if(ent.Is(_T("INSERT"))){ ent.GetData(2, szBlkName); csBlkName = szBlkName; } else{ csBlkName = GetEquipBlkName(ent); ent.GetData(8, szBlkName); } ThickBlkPLine(csBlkName, nDist); PickSet ss(SS_FREE); if(ent.Is(_T("INSERT"))){ RBList rbMask2(RTDXF0, _T("INSERT"), 2, csBlkName, NULL); ss.Get(_T("X"), NULL, NULL, rbMask2); } else{ RBList rbMask2(RTDXF0, _T("ATS_EQUIPMENT"), 8, szBlkName, NULL); ss.Get(_T("X"), NULL, NULL, rbMask2); } UpdateGraphic(ss); } //*************************************************************************************************** // 管线粗细 //*************************************************************************************************** int GetBoldPipeState() { ads_retint(g_bIsPipeThick); return RTNORM; } int SetBoldPipeState() { PostCommand(_T("gxcx "), false); return RTNORM; } void SetPipeThickOrThin() { // RBList rbMaskPipe(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); // PickSet ss(SS_FREE); // ss.Get(_T("X"), NULL, NULL, rbMaskPipe); TDbPsConfig *pConfig = GetDwgPsGlobal(AcDb::kForWrite); if (pConfig){ g_bIsPipeThick = pConfig->IsLineWeight(); g_bIsPipeThick = !g_bIsPipeThick; pConfig->SetLineWeight(g_bIsPipeThick); pConfig->close(); } PickSet ssObj(SS_FREE); if(GetEntByDxf(ssObj, _T("ATS_PIPE,ATS_DOUBLELINEPIPE,ATS_FLANGE,ATS_PIPECANAL"), 1)==Acad::eOk) { UpdateGraphic(ssObj); } // SHads_command(RTSTR, _T("REGEN"), NULL); //更快一些 acedRedraw(NULL,0); } //*************************************************************************************************** // 管线打断 //*************************************************************************************************** void PipeWireBreak() { RBList rbMask = ads_buildlist( -4, _T(""), -4, _T(""), -4, _T("or>"), NULL); Entity entSel; XPoint ptPick, ptPick2; if(SelectEntity1(g_nCurPipeWidth*DocGetPScale(), _T("\n请选取要打断管线的第一截断点<退出>:"), entSel, ptPick, rbMask)==RTNORM) { int nOsMode=0; nOsMode |= OS_INT|OS_NEA; XPushVar vOsMode(_T("OSMODE"), nOsMode); entSel.Redraw(3); if(ads_getpoint(ptPick, _T("\n再点取该管线上另一截断点<退出>: "), ptPick2) != RTNORM) BreakEntity(entSel, ptPick, ptPick); else BreakEntity(entSel, ptPick, ptPick2); entSel.Redraw(4); } return; } //*************************************************************************************************** // 双线倒角 //*************************************************************************************************** void ChamferPipe(Entity entFirst, Entity entSecond, XPoint ptFirst, XPoint ptSecond) { XPoint ptFirstS, ptFirstE, ptSecondS, ptSecondE, ptInt; GetPipePoint(entFirst, ptFirstS, ptFirstE); GetPipePoint(entSecond, ptSecondS, ptSecondE); if(IsPipeVertical(entFirst) || IsPipeVertical(entSecond)){ adsout << _T("\n不能选择立管!"); return; } if(fabs(ptFirstS.z - ptSecondS.z) > 0.01){ //2管线不在同一平面上 adsout << _T("\n2管线不在同一平面上!"); return; } if(GetPipeSys(entFirst) != GetPipeSys(entSecond)){ adsout << _T("\n2管线类型不一致!"); return; } XLine l1(ptFirstS, ptFirstE, 1); XLine l2(ptSecondS, ptSecondE, 1); l1.SetLineFlag(LS_FINITE); l2.SetLineFlag(LS_FINITE); int ret = l2.Intersection(&l1, ptInt); if(ret == 1){ adsout << _T("\n2管线已经相连!"); return; } l1.SetLineFlag(LS_INFINITE); l2.SetLineFlag(LS_INFINITE); ret = l2.Intersection(&l1, ptInt); if(ret == 0){ adsout << _T("\n2管线平行,无法连接!"); return; } int ret1 = ptInt&l1; int ret2 = ptInt&l2; if(ret1 == PR_EXTEND){ //交点在第一根管线延长线上 double nDist1 = ads_distance(ptInt, ptFirstS); double nDist2 = ads_distance(ptInt, ptFirstE); OPENOBJ_BEGIN(entFirst, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ if(nDist1 < nDist2) pPipe->SetStartPoint(ptInt); else pPipe->SetEndPoint(ptInt); } OPENOBJ_END(); } else if(ret1 == PR_INSIDE){//交点在第一根管线上 double nDist1 = ads_distance(ptInt, ptFirstS); double nDist2 = ads_distance(ptFirst, ptFirstS); OPENOBJ_BEGIN(entFirst, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ if(nDist1 < nDist2) pPipe->SetStartPoint(ptInt); else pPipe->SetEndPoint(ptInt); } OPENOBJ_END(); } if(ret2 == PR_EXTEND){ //交点在第二根管线延长线上 double nDist1 = ads_distance(ptInt, ptSecondS); double nDist2 = ads_distance(ptInt, ptSecondE); OPENOBJ_BEGIN(entSecond, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ if(nDist1 < nDist2) pPipe->SetStartPoint(ptInt); else pPipe->SetEndPoint(ptInt); } OPENOBJ_END(); } else if(ret2 == PR_INSIDE){//交点在第二根管线上 double nDist1 = ads_distance(ptInt, ptSecondS); double nDist2 = ads_distance(ptSecond, ptSecondS); OPENOBJ_BEGIN(entSecond, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ if(nDist1 < nDist2) pPipe->SetStartPoint(ptInt); else pPipe->SetEndPoint(ptInt); } OPENOBJ_END(); } } //*************************************************************************************************** // 管线连接 //*************************************************************************************************** void GetLineMax2Pt(XPoint pt1, XPoint pt2, XPoint &pt3, XPoint &pt4) { XLine l1(pt1, pt3, LS_FINITE); XLine l2(pt2, pt3, LS_FINITE); XLine l3(pt1, pt4, LS_FINITE); XLine l4(pt2, pt4, LS_FINITE); double nMaxLen = 0.0; XPoint ptStart, ptEnd; nMaxLen = l1.GetLength() > nMaxLen ? l1.GetLength() : nMaxLen; nMaxLen = l2.GetLength() > nMaxLen ? l2.GetLength() : nMaxLen; nMaxLen = l3.GetLength() > nMaxLen ? l3.GetLength() : nMaxLen; nMaxLen = l4.GetLength() > nMaxLen ? l4.GetLength() : nMaxLen; if(nMaxLen == l1.GetLength()){ pt3 = l1.StartPoint(); pt4 = l1.EndPoint(); return; } if(nMaxLen == l2.GetLength()){ pt3 = l2.StartPoint(); pt4 = l2.EndPoint(); return; } if(nMaxLen == l3.GetLength()){ pt3 = l3.StartPoint(); pt4 = l3.EndPoint(); return; } if(nMaxLen == l4.GetLength()){ pt3 = l4.StartPoint(); pt4 = l4.EndPoint(); return; } } BOOL IsParallel(XLine &l1, XLine &l2) { AcGeVector3d vt1 = XVector3D(l1.EndPoint() - l1.StartPoint()).AsAcGeVector3d(); AcGeVector3d vt2 = XVector3D(l2.EndPoint() - l2.StartPoint()).AsAcGeVector3d(); if(vt1.isParallelTo(vt2)==Adesk::kTrue) //平行 return TRUE; else if(vt1.isCodirectionalTo(vt2)==Adesk::kTrue) //相反 return TRUE; return FALSE; } BOOL Is2PipeParallel(AcDbObjectId id1, AcDbObjectId id2) { XPoint p1, p2, p3, p4; OPENOBJ_BEGIN(id1, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p1 = pPipe->StartPoint(); p2 = pPipe->EndPoint(); } OPENOBJ_END(); OPENOBJ_BEGIN(id2, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p3 = pPipe->StartPoint(); p4 = pPipe->EndPoint(); } OPENOBJ_END(); XLine line1(p1, p2, 1); XLine line2(p3, p4, 1); if(IsParallel(line1,line2)) return TRUE; else return FALSE; } BOOL Is2PipeParallel(Entity ent1, Entity ent2) { XPoint p1, p2, p3, p4; OPENOBJ_BEGIN(ent1, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p1 = pPipe->StartPoint(); p2 = pPipe->EndPoint(); } OPENOBJ_END(); OPENOBJ_BEGIN(ent2, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p3 = pPipe->StartPoint(); p4 = pPipe->EndPoint(); } OPENOBJ_END(); XLine line1(p1, p2, 1); XLine line2(p3, p4, 1); if(IsParallel(line1,line2)) return TRUE; else return FALSE; } //判断2根管线是否是同一直线,且相邻的,且同类型,如果是:返回2端端点 BOOL Is2PipeOnLine(Entity entSel1, Entity entSel2, XPoint &ptMax1, XPoint &ptMax2) { XPoint p1, p2, p3, p4; TPipeSys::SysType sysType1, sysType2; OPENOBJ_BEGIN(entSel1, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p1 = pPipe->StartPoint(); p2 = pPipe->EndPoint(); sysType1 = pPipe->GetSysType(); } OPENOBJ_END(); OPENOBJ_BEGIN(entSel2, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p3 = pPipe->StartPoint(); p4 = pPipe->EndPoint(); sysType2 = pPipe->GetSysType(); } OPENOBJ_END(); if(sysType1 != sysType2){ return FALSE; } XLine line1(p1, p2, 1); XLine line2(p3, p4, 1); if(Is2LineOnLine(line1,line2)){ XPoint ptMin1, ptMin2, ptTmp3, ptTmp4, ptTmp1(p3), ptTmp2(p4); GetLineMax2Pt(p1, p2, ptTmp1, ptTmp2); ptMax1 = ptTmp1; ptMax2 = ptTmp2; if(ptTmp1 != p3 && ptTmp1 != p4){ ptMin1 = ptTmp2 == p3 ? p4 : p3; ptMin2 = ptTmp1 == p2 ? p1 : p2; ptTmp3 = ptTmp1 == p1 ? p2 : p1; ptTmp1 = ptTmp2; //自己的端点 } else{ ptMin1 = ptTmp1 == p3 ? p4 : p3; ptMin2 = ptTmp2 == p2 ? p1 : p2; ptTmp3 = ptTmp2 == p1 ? p2 : p1; ptTmp1 = ptTmp1; } if(ptMin1 == ptMin2){ //端点相同,说明他们相连 return TRUE; } } return FALSE; } void Join2Pipe() { RBList rbMask = ads_buildlist( -4, _T(""), -4, _T(""), -4, _T("or>"), NULL); Entity entSel1, entSel2; XPoint ptPick1, ptPick2; if(SelectEntity1(g_nCurPipeWidth*DocGetPScale(), _T("\n请拾取要连接的第一根管线 <退出>:"), entSel1, ptPick1, rbMask)!=RTNORM) return; if(SelectEntity1(g_nCurPipeWidth*DocGetPScale(), _T("\n请拾取要连接的第二根管线 <退出>:"), entSel2, ptPick2, rbMask)!=RTNORM) return; if(entSel1 == entSel2) return; XPushVar vOsMode(_T("OSMODE"), 0); XPoint p1, p2, p3, p4; TPipeSys::SysType sysType1, sysType2; OPENOBJ_BEGIN(entSel1, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p1 = pPipe->StartPoint(); p2 = pPipe->EndPoint(); sysType1 = pPipe->GetSysType(); } OPENOBJ_END(); OPENOBJ_BEGIN(entSel2, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ p3 = pPipe->StartPoint(); p4 = pPipe->EndPoint(); sysType2 = pPipe->GetSysType(); } OPENOBJ_END(); if(sysType1 != sysType2){ ads_alert(_T("不是同类型管线!")); return; } XLine line1(p1, p2, 1); XLine line2(p3, p4, 1); if(Is2LineOnLine(line1,line2)){ XPoint ptTmp3, ptTmp4, ptTmp1(p3), ptTmp2(p4); GetLineMax2Pt(p1, p2, ptTmp1, ptTmp2); XPoint ptMin1, ptMin2, ptMax1(ptTmp1), ptMax2(ptTmp2); if(ptTmp1 != p3 && ptTmp1 != p4){ ptMin1 = ptTmp2 == p3 ? p4 : p3; ptMin2 = ptTmp1 == p2 ? p1 : p2; ptTmp3 = ptTmp1 == p1 ? p2 : p1; ptTmp1 = ptTmp2; //自己的端点 } else{ ptMin1 = ptTmp1 == p3 ? p4 : p3; ptMin2 = ptTmp2 == p2 ? p1 : p2; ptTmp3 = ptTmp2 == p1 ? p2 : p1; ptTmp1 = ptTmp1; } ///////////////////////////////////////////////////////////////////////////////// // 以下处理4通的管线,选中的2管线合并,置上 //自定义实体缺陷:修改2根相连的管线的遮挡系数,使他们和交叉的另2根管线发生“强制遮挡”,这2根相连的管线无法合并,也就无法遮挡 //处理办法:把和他们交叉的另2管管线也做同样的连接操作,ok if(ptMin1 == ptMin2){ int up, low; BOOL ret = GetInterPipeLevel(ptMax1, ptMax2, ptMax1.z, up, low); OPENOBJ_BEGIN(entSel2, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ pPipe->SetEndPoint(ptMax1); pPipe->SetStartPoint(ptMax2); if(up != 256) pPipe->SetHideLevel(up+1); else pPipe->SetHideLevel(low+1); } OPENOBJ_END(); entSel1.Erase(); PickSet ss(SS_FREE); XPoint ptF1(ptMax1), ptF2(ptMax2); double nAng = ads_angle(ptF1, ptF2); ads_polar(ptF1, nAng, 50, ptF1); ads_polar(ptF2, nAng, -50, ptF2); GetPipeFPickSet(ptF1, ptF2, ss); // DrawLine(ptF2, ptF1); ss-=entSel2; int len = ss.Length(); if(len > 2){ PickSet ssDel(SS_FREE); XLine line1(ptMax1, ptMax2, 1); for(long i=0;iSetEndPoint(ptMax3); pPipe->SetStartPoint(ptMax4); } OPENOBJ_END(); ent2.Erase(); } } return; } ///////////////////////////////////////////////////////////////////////////////// // 以下处理同一直线上不连接的2管线连接 //修改其中一根管线延长至另一根,他们会自动合并成一根 OPENOBJ_BEGIN(entSel2, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ if(pPipe->StartPoint() == ptTmp1) pPipe->SetEndPoint(ptTmp3); else pPipe->SetStartPoint(ptTmp3); } OPENOBJ_END(); } else{ //管线圆角 // cet 2011.2.15 modify 增加对异面管线的处理,生成扣弯 //adsout << _T("\n2根管线不在同一直线上!"); //ChamferPipe(entSel1, entSel2, ptPick1, ptPick2); XPoint ptFirstS, ptFirstE, ptSecondS, ptSecondE, ptInt; GetPipePoint(entSel1, ptFirstS, ptFirstE); GetPipePoint(entSel2, ptSecondS, ptSecondE); if(IsPipeVertical(entSel1) || IsPipeVertical(entSel2)) { adsout << _T("\n不能选择立管!"); return; } if(fabs(ptFirstS.z - ptSecondS.z) > 0.01) //2管线不在同一平面上 { XPoint pt1 = ptFirstS, pt2 = ptFirstE, pt3 = ptSecondS, pt4 = ptSecondE; pt1.z = 0; pt2.z = 0; pt3.z = 0; pt4.z = 0; XLine l1(pt1, pt2, 1); XLine l2(pt3, pt4, 1); l1.SetLineFlag(LS_INFINITE); l2.SetLineFlag(LS_INFINITE); int ret = l2.Intersection(&l1, ptInt); if(ret == 1 || Is2LineOnLine(l1,l2)) // 两管线在XY平面的投影有交点或共线 { if (ret != 1) { int nOsMode=0; xg_getvar(_T("OSMODE"), &nOsMode); nOsMode &= ~0x4000; nOsMode |= OS_INT|OS_NEA|OS_END|OS_INS; XPushVar vOsMode2(_T("OSMODE"), nOsMode); XPoint pt; if (acedGetPoint(NULL, _T("\n请选择扣弯插入点:"), pt) != RTNORM) { return; } pt.Project(&l1, ptInt); } if (!ptInt) { return; } XLine line1(ptFirstS, ptFirstE, 1); XLine line2(ptSecondS, ptSecondE, 1); ptInt.Project(&line1, pt3); ptInt.Project(&line2, pt4); // 根据投影点位置设置管线端点 int ret1 = pt3&line1; int ret2 = pt4&line2; if(ret1 == PR_EXTEND) //交点在第一根管线延长线上 { double nDist1 = ads_distance(pt3, ptFirstS); double nDist2 = ads_distance(pt3, ptFirstE); OPENOBJ_BEGIN(entSel1, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe != NULL) { if(nDist1 < nDist2) { pPipe->SetStartPoint(pt3); } else { pPipe->SetEndPoint(pt3); } } OPENOBJ_END(); } if(ret2 == PR_EXTEND) //交点在第二根管线延长线上 { double nDist1 = ads_distance(pt4, ptSecondS); double nDist2 = ads_distance(pt4, ptSecondE); OPENOBJ_BEGIN(entSel2, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe != NULL) { if(nDist1 < nDist2) { pPipe->SetStartPoint(pt4); } else { pPipe->SetEndPoint(pt4); } } OPENOBJ_END(); } TDbPipe *pNewPipe = NULL; OPENOBJ_BEGIN(entSel2, AcDb::kForRead, TDbPipe, pPipe); if(pPipe != NULL) { pNewPipe = ClonePipe(pPipe); } OPENOBJ_END(); if (pNewPipe != NULL) { pNewPipe->SetStartPoint(pt3); pNewPipe->SetEndPoint(pt4); AddToCurrentSpace(pNewPipe, Adesk::kTrue); } } } else { ChamferPipe(entSel1, entSel2, ptPick1, ptPick2); } } return; } //*************************************************************************************************** // 设备连管 //*************************************************************************************************** extern void DoLinkHydrant(Entity entEq, Entity entPipe); BOOL IsSamePipeSys(Entity entPipe, Entity entEq) { BOOL bRet = FALSE; TCHAR szPipeLay[256]; TCHAR szEqLay[256]; entPipe.GetData(8, szPipeLay); entEq.GetData(8, szEqLay); if((_tcsicmp(szPipeLay, LAY_PIPE_FEED) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_FEED2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_FEED3) == 0) && _tcsicmp(szEqLay, LAY_EQ_FEED) == 0) bRet = TRUE; else if((_tcsicmp(szPipeLay, LAY_PIPE_HEADFEED) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_HEADFEED2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_HEADFEED3) == 0) && _tcsicmp(szEqLay, LAY_EQ_HEADFEED) == 0) bRet = TRUE; else if((_tcsicmp(szPipeLay, LAY_PIPE_HEADBACK) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_HEADBACK2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_HEADBACK3) == 0) && _tcsicmp(szEqLay, LAY_EQ_HEADBACK) == 0) bRet = TRUE; else if(_tcsicmp(szPipeLay, LAY_PIPE_DIRT) == 0 && (_tcsicmp(szEqLay, LAY_EQ_DIRT) == 0 || _tcsicmp(szEqLay, LAY_EQUIP_LEAK) == 0)) bRet = TRUE; else if(_tcsicmp(szPipeLay, LAY_PIPE_USELESS) == 0 && _tcsicmp(szEqLay, LAY_EQ_USELESS) == 0) bRet = TRUE; else if(_tcsicmp(szPipeLay, LAY_PIPE_RAIN) == 0 && _tcsicmp(szEqLay, LAY_EQ_RAIN)) bRet = TRUE; else if((_tcsicmp(szPipeLay, LAY_PIPE_USED) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_USED2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_USED3) == 0) && _tcsicmp(szEqLay, LAY_EQ_USED) == 0) bRet = TRUE; else if((_tcsicmp(szPipeLay, LAY_PIPE_FIRE) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_FIRE2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_FIRE3) == 0) && (_tcsicmp(szEqLay, LAY_EQ_FIRE) == 0 || _tcsicmp(szEqLay, LAY_EQUIP_HYDRANT) == 0)) bRet = TRUE; else if((_tcsicmp(szPipeLay, LAY_PIPE_SPRINKLE) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_SPRINKLE2) == 0 || _tcsicmp(szPipeLay, LAY_PIPE_SPRINKLE3) == 0) && (_tcsicmp(szEqLay, LAY_EQ_SPRINKLE) == 0 || _tcsicmp(szEqLay, LAY_EQUIP_SPRINKLE) == 0)) bRet = TRUE; else if(_tcsicmp(szPipeLay, LAY_PIPE_COAGULATE) == 0 && _tcsicmp(szEqLay, LAY_EQ_COAGULATE) == 0) bRet = TRUE; else if ((_tcsicmp(szPipeLay, LAY_VPIPE_FIRE) == 0 ||_tcsicmp(szPipeLay, LAY_VPIPE_FIRE2) == 0 || _tcsicmp(szPipeLay, LAY_VPIPE_FIRE3) == 0)&& _tcsicmp(szEqLay, LAY_EQUIP_HYDRANT) == 0) // cet 2010.8.31 add 支持消防立管与消火栓的连接 { bRet = TRUE; } else if (_tcsicmp(szPipeLay, LAY_PIPE_USELESS) == 0 && _tcsicmp(szEqLay, LAY_EQUIP_LEAK) == 0) // cet 2010.11.22 add 支持废水与地漏连接 { bRet = TRUE; } return bRet; } void EquipLineToPipe() { Entity entMain; RBList rbMask(RTDXF0, _T("ATS_EQUIPMENT"), 8, _T("*"), NULL); RBList rbMaskPipe(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); if(SelectEntity(_T("\n请选择干管<退出>:"), entMain, rbMaskPipe) != RTNORM) return; PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择需要连接管线的设备<退出>"), ss, rbMask) != RTNORM) return; //先把和干管无关的设备剔除 PickSet ssDel(SS_FREE); for(long m=0;m 0){ AcGePoint3dArray ptArr; PickSet ssPartner(SS_FREE); Entity ent = ss[0L]; XPoint ptLoc; OPENOBJ_BEGIN(ent, AcDb::kForRead, TDbEquipment, pEquip); if(pEquip){ ptLoc = pEquip->GetLocation(); } OPENOBJ_END(); // ptLoc.Project(lineMain, ptNew);//支持干管延长线上连设备 pPipe->getClosestPointTo(ptLoc, ptNew, Adesk::kTrue); ptNew.z = ptLoc.z; ptArr.append(ptLoc); XPoint ptProject = ptNew; ptProject.z = ptStart.z; ptArrMain.append(ptProject); AcGeVector3d vt1 = ptLoc - ptNew; //1进行分组 for(long j=0;jGetLocation(); // ptLoc2.Project(lineMain, ptNew2); pPipe->getClosestPointTo(ptLoc2, ptNew2, Adesk::kTrue); ptNew2.z = ptLoc.z; } OPENOBJ_END(); double dDist = ads_distance(ptNew2, ptNew); AcGeVector3d vt2 = ptLoc2 - ptNew2; if(ads_distance(ptNew2, ptNew) < dShortDist && vt1.dotProduct(vt2) > 0){//共线 ssPartner += ent2; ptArr.append(ptLoc2); } } ssPartner+=ent; ss-=ssPartner; AcDbXline xline; xline.setUnitDir(vt1); xline.setBasePoint(ptLoc); //2进行排序 if(ssPartner.Length() > 1){ SortPoints(ptArr, &xline, FALSE); int nCount = ptArr.length(); for(int i=0; iclone(); pNewPipe->SetBulge(0); pNewPipe->SetStartPoint(ptTmp1); pNewPipe->SetEndPoint(ptTmp2); AddToCurrentSpace(pNewPipe, Adesk::kTrue); } } ptLoc = ptArr[0]; pPipe->getClosestPointTo(ptLoc, ptNew, Adesk::kTrue); ptNew.z = ptLoc.z; if(ptNew != ptLoc) { TDbPipe *pNewPipe = new TDbPipe; pNewPipe = (TDbPipe*)pPipe->clone(); pNewPipe->SetBulge(0); pNewPipe->SetStartPoint(ptNew); pNewPipe->SetEndPoint(ptLoc); AddToCurrentSpace(pNewPipe, Adesk::kTrue); } //3 如果连接喷头的管线与干管有高度差,自动生成扣弯 if(fabs(pPipe->StartPoint().z - ptLoc.z) > 0.01){ XPoint pt1, pt2; pt1 = ptNew; pt2 = ptNew; pt2.z = pPipe->StartPoint().z; TDbPipe *pNewPipe2 = new TDbPipe; pNewPipe2 = (TDbPipe*)pPipe->clone(); pNewPipe2->SetBulge(0); pNewPipe2->SetStartPoint(pt1); pNewPipe2->SetEndPoint(pt2); AcDbObjectId id2 = AddToCurrentSpace(pNewPipe2, Adesk::kTrue); } } } OPENOBJ_END(); // 二,如果有的设备连在干管的延长线上,现在进行延长干管 // 2008-7-24 支持LINE管, 不支持ARC管 sr OPENOBJ_BEGIN(entMain, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ double dBulge = pPipe->GetBulge(); if(fabs(dBulge) > 0.001) //弧就不考虑了 return; } OPENOBJ_END(); AcDbXline xlineMain; xlineMain.setUnitDir(vtMain); xlineMain.setBasePoint(ptStart); ptArrMain.append(ptStart); ptArrMain.append(ptEnd); SortPoints(ptArrMain, &xlineMain, FALSE); int nCountAll = ptArrMain.length(); XPoint ptTmpS = ptArrMain[0]; //第一个投影点 XPoint ptTmpE = ptArrMain[nCountAll-1]; //最后1个投影点 XLine lineTmp(ptTmpS, ptTmpE, 1); if(lineTmp.GetLength() - lineMain.GetLength() > 0.1) { OPENOBJ_BEGIN(entMain, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ double dBulge = pPipe->GetBulge(); if(fabs(dBulge) < 0.001) pPipe->SetPoints(ptTmpS, ptTmpE); } OPENOBJ_END(); } return; } //*************************************************************************************************** // 断管符号 //*************************************************************************************************** extern CString GetEquipLayBySys(TPipeSys::SysType sys); void InsBreakPipeSign() { g_ssPickFirst.Free(); RBList rbMask = ads_buildlist( -4, _T(""), -4, _T(""), -4, _T("or>"), NULL); // RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择需要插入断管符号的管线<退出>"), ss, rbMask) != RTNORM) return; CString csDwb = g_csDwbPath + _T("TwtSys"); XString xsTmp, xsTmp2; if(LoadDwbBlock(csDwb, _T("00000132"), xsTmp) != RTNORM) //断线 return; if(LoadDwbBlock(csDwb, _T("00000478"), xsTmp2) != RTNORM) //双线管断线 return; Entity entLast; double nRotate(0), dDn(0); for(long i=0;iIsVertical()){ nRotate = ads_angle(pPipe->GetStartPoint(), pPipe->GetEndPoint()); // zxl modify 2013.04.22 // dDn = pPipe->GetDnDiameter(); dDn = pPipe->GetDnDiameter() * 100; dDn = dDn / DocGetPScale(); if (DocGetMeterUnitDraw()) { dDn = dDn / 1000.0; } AcDbObjectId nodeId1(NULL), nodeId2(NULL); nodeId1 = pPipe->GetNode(0); OPENOBJ_BEGIN(nodeId1, AcDb::kForRead, TDbPipeNode, pNode1); if(pNode1){ int num = pNode1->GetInterfaceNum(); if(num == 1){ if(pPipe->isKindOf(TDbDoubleLinePipe::desc())) { // cet 2011.8.18 modify 图层没有设置上,图层改为随双线水管图层 // InsEquipmentByName(xsTmp2, pNode1->GetLocation(), nRotate, GetEquipLayBySys(pPipe->GetSysType()), FALSE, FALSE); InsEquipmentByName(xsTmp2, pNode1->GetLocation(), nRotate, pPipe->GetLayer(), FALSE, FALSE); } else InsEquipmentByName(xsTmp, pNode1->GetLocation(), nRotate, GetEquipLayBySys(pPipe->GetSysType()), FALSE, FALSE); entLast.GetLast(); WriteXdata(entLast, _T("TG-LAYER"), szLayer); if(pPipe->isKindOf(TDbDoubleLinePipe::desc())){ OPENOBJ_BEGIN(entLast, AcDb::kForWrite, TDbEquipment, pEquip); if(pEquip){ pEquip->SetScale(dDn); } OPENOBJ_END(); } } } OPENOBJ_END(); nodeId2 = pPipe->GetNode(1); OPENOBJ_BEGIN(nodeId2, AcDb::kForRead, TDbPipeNode, pNode2); if(pNode2){ int num = pNode2->GetInterfaceNum(); if(num == 1){ if(pPipe->isKindOf(TDbDoubleLinePipe::desc())) { // cet 2011.8.18 modify 图层没有设置上,图层改为随双线水管图层 // InsEquipmentByName(xsTmp2, pNode2->GetLocation(), nRotate, GetEquipLayBySys(pPipe->GetSysType()), FALSE, FALSE); InsEquipmentByName(xsTmp2, pNode2->GetLocation(), nRotate, pPipe->GetLayer(), FALSE, FALSE); } else InsEquipmentByName(xsTmp, pNode2->GetLocation(), nRotate, GetEquipLayBySys(pPipe->GetSysType()), FALSE, FALSE); entLast.GetLast(); WriteXdata(entLast, _T("TG-LAYER"), szLayer); if(pPipe->isKindOf(TDbDoubleLinePipe::desc())){ OPENOBJ_BEGIN(entLast, AcDb::kForWrite, TDbEquipment, pEquip); if(pEquip){ pEquip->SetScale(dDn); } OPENOBJ_END(); } } } OPENOBJ_END(); } OPENOBJ_END(); } } //*************************************************************************************************** // 设备移动 //*************************************************************************************************** void MoveEquipment() { g_ssPickFirst.Free(); XPushVar vOrthoMode(_T("ORTHOMODE"), 1); //f8 RBList rbMask(RTDXF0, _T("ATS_EQUIPMENT"), 8, _T("*"), NULL); RBList rbMaskPipe(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); // zxl 2014.02.10 add 去除提示 xg_setvar(_T("CMDECHO"), 0); int nOsMode=0; xg_getvar(_T("OSMODE"), &nOsMode); if(g_bTgOsnap) { nOsMode &= ~0x4000; nOsMode |= OS_INT|OS_NEA|OS_PER|OS_END|OS_CEN; } XPushVar vOsMode(_T("OSMODE"), nOsMode); double dCeltScale = 1; xg_getvar(_T("CELTSCALE"), &dCeltScale); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择需要移动的设备<退出>"), ss, rbMask) != RTNORM) return; XPoint ptIns, ptTemp; double x,y,z; XPointList lstPT; ss.GetExtend(ptIns, &x, &y, &z); for(long i=0;iGetLocation(); lstPT.NewAppend(ptLoc); } OPENOBJ_END(); } XPoint ptUcs = Wcs2Ucs(ptIns); ptUcs.z = 0; int nRet = DragPickSet1(ss, ptUcs); if(nRet != RTNORM) return; for(i=0;iGetLocation(); PickSet ssDim(SS_FREE); RBList rbMaskDim(RTDXF0, _T("ATS_DIMENSION2"), NULL); XPoint ptOldLoc = *lstPT[i]; if(fabs(ptLoc.z - ptOldLoc.z) > 0.01) if(pEquip->upgradeOpen()==Acad::eOk) { ptLoc.z = ptOldLoc.z; pEquip->SetLocation(ptLoc); pEquip->SetInsert(ptLoc); pEquip->downgradeOpen(); } ptOldLoc.z = 0; GetPointPickSet(ptOldLoc, ssDim, rbMaskDim, 650); long lenDim = ssDim.Length(); if(ssDim.Length() == 1){ Entity entDim = ssDim[0L]; OPENOBJ_BEGIN(entDim, AcDb::kForWrite, TDbDimension2, pDim); if(pDim){ AcGeVector3d vectTmp(ptLoc.x - ptOldLoc.x, ptLoc.y - ptOldLoc.y, 0); AcGePoint3dArray gripPoints; AcDbIntArray osnapModes; AcDbIntArray geomIds; pDim->getGripPoints(gripPoints,osnapModes,geomIds); int ptlen = gripPoints.length(); for (int n=0;nmoveGripPointsAt(indices, vectTmp); } } } OPENOBJ_END(); } PickSet ssPipe(SS_FREE); GetPointPickSet(ptLoc, ssPipe, rbMaskPipe, 10); int num = pEquip->GetInterfaceNum(); if(num < 1) continue; AcDbObjectId PipeId = NULL; //如果移动后新位置有管线,而且是自己所接管线,则更新管线起始点 if(ssPipe.Length() > 0){ if(ssPipe.Length() == 1){ Entity entNewPosPipe = ssPipe[0L]; acdbGetObjectId(PipeId, entNewPosPipe); BOOL bFlag = FALSE; for(int m=0;mGetInterface(m, face); if(PipeId == face.m_idPipe){ bFlag = TRUE; break; } } if(!bFlag) continue; for(m=0;mGetInterface(m, face); OPENOBJ_BEGIN(face.m_idPipe, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe && !pPipe->IsVertical()){ XPoint ptStart, ptEnd; pPipe->getStartPoint(ptStart); pPipe->getEndPoint(ptEnd); ptOldLoc.z = ptStart.z; if(ptStart == ptOldLoc) pPipe->SetStartPoint(ptLoc); else if(ptEnd == ptOldLoc) pPipe->SetEndPoint(ptLoc); } OPENOBJ_END(); } } continue; } //如果移动后新位置没有管线,就生成一个新的 double nDnNew(-1); //新引出的管线,管径为设备所接管中最小的一个 for(int m=0;mGetInterface(m, face); PipeId = face.m_idPipe; OPENOBJ_BEGIN(PipeId, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ double nDnTmp = pPipe->GetDnDiameter(); if(nDnTmp < nDnNew || nDnNew < 0) nDnNew = nDnTmp; } OPENOBJ_END(); } OPENOBJ_BEGIN(PipeId, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ TDbPipe *pNewPipe = new TDbPipe; pNewPipe = (TDbPipe*)pPipe->clone(); pNewPipe->SetStartPoint(ptLoc); pNewPipe->SetDnDiameter(nDnNew); pNewPipe->SetEndPoint(*lstPT[i]); AddToCurrentSpace(pNewPipe, Adesk::kTrue); } OPENOBJ_END(); } OPENOBJ_END(); } } //*************************************************************************************************** // 管线置上 //*************************************************************************************************** void SetPipeUp() { RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择需要置上的管线<退出>"), ss, rbMask) != RTNORM) return; for(long i=0;iGetHideLevel(); if(up < pPipeF->GetHideLevel() || up == 1000) up = pPipeF->GetHideLevel(); } OPENOBJ_END(); } if(ssF.Length() == 0) pPipe->SetHideLevel(pPipe->GetHideLevel()+1); else pPipe->SetHideLevel(up+1); } OPENOBJ_END(); } } //*************************************************************************************************** // 管线置下 //*************************************************************************************************** void SetPipeDown() { RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择需要置下的管线<退出>"), ss, rbMask) != RTNORM) return; for(long i=0;iGetHideLevel(); if(low > pPipeF->GetHideLevel() || low == -1000) low = pPipeF->GetHideLevel(); } OPENOBJ_END(); } if(ssF.Length() == 0) pPipe->SetHideLevel(pPipe->GetHideLevel()-1); else pPipe->SetHideLevel(low-1); } OPENOBJ_END(); } } //*************************************************************************************************** // 多线倒角 //*************************************************************************************************** void DoFilletPipe(Entity entMain, PickSet &ss, double iFilletDist) { // zxl 2012.07.23 add if (iFilletDist <= 0.0) { return; } SHads_command(RTSTR, _T(".UNDO"), RTSTR, _T("MARK"), RTNONE); // Make a undo mark cet 2011.5.23 add 取消操作后恢复管线原始长度 XPoint p1, p2, p3, p4, ptMove, ptInter; GetPipePoint(entMain, p1, p2); XLine line1(p1, p2); double nRotate = ads_angle(p1, p2); Entity entTmp; DList lstPt, lstPt2, lstPt3; XCurveSegment seg; for(long i=0;i ads_distance(p4, ptInt) ? p3 : p4; ptTmp4 = ads_distance(p3, ptInt) < ads_distance(p4, ptInt) ? p3 : p4; double nRotate2 = ads_angle(ptInt, ptTmp3); ads_polar(ptInt, nRotate-PI, iFilletDist, ptTmp1); ads_polar(ptInt, nRotate, iFilletDist, ptTmp5); ads_polar(ptInt, nRotate2, iFilletDist, ptTmp2); XLine line3(ptTmp1, ptTmp2, 1); OPENOBJ_BEGIN(ent, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ XPoint ptLoc = pPipe->GetLabelLocation(); pPipe->SetStartPoint(ptTmp2); pPipe->SetEndPoint(ptTmp3); pPipe->SetLabelLocation(ptLoc); } OPENOBJ_END(); lstPt.Append(new XPoint(ptTmp2)); lstPt2.Append(new XPoint(ptTmp1)); lstPt3.Append(new XPoint(ptTmp5)); } TPipePerDocData *pData = GetCurPipeDocData(); pData->ApplyUpdates(); int itype; struct resbuf pointbuf; ads_grread(5, &itype, &pointbuf);//得到动态点pointbuf while(1){ int iRet = ads_grread(5, &itype, &pointbuf);//得到动态点pointbuf ads_point_set(pointbuf.resval.rpoint, ptMove);//ptMove动态点 ptMove = Ucs2Wcs(ptMove); ads_redraw(NULL, 1); //不画线演示 if(itype != 5 && itype != 3) { SHads_command(RTSTR, _T("UNDO"), RTSTR, _T("BACK"), RTNONE); // cet 2011.5.23 add 恢复管线原始长度 break; } AcGeVector3d vectBase(seg.EndPoint().x - seg.StartPoint().x, seg.EndPoint().y - seg.StartPoint().y, 0); AcGeVector3d vectTmp(ptMove.x - ptInter.x, ptMove.y - ptInter.y, 0); double dAng = vectBase.angleTo(vectTmp, AcGeVector3d::kZAxis); for(int j=0;j PI) ptend = pt2; else ptend = pt3; if(itype == 3){ OPENOBJ_BEGIN(entTmp, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ TDbPipe *pNewPipe = new TDbPipe; // zxl 2013.05.30 add 新生成管线标注位置 pNewPipe = (TDbPipe*)pPipe->clone(); bool bDown = true; AcGePoint3d pt = pPipe->GetLabelLocation(); AcGePoint3d ptOnPipe; pPipe->getClosestPointTo(pt, ptOnPipe); double dDist = pt.distanceTo(ptOnPipe); AcGeVector3d vt = pt - ptOnPipe; double dAngle = vt.angleTo(AcGeVector3d::kXAxis); if (dAngle >= 0 && dAngle < PI) { bDown = false; } pNewPipe->SetStartPoint(pt1); pNewPipe->SetEndPoint(ptend); double nRotate1 = ads_angle(Wcs2Ucs(pt1), Wcs2Ucs(ptend)); if(nRotate > PI/2 && nRotate <=PI*3/2) nRotate += PI; XPoint ptPick = pNewPipe->MidPoint(); ptPick = Wcs2Ucs(ptPick); if(bDown) ads_polar(ptPick, nRotate1+PI/2, -dDist, ptPick); else ads_polar(ptPick, nRotate1+PI/2, dDist, ptPick); ptPick = Ucs2Wcs(ptPick); pNewPipe->SetLabelLocation(ptPick); // zxl 2013.05.29 add if (pNewPipe->IsLabelValid()) { pNewPipe->EnableDrawLabel(FALSE); } AddToCurrentSpace(pNewPipe, Adesk::kTrue); } OPENOBJ_END(); } else { XPoint ptTmpUcs1 = Wcs2Ucs(pt1); XPoint ptTmpUcs2 = Wcs2Ucs(ptend); ads_grdraw(ptTmpUcs1, ptTmpUcs2, -1, 0); //演示 } } if(itype == 3) return; } } // 2011.01.04 add 支持弧度倒角 void ArcChamferPipe(Entity ent1, Entity ent2, double dRadius) { // zxl 2012.07.23 add if (dRadius <= 0.0) { return; } double dLen1 = 0.0, dLen2 = 0.0; // 管长 XPoint pt1, pt2, pt3, pt4, ptMid1, ptMid2; GetPipePoint(ent1, pt1, pt2, ptMid1); GetPipePoint(ent2, pt3, pt4, ptMid2); AcDbLine l1(pt1, pt2), l2(pt3, pt4); AcGePoint3dArray arPt1; l1.intersectWith(&l2, AcDb::kExtendBoth, arPt1); // 无交点 if (arPt1.length() != 1) { return; } XPoint pt = arPt1[0]; // 两管交点 dLen1 = pt1.Distance(pt2); dLen2 = pt3.Distance(pt4); // 管长必须大于倒角半径 if (dLen1 < dRadius || dLen2 < dRadius) { return; } AcGeVector3d vt1 = pt - ptMid1, vt2 = pt - ptMid2; vt1.normalize(); vt2.normalize(); XPoint pt5 = pt - vt1 * dRadius, pt6 = pt - vt2 * dRadius; //修改支管端点 OPENOBJ_BEGIN(ent2, AcDb::kForWrite, TDbPipe, pPipe); if (pPipe != NULL) { XPoint ptS, ptE; ptS = pPipe->StartPoint(); ptE = pPipe->EndPoint(); if (ptS.Distance(pt) < 1e-3) { pPipe->SetStartPoint(pt6); } else if (ptE.Distance(pt) < 1e-3) { pPipe->SetEndPoint(pt6); } } OPENOBJ_END(); // 修改主干管 PickSet ss(SS_FREE); RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); GetPointPickSet(Wcs2Ucs(pt), ss, rbMask, 10); ss -= ent1; ss -= ent2; if (ss.Length() == 0) // 没有连接其他管 { OPENOBJ_BEGIN(ent1, AcDb::kForWrite, TDbPipe, pPipe); if (pPipe != NULL) { XPoint ptS, ptE; ptS = pPipe->StartPoint(); ptE = pPipe->EndPoint(); if (ptS.Distance(pt) < 1e-3) { pPipe->SetStartPoint(pt5); } else if (ptE.Distance(pt) < 1e-3) { pPipe->SetEndPoint(pt5); } } OPENOBJ_END(); } AcGeVector3d vtDir = vt1.crossProduct(vt2); vtDir.normalize(); vt1 = vt1.rotateBy(PI / 2, vtDir); vt2 = vt2.rotateBy(PI / 2, vtDir); AcDbLine line1(pt5, pt5 + vt1), line2(pt6, pt6 + vt2); AcGePoint3dArray arPt; line1.intersectWith(&line2, AcDb::kExtendBoth, arPt); if (arPt.length() != 1) { return; } XPoint ptIns = arPt[0]; dRadius = pt5.Distance(ptIns); // 圆弧半径 XPoint ptMid; ptMid.x = (pt5.x + pt6.x) / 2; ptMid.y = (pt5.y + pt6.y) / 2; ptMid.z = (pt5.z + pt6.z) / 2; AcGeVector3d vt = ptMid - ptIns; vt.normalize(); XPoint pt7 = ptIns + vt * dRadius; // 弧上一点 XArc arc(pt5, pt7, pt6); TDbPipe *pNewPipe = NULL; OPENOBJ_BEGIN(ent1, AcDb::kForRead, TDbPipe, pPipe) if (pPipe != NULL) { pNewPipe = ClonePipe(pPipe); } OPENOBJ_END(); arc.GetStartPoint(pt5); arc.GetEndPoint(pt6); pNewPipe->SetPoints(pt5, pt6, arc.Bulge()); // zxl 2013.05.29 add if (pNewPipe->IsLabelValid()) { pNewPipe->EnableDrawLabel(FALSE); } AddToCurrentSpace(pNewPipe, Adesk::kTrue); } // cet 2011.4.27 add 从注册表读取数据 bool ReadRegData(const CString &strKey, double& dVal) { CRegProperty regProp(GetRegLocation(), _T("PipeChamfer")); regProp.SetTopRootKey(HKEY_CURRENT_USER); return regProp.GetValue(strKey, dVal); } // cet 2011.4.27 add 将数据写入注册表 bool WriteRegData(const CString &strKey, double dVal) { CRegProperty regProp(GetRegLocation(), _T("PipeChamfer")); regProp.SetTopRootKey(HKEY_CURRENT_USER); return regProp.SetValue(strKey, dVal); } void FilletPipe() { g_ssPickFirst.Free(); RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); Entity entMain; PickSet ss(SS_FREE); if(SelectEntity(_T("\n请选择主干管<退出>"), entMain, rbMask) != RTNORM) return; if(SelectEntities(_T("\n请选择支管<退出>"), ss, rbMask) != RTNORM) return; double nFilletDist(100); // cet 2011.1.5 modify 支持弧度倒角 // xg_getvar(_T("FilletRad"), &nFilletDist); // CString csPrompt; // csPrompt.Format(_T("\n请输入倒角距离<%.0f>"), nFilletDist); // ads_getreal(csPrompt, &nFilletDist); // // xg_setvar(_T("FilletRad"), nFilletDist); // DoFilletPipe(entMain, ss, nFilletDist); // cet 2011.4.27 add CString strPrompt; nFilletDist = 0.0; ReadRegData(_T("LineChamfer"), nFilletDist); strPrompt.Format(_T("\n请输入倒角距离[弧形倒角(A)]<%.0f>:"), nFilletDist); int nRet; INITGET_BEG(0, _T("A")); // cet 2011.4.27 modify // nRet = ads_getreal(_T("\n请输入倒角距离[弧形倒角(A)]<退出>:"), &nFilletDist); nRet = ads_getreal(strPrompt, &nFilletDist); INITGET_END(); //if (nRet == RTNORM) cet 2011.4.27 modify if (nRet == RTNORM || nRet == RTNONE) { WriteRegData(_T("LineChamfer"), nFilletDist); // cet 2011.4.27 add DoFilletPipe(entMain, ss, nFilletDist); } else if (nRet == RTKWORD) { CString strTip; // cet 2011.4.27 modify //strTip.Format(_T("\n请输入倒角半径<退出>:"), nFilletDist); //if (ads_getreal(strTip, &nFilletDist) == RTNORM) nFilletDist = 0.0; ReadRegData(_T("ArcChamfer"), nFilletDist); strTip.Format(_T("\n请输入倒角半径<%.0f>:"), nFilletDist); nRet = ads_getreal(strTip, &nFilletDist); if (nRet == RTNORM || nRet == RTNONE) { WriteRegData(_T("ArcChamfer"), nFilletDist); // cet 2011.4.27 add for (long i = 0; i < ss.Length(); i++) { ArcChamferPipe(entMain, ss[i], nFilletDist); } } } } //*************************************************************************************************** // 管线延长 //*************************************************************************************************** void ExternPipeByEq() { RBList rbMask(RTDXF0, _T("ATS_EQUIPMENT"),NULL); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择要延长的附件:<退出>"), ss, rbMask) != RTNORM) return; PickSet ssDo(SS_FREE); long len = ss.Length(); for(long i=0;iGetInterfaceNum(); if(num == 1) { ssDo+=ent; } } OPENOBJ_END(); } len = ssDo.Length(); if(len < 1) return; double dDist(1000); ads_getreal(_T("\n请输入延长的距离<1000>:"), &dDist); for(i=0;iGetLocation(); TPipeInterface face; pEquip->GetInterface(0, face); AcDbObjectId nextPipeId = face.m_idPipe; OPENOBJ_BEGIN(nextPipeId, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ XPoint ptStart = pPipe->StartPoint(); XPoint ptEnd = pPipe->EndPoint(); if(ptStart == ptLoc) { AcGeVector3d vt(ptStart - ptEnd); vt.normalize(); vt *= dDist; ptStart += vt; pPipe->SetStartPoint(ptStart); pEquip->SetLocation(ptStart); pEquip->SetInsert(ptStart); } else { AcGeVector3d vt(ptEnd - ptStart); vt.normalize(); vt *= dDist; ptEnd += vt; pPipe->SetEndPoint(ptEnd); pEquip->SetLocation(ptEnd); pEquip->SetInsert(ptEnd); } } OPENOBJ_END(); } OPENOBJ_END(); } } void GetLayerColor(const CString &strlayerName, Adesk::UInt16 &nColor) { AcDbLayerTable *pLayerTbl = NULL; acdbCurDwg()->getLayerTable(pLayerTbl, AcDb::kForRead); if (pLayerTbl != NULL) { if (pLayerTbl->has(strlayerName)) { AcDbLayerTableRecord *pRec = NULL; pLayerTbl->getAt(strlayerName, pRec, AcDb::kForRead); pLayerTbl->close(); if (pRec != NULL) { nColor = pRec->color().colorIndex(); pRec->close(); } } } } void ExternSysPipe() { g_ssPickFirst.Free(); RBList rbMask = ads_buildlist( -4, _T(""), -4, _T(""), -4, _T("or>"), NULL); XPoint ptPick, ptLoc; Entity entSel; if(SelectEntity1(g_nCurPipeWidth*DocGetPScale(), _T("\n请拾取要延长的管线(注意点取靠近要延长的端点) <选择附件延长管线>:"), entSel, ptPick, rbMask)!=RTNORM) { ExternPipeByEq(); return; } double nRotate(0); CString strLayer; // cet 2010.6.23 add Adesk::UInt16 nColor = 0; // cet 2010.6.23 add OPENOBJ_BEGIN(entSel, AcDb::kForRead, TDbPipe, pPipe); if(pPipe){ nRotate = ads_angle(pPipe->GetStartPoint(), pPipe->GetEndPoint()); // cet 2011.8.26 modify 求距离时点不在同一坐标系内 // double nDist1 = ads_distance(ptPick, pPipe->GetStartPoint()); // double nDist2 = ads_distance(ptPick, pPipe->GetEndPoint()); double nDist1 = ads_distance(Ucs2Wcs(ptPick), pPipe->GetStartPoint()); double nDist2 = ads_distance(Ucs2Wcs(ptPick), pPipe->GetEndPoint()); if(nDist1 < nDist2) ptLoc = pPipe->StartPoint(); else ptLoc = pPipe->EndPoint(); strLayer = pPipe->layer(); // cet 2010.6.23 add nColor = pPipe->colorIndex(); // cet 2010.6.23 add } OPENOBJ_END(); if(nRotate > PI) nRotate -= PI; TPipeEdJig jig(ptLoc, ptLoc, 50); jig.m_ptRef = ptLoc; jig.m_nLockAng = nRotate; jig.m_bLock = FALSE; // cet 2010.6.23 add if (nColor == 256) // 随层时查看图层颜色 { GetLayerColor(strLayer, nColor); } if (nColor == 1) // 管线颜色为红色时, 将jig操作时颜色显示为绿色 { jig.IsChangeColor(true); } jig.SetPrompt(_T("\n请点取延长位置点:<退出>")); int ret = jig.DoIt(); if(ret != RTNORM){ return; } ptPick = jig.GetCorrectPt(); if(!ptPick) return; AcDbObjectId id = NULL; OPENOBJ_BEGIN(entSel, AcDb::kForWrite, TDbPipe, pPipe); if(pPipe){ AcDbObjectId nodeId1(NULL), nodeId2(NULL); nodeId1 = pPipe->GetNode(0); nodeId2 = pPipe->GetNode(1); OPENOBJ_BEGIN(nodeId1, AcDb::kForRead, TDbPipeNode, pNode); if(pNode){ XPoint ptTmp = pNode->GetLocation(); if(ptTmp != ptLoc) id = nodeId1; } OPENOBJ_END(); OPENOBJ_BEGIN(nodeId2, AcDb::kForRead, TDbPipeNode, pNode); if(pNode){ XPoint ptTmp = pNode->GetLocation(); if(ptTmp != ptLoc) id = nodeId2; } OPENOBJ_END(); if(ptLoc == pPipe->StartPoint()) pPipe->SetStartPoint(ptPick); else pPipe->SetEndPoint(ptPick); } OPENOBJ_END(); SSearchPipeList *pListAll = new SSearchPipeList(); PickSet ssAll(SS_FREE); if(!SearchSprinkPipeSys(entSel, id, pListAll, ssAll)){ delete pListAll; return; } delete pListAll; ssAll-=entSel; AcGeVector3d vectTmp(ptPick.x - ptLoc.x, ptPick.y - ptLoc.y, 0); AcGeMatrix3d mat; mat.setToTranslation(vectTmp); long len = ssAll.Length(); if(len > 1){ ssAll.Redraw(3); TCHAR szTmp[32]; ads_getstring(0, _T("\n该管线所连接其它管线是否联动:"), szTmp); ssAll.Redraw(4); if(_tcsicmp(szTmp, _T("N")) == 0) return; } for(long i=0;itransformBy(mat); TDbPipe *pPipe = NULL; if(pPipe = TDbPipe::cast(pEnt)){ DList lstAttachment; pPipe->GetAttachments(lstAttachment); int iLen = lstAttachment.Length(); for(int m=0;mtransformBy(mat); } OPENOBJ_END(); } } } OPENOBJ_END(); } } //*************************************************************************************************** // 管线交叉检查 //*************************************************************************************************** //double GetPipeStartEle(Entity entPipe) //{ // OPENOBJ_BEGIN(entPipe, AcDb::kForRead, TDbPipe, pPipe); // if(pPipe){ // AcDbObjectId nodeId1(NULL); // double dn = pPipe->GetDnDiameter(); // dn = dn / 2.0; // TPipeSys::FlowDirection dir = pPipe->GetFlowDir(); // if(dir == TPipeSys::kFromStart){ // return (pPipe->StartPoint().z - dn)/1000; // } // else{ // return (pPipe->EndPoint().z - dn)/1000; // } // } // OPENOBJ_END(); //// OPENOBJ_BEGIN(entPipe, AcDb::kForRead, TDbPipe, pPipe); //// if(pPipe){ //// AcDbObjectId nodeId1(NULL); //// TPipeSys::FlowDirection dir = pPipe->GetFlowDir(); //// if(dir == TPipeSys::kFromStart) //// nodeId1 = pPipe->GetNode(0); //// else //// nodeId1 = pPipe->GetNode(1); //// //// OPENOBJ_BEGIN(nodeId1, AcDb::kForRead, TDbEquipment, pEquip); //// if(pEquip){ //// int num = pEquip->GetInterfaceNum(); //// for(int i=0;iGetInterface(i, face); //// CString csPipeDownEle = pEquip->GetISysLabel(i); //// AcDbObjectId nextPipeId = face.m_idPipe; //// if(nextPipeId == pPipe->objectId()){ //// double nPipeEle = _tstof(csPipeDownEle); //// return nPipeEle; //// } //// } //// } //// OPENOBJ_END(); //// } //// OPENOBJ_END(); // return 0; //} //CString GetPipeNameBySys(TPipeSys::SysType sys); //extern double GetPipeOutDByDn(const TCHAR* szMat, int iDnIn); // //void CheckPipeInter() //{ // RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管线")), NULL); // PickSet ss(SS_FREE); // if(SelectEntities(_T("\n请选择检查范围<整张图>:"), ss, rbMask) != RTNORM){ // ss.Get(_T("X"), NULL, NULL, rbMask); // } // BOOL bDim = FALSE; // TCHAR szTmp[32]; // ads_getstring(0, _T("\n没有发生碰撞的交叉管线是否标注:"), szTmp); // if(_tcsicmp(szTmp, _T("Y")) == 0) // bDim = TRUE; // // XPointList lstPtInt; // BOOL bHasInter = TRUE; // for(long i=0;iGetMaterial(); // csMat = GetPipeMaterialByIdx(iMaterial); // sys1 = pPipe->GetSysType(); // ptStart = pPipe->StartPoint(); // ptEnd = pPipe->EndPoint(); // nDn = pPipe->GetDnDiameter(); // nI = pPipe->GetPipeGradient(); // TPipeSys::FlowDirection dir = pPipe->GetFlowDir(); // if(dir == TPipeSys::kFromStart) // ptWell = ptStart; // else // ptWell = ptEnd; // } // OPENOBJ_END(); // nDn = GetPipeOutDByDn(csMat, (int)nDn); // // ptStart.z = 0; // ptEnd.z = 0; // ptWell.z = 0; // XLine line1(ptStart, ptEnd, 1); // PickSet ssF(SS_FREE); // struct resbuf *pointlist; // pointlist = ads_buildlist(RTPOINT, &ptStart, RTPOINT, &ptEnd, NULL); // ssF.Get(_T("F"), pointlist, NULL, rbMask); // ads_relrb(pointlist); // for(long j=0;jGetMaterial(); // csMat2 = GetPipeMaterialByIdx(iMaterial); // // sys2 = pPipe->GetSysType(); // ptStart = pPipe->StartPoint(); // ptEnd = pPipe->EndPoint(); // nI2 = pPipe->GetPipeGradient(); // nDn2 = pPipe->GetDnDiameter(); // TPipeSys::FlowDirection dir = pPipe->GetFlowDir(); // if(dir == TPipeSys::kFromStart) // ptWell = ptStart; // else // ptWell = ptEnd; // ptWell.z = 0; // double nDist2Well2 = ads_distance(ptInt, ptWell) / 1000; // nPipeEle2 = nPipeEle2 - nDist2Well2*nI2; // } // OPENOBJ_END(); // nDn2 = GetPipeOutDByDn(csMat2, (int)nDn2); // XPoint ptTurn; // // if(bDim || (fabs(nPipeEle2 - nPipeEle1) < nDn || fabs(nPipeEle2 - nPipeEle1) < nDn2)){ // ads_polar(ptInt, PI/4, nDist1, ptTurn); // TDbSymbMultiLeader *pLeader = new TDbSymbMultiLeader; // XPointList lstVertexes; // lstVertexes.Append(new XPoint(ptInt)); // pLeader->SetLeaderVertexes(lstVertexes); // pLeader->SetText1(XString(_T("%s%.3f"), GetPipeNameBySys(sys2), nPipeEle2)); // pLeader->SetText2(XString(_T("%s%.3f"), GetPipeNameBySys(sys1),nPipeEle1)); // pLeader->SetLeaderPoint(ptTurn); // pLeader->SetArrow(TDbSymbMultiLeader::kNone); // AcDbObjectId idTextStyle = InitTextStyle(g_csTwtDimStyle); // pLeader->SetTextStyleId(idTextStyle); // pLeader->SetTextLayerId(InitLayer(LAY_TEXT)); // pLeader->SetTextHeight(g_nTwtDimHeight); // pLeader->SetTextBaseLen(pLeader->GetDefaultTextBaseLen()+2); // pLeader->AddToCSpace(Adesk::kTrue); // } // // if(fabs(nPipeEle2 - nPipeEle1) < nDn || fabs(nPipeEle2 - nPipeEle1) < nDn2){ // XPoint p1, p2, p3, p4; // ads_polar(ptInt, 0, nDist1, p1); // ads_polar(p1, PI/2, nDist1, p1); // ads_polar(ptInt, PI, nDist1, p2); // ads_polar(p2, PI/2, -nDist1, p2); // ads_grdraw(p1, p2, 2, 0); // ads_polar(ptInt, PI/2, nDist1, p3); // ads_polar(p3, PI, nDist1, p3); // ads_polar(ptInt, PI/2, -nDist1, p4); // ads_polar(p4, 0, nDist1, p4); // ads_grdraw(p3, p4, 2, 0); // bHasInter = TRUE; // continue; // } // // XPoint p1, p2, p3, p4; // ads_polar(ptInt, 0, nDist2, p1); // ads_polar(p1, PI/2, nDist2, p1); // ads_polar(ptInt, PI, nDist2, p2); // ads_polar(p2, PI/2, -nDist2, p2); // ads_grdraw(p1, p2, 1, 0); // ads_polar(ptInt, PI/2, nDist2, p3); // ads_polar(p3, PI, nDist2, p3); // ads_polar(ptInt, PI/2, -nDist2, p4); // ads_polar(p4, 0, nDist2, p4); // ads_grdraw(p3, p4, 1, 0); // } // } // if(bHasInter) // adsout << _T("\n黄叉表示室外管线存在碰撞!"); //} //*************************************************************************************************** // 立管半径 //*************************************************************************************************** void SetVerPipeRadius() { g_ssPickFirst.Free(); RBList rbMask(RTDXF0, _T("ATS_PIPE"), 8, GetLayerNames(_T("管")), NULL); PickSet ss(SS_FREE); if(SelectEntities(_T("\n请选择要修改半径的立管或扣弯<退出>:"), ss, rbMask) != RTNORM) return; if(ss.Length() < 1) return; Entity entSel = ss[0L]; double nRadius(0); OPENOBJ_BEGIN(entSel, AcDb::kForRead, TDbPipe, pPipe); if(pPipe && pPipe->IsVertical()){ nRadius = pPipe->GetRadius(); } OPENOBJ_END(); CString csPrompt; csPrompt.Format(_T("\n请给出新半径值mm<%.2f>:"), nRadius); ads_getreal(csPrompt, &nRadius); if(nRadius < 0.01) return; for(long i=0;iIsVertical()){ pPipe->SetRadius(nRadius); } OPENOBJ_END(); } }