#include "StdAfx.h" #include "globalfunc.h" #include "AcDbObjectPtr.h" #include "WellSerial.h" #include #include "DbWell.h" #include "Dbpipe.h" #include "PickEntSet.h" extern void ModifyWellDimPosAngle(Entity &ent); extern int EvadeUpdating(Entity &ent); //两条支管长度比较 bool CompareList(SSearchPipeList *pList1, SSearchPipeList *pList2) { if (pList1->m_iSpare > pList2->m_iSpare) { return false; } else if (pList1->m_iSpare == pList2->m_iSpare) { if (pList1->m_nSpare >= pList2->m_nSpare) { return false; } } return true; } CWellSerial::CWellSerial() { m_bEvade = true; m_bUpdateSerial = true; } void CWellSerial::SetEvade(bool bEvade) { m_bEvade = bEvade; } void CWellSerial::SetStartWell( Entity &ent ) { m_entStartWell = ent; } void CWellSerial::SetEndWell( Entity &ent) { m_entEndWell = ent; } void CWellSerial::SetSerialType( int nType ) { m_nSeriralType = nType; } void CWellSerial::SetAdd( bool bAdd ) { m_bAdd = bAdd; } void CWellSerial::SetWellSerial( const CString &sSerial ) { m_sWellSerial = sSerial; } bool CWellSerial::CheckWellSys() { CString sLayerS, sLayerE; OPENOBJ_BEGIN(m_entStartWell, AcDb::kForRead, AecXDbWell, pEnt); if(pEnt != NULL) { sLayerS = pEnt->layer(); } OPENOBJ_END(); OPENOBJ_BEGIN(m_entEndWell, AcDb::kForRead, AecXDbWell, pEnt); if(pEnt != NULL) { sLayerE = pEnt->layer(); } OPENOBJ_END(); if (sLayerS.Compare(sLayerE) == 0) { m_sWellLayer = sLayerS; return true; } return false; } void CWellSerial::UpdateWellSerival() { // 起始井和终止井不是同一图层 zxl 2013.04.25 add if (!CheckWellSys()) { acedPrompt(_T("\n起点井与终点井不属于同一类型,请再次选择!")); return; } // 根据起点井搜索管网系统 SSearchPipeList *pList = new SSearchPipeList(); PickSet ssAll(SS_FREE); if(!GlobalFunc::SearchSprinkPipeSys(m_entStartWell, NULL, pList, ssAll)) { acutPrintf(_T("\n发现系统存在回路,请核查!")); delete pList; return; } if (pList != NULL) { pList->m_iType = 3; } // 初始化管网,以判断井是否已编号 SSearchPipeList *pLstNew = new SSearchPipeList; InitPipeSys(pList, pLstNew); while (pLstNew->m_pPrevious != NULL) { pLstNew = pLstNew->m_pPrevious; } delete pList; pList = NULL; pList = pLstNew; // 找出终点井 SSearchPipeList *pEndWell = FindEndWell(pList); if (pEndWell == NULL) { // 提示请在同一管网上选择井 acutPrintf(_T("\n起点井与终点井不在同一管网系统中,请核查连接是否正确!\n")); ssAll.Redraw(3); delete pList; return; } //选择终止井后 实施躲避更新时缩放全屏 使管网中所有井进入当前屏幕 zxl 2011.11.07 add if (m_bEvade) { XPoint ptLow,ptUp; ssAll.GetExtend(ptLow,ptUp); GlobalFunc::AssureInCurrentView_New(ptLow,ptUp);//支持UCS } // 根据支路编号方式,进行编号 switch(m_nSeriralType) { case 0: // Y24 ← Y24-3 ←Y24-2 ←Y24-1 { UpdateSerialType0(pEndWell); break; } case 1: // Y24 ← Y24-1 ←Y24-2 ←Y24-3 { UpdateSerialType1(pEndWell); break; } case 2: // Y24 ← Y83 ←Y82 ←Y81 { UpdateSerialType2(pEndWell, false); break; } case 3: // Y24 ← Y81 ←Y82 ←Y83 { UpdateSerialType3(pEndWell, false); break; } case 4: // Y24 ← Y27 ←Y26 ←Y25 { UpdateSerialType4(pEndWell, false); break; } case 5: // Y24 ← Y25 ←Y26 ←Y27 { UpdateSerialType5(pEndWell, false); break; } case 6: // 不修改支路井编号 { UpdateSerialType6(pEndWell); break; } } if (m_bUpdateSerial) { m_bAdd = !m_bAdd; ChangeWellSerial(); } acutPrintf(XString(_T("终点井编号为%s!"), m_sWellSerial)); delete pList; } SSearchPipeList* CWellSerial::FindEndWell(SSearchPipeList *pList) { if (pList == NULL) { return NULL; } AcDbObjectId id; acdbGetObjectId(id, m_entEndWell); std::stack stWell; stWell.push(pList); SSearchPipeList *pTemp = NULL; while (!stWell.empty()) { pTemp = stWell.top(); stWell.pop(); if (pTemp->m_iType == 3) { if (id == pTemp->m_ID) { return pTemp; } } for (int i = 0; i < pTemp->m_lstNode.Length(); i++) { stWell.push(pTemp->m_lstNode[i]); } } return NULL; } // zxl 2013.04.27 add void SetValue(SSearchPipeList *pS, SSearchPipeList *qD) { qD->m_bNeedCale = pS->m_bNeedCale; qD->m_csName = pS->m_csName; qD->m_ID = pS->m_ID; qD->m_iType = pS->m_iType; } void CWellSerial::InitPipeSys(SSearchPipeList *pList, SSearchPipeList *pLstNew) { if (pList == NULL) { return; } // zxl 2013.04.27 add pList->m_bNeedCale = false; if (!(pList->m_iType != 3 && pList->m_lstNode.Length() > 1) && !(pList->m_iType == 3 && !IsSameSys(pList->m_ID))) { SetValue(pList, pLstNew); pLstNew->m_lstNode.Reset(); } else { pLstNew->m_pPrevious->m_lstNode.Remove(); pLstNew = pLstNew->m_pPrevious; while (pLstNew != NULL) { if (pLstNew->m_iType == 3 && IsSameSys(pLstNew->m_ID)) { break; } for (int n = 0; n < pLstNew->m_pPrevious->m_lstNode.Length(); n++) { if (pLstNew->m_pPrevious->m_lstNode[n] == pLstNew) { pLstNew->m_pPrevious->m_lstNode.Remove(n); } } pLstNew = pLstNew->m_pPrevious; } } for (int i = 0; i < pList->m_lstNode.Length(); i++) { // zxl 2013.04.27 add SSearchPipeList *p = new SSearchPipeList; pLstNew->m_lstNode.Append(p); p->m_pPrevious = pLstNew; InitPipeSys(pList->m_lstNode[i], p); } } void CWellSerial::SetPipeDirection(std::vector &vecPipe, std::vector &vecWell, bool bBra = false) { std::vector::iterator itPipe; std::vector::iterator itWell; for (itPipe = vecPipe.begin(), itWell = vecWell.begin(); itPipe != vecPipe.end() && itWell != vecWell.end(); itPipe++, itWell++) { XPoint ptFront; SSearchPipeList *pListWell = *itWell; OPENOBJ_BEGIN(pListWell->m_ID, AcDb::kForRead, CDbEquipment, pEquip); if (pEquip == NULL) { continue; } ptFront = pEquip->GetLocation(); OPENOBJ_END(); SSearchPipeList *pListPipe = *itPipe; OPENOBJ_BEGIN(pListPipe->m_ID, AcDb::kForWrite, CDbPipe, pPipe); if(pPipe) { XPoint p1 = ptFront; p1.z = 0; XPoint p2 = pPipe->StartPoint(); p2.z = 0; if (!bBra)//主干流向 { if(p1 == p2) pPipe->SetFlowDir(TPipeSys::kFromEnd); else pPipe->SetFlowDir(TPipeSys::kFromStart); } else//分支流向 { if(p1 == p2) pPipe->SetFlowDir(TPipeSys::kFromStart); else pPipe->SetFlowDir(TPipeSys::kFromEnd); } } OPENOBJ_END(); } } void CWellSerial::UpdateSerialType0( SSearchPipeList *pEndWell ) { std::vector vecWell; std::vector vecPipe; GetMainWell(pEndWell, vecWell, vecPipe); // 获得主干上的井和管线 SetPipeDirection(vecPipe, vecWell); CString sName; AcDbObjectId idEnd = pEndWell->m_ID; std::vector::reverse_iterator it; //遍历主干井 for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { AcDbObjectId id = NULL; SSearchPipeList *pList = *it; if (pList->m_iType != 3) { continue; } id = pList->m_ID; ModifyWellSerial(id); pList->m_csName = m_sWellSerial; sName = m_sWellSerial; if (pList->m_lstNode.Length() > 1) { ModifyBranchSeiral0(pList, pList->m_ID); } m_sWellSerial = sName; ChangeWellSerial(); } } // 编号 支井(从叶子节点向主干递减) zxl 2012.10.18 add void CWellSerial::ModifyBranchSeiral0(SSearchPipeList *pList, AcDbObjectId &id) { int iLen = 0; double dLen = 0; CString csName = pList->m_csName; //寻找分支,从分支末端进行编号 if (pList->m_lstNode.Length() > 1) { std::vector vecLongestList; std::vector vecPList; //遍历各个分支节点,得到每条分支的最长管线 for (int i = 0; i < pList->m_lstNode.Length(); i++) { SSearchPipeList *pListBra = pList->m_lstNode[i]; if (!pListBra->m_bNeedCale) { iLen = 0; dLen = 0; vecPList.clear(); CalcNodeNum(pListBra, iLen, dLen, vecPList); std::sort(vecPList.begin(), vecPList.end(), CompareList); pListBra = vecPList.back(); vecLongestList.push_back(pListBra); } } //以每个分支的最长管线作为主干进行递归编号 std::sort(vecLongestList.begin(), vecLongestList.end(), CompareList); m_sWellSerial.Format(_T("%s-1"), csName); std::vector::reverse_iterator it; CString csSerial; for (it = vecLongestList.rbegin(); it != vecLongestList.rend(); it++) { SSearchPipeList *pLongList = *it; //从末端开始进行编号 while (!pLongList->m_bNeedCale) { if (pLongList->m_iType == 3) { ModifyWellSerial(pLongList->m_ID); pLongList->m_csName = m_sWellSerial; pLongList->m_bNeedCale = true; m_sWellSerial = GlobalFunc::PlusString(m_sWellSerial, 1, TRUE); csSerial = m_sWellSerial; ModifyBranchSeiral0(pLongList, pLongList->m_ID);// 记录分支号,对分支的分支进行编号 m_sWellSerial = csSerial; } if (pLongList->m_iType == 0)//设置管线流向 { std::vector vecBraWell; std::vector vecBraPipe; vecBraPipe.push_back(pLongList); vecBraWell.push_back(pLongList->m_pPrevious); SetPipeDirection(vecBraPipe, vecBraWell); } pLongList = pLongList->m_pPrevious; } } } } // 编号 支井(从叶子节点向主干递增) zxl 2012.10.18 add void CWellSerial::ModifyBranchSeiral1(SSearchPipeList *pList, AcDbObjectId &id) { int iLen = 0; double dLen = 0; CString csName = pList->m_csName; //寻找分支,从分支末端进行编号 if (pList->m_lstNode.Length() > 1) { std::vector vecLongestList; std::vector vecPList; //遍历各个分支节点,得到每条分支的最长管线 for (int i = 0; i < pList->m_lstNode.Length(); i++) { SSearchPipeList *pListBra = pList->m_lstNode[i]; if (!pListBra->m_bNeedCale) { iLen = 0; dLen = 0; vecPList.clear(); CalcNodeNum(pListBra, iLen, dLen, vecPList); std::sort(vecPList.begin(), vecPList.end(), CompareList); pListBra = vecPList.back(); vecLongestList.push_back(pListBra); } } //以每个分支的最长管线作为主干进行递归编号 std::sort(vecLongestList.begin(), vecLongestList.end(), CompareList); m_sWellSerial.Format(_T("%s-1"), csName); std::vector::reverse_iterator it; CString csSerial; for (it = vecLongestList.rbegin(); it != vecLongestList.rend(); it++) { SSearchPipeList *pLongList = *it; //从分支开始处进行编号 std::vector vecLst; while (!pLongList->m_bNeedCale) { pLongList->m_bNeedCale = true; vecLst.push_back(pLongList); pLongList = pLongList->m_pPrevious; } std::vector::reverse_iterator itR; for (itR = vecLst.rbegin(); itR!= vecLst.rend(); itR++) { pLongList = *itR; if (pLongList->m_iType == 3) { ModifyWellSerial(pLongList->m_ID); pLongList->m_csName = m_sWellSerial; pLongList->m_bNeedCale = true; m_sWellSerial = GlobalFunc::PlusString(m_sWellSerial, 1, TRUE); csSerial = m_sWellSerial; ModifyBranchSeiral1(pLongList, pLongList->m_ID);// 记录分支号,对分支的分支进行编号 m_sWellSerial = csSerial; } if (pLongList->m_iType == 0)//设置管线流向 { std::vector vecBraWell; std::vector vecBraPipe; vecBraPipe.push_back(pLongList); vecBraWell.push_back(pLongList->m_pPrevious); SetPipeDirection(vecBraPipe, vecBraWell); } } } } } void CWellSerial::UpdateSerialType1( SSearchPipeList *pEndWell ) { std::vector vecWell; std::vector vecPipe; GetMainWell(pEndWell, vecWell, vecPipe); // 获得主干上的井和管线 SetPipeDirection(vecPipe, vecWell); CString sName; AcDbObjectId idEnd = pEndWell->m_ID; std::vector::reverse_iterator it; //遍历主干井 for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { AcDbObjectId id = NULL; SSearchPipeList *pList = *it; if (pList->m_iType != 3) { continue; } id = pList->m_ID; ModifyWellSerial(id); pList->m_csName = m_sWellSerial; sName = m_sWellSerial; if (pList->m_lstNode.Length() > 1) { ModifyBranchSeiral1(pList, pList->m_ID); } m_sWellSerial = sName; ChangeWellSerial(); } } //检查井是否只有一条支路井 bool CWellSerial::CheckPipeBra(SSearchPipeList *&pListBra) { int iNum = 0; int iNo = 0; SSearchPipeList *pListTemp; for (int j = 0; j < pListBra->m_lstNode.Length(); j++) { pListTemp = pListBra->m_lstNode[j]; if (pListTemp->m_bNeedCale) { continue; } SSearchPipeList *pListNode; for (int n = 0; n < pListTemp->m_lstNode.Length(); n++) { pListNode = pListTemp->m_lstNode[n]; if (pListNode->m_iType == 3) { iNum++; iNo = j; } } } if (iNum > 1) { return false; } else if(pListBra->m_lstNode.Length() > 0) { pListBra = pListBra->m_lstNode[iNo]; return true; } return false; } void CWellSerial::UpdateSerialType2or3(SSearchPipeList *pEndWell, bool bBraSerial, bool bAdd) { std::vector vecWell; std::vector vecPipe; GetMainWell(pEndWell, vecWell, vecPipe); // 获得主干上的井 if (!bBraSerial) { SetPipeDirection(vecPipe, vecWell); } else { SetPipeDirection(vecPipe, vecWell, true); } //判断是支路,且递增性与该类型标注相同时从分支起始处编号 if (bBraSerial && bAdd) { std::reverse(vecWell.begin(), vecWell.end()); } std::vector::reverse_iterator it; for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { SSearchPipeList *pList = *it; if (pList->m_iType != 3) { continue; } ModifyWellSerial(pList->m_ID); ChangeWellSerial(); } if (bBraSerial && bAdd) { std::reverse(vecWell.begin(), vecWell.end()); } //遍历支路时,从叶子节点开始遍历 if (bBraSerial) { std::reverse(vecWell.begin(), vecWell.end()); } int iLen = 0; double dLen = 0; //遍历主干,分别对支路进行编号 for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { SSearchPipeList *pList = *it; if (pList->m_lstNode.Length() > 1) { std::vector vecLongestList; std::vector vecPList; //遍历各个分支节点,得到每条分支的最长管线 for (int i = 0; i < pList->m_lstNode.Length(); i++) { SSearchPipeList *pListBra = pList->m_lstNode[i]; if (!pListBra->m_bNeedCale) { iLen = 0; dLen = 0; vecPList.clear(); CalcNodeNum(pListBra, iLen, dLen, vecPList); std::sort(vecPList.begin(), vecPList.end(), CompareList); pListBra = vecPList.back(); vecLongestList.push_back(pListBra); } } //以每个分支的最长管线作为主干进行递归编号 std::sort(vecLongestList.begin(), vecLongestList.end(), CompareList); while (!vecLongestList.empty()) { SSearchPipeList *pLongList = vecLongestList.back(); vecLongestList.pop_back(); UpdateSerialType2or3(pLongList, true, bAdd); } } } } void CWellSerial::UpdateSerialType2( SSearchPipeList *pEndWell, bool bBraSerial) { UpdateSerialType2or3(pEndWell, bBraSerial, m_bAdd); } void CWellSerial::UpdateSerialType3( SSearchPipeList *pEndWell, bool bBraSerial) { UpdateSerialType2or3(pEndWell, bBraSerial, !m_bAdd); } //主干和分支混合标注:先编号主干,遇到分支则开始分支编号 void CWellSerial::UpdateSerialType4or5(SSearchPipeList *pEndWell, bool bBraSerial, bool bAdd) { std::vector vecWell; std::vector vecPipe; GetMainWell(pEndWell, vecWell, vecPipe); // 获得主干上的井 if (!bBraSerial) { SetPipeDirection(vecPipe, vecWell); } if (bBraSerial && bAdd) { std::reverse(vecWell.begin(), vecWell.end()); } int iLen = 0; double dLen = 0; std::vector::reverse_iterator it; //遍历主干并编号,遇到对支路时对支路进行编号 for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { SSearchPipeList *pList = *it; if (pList->m_iType != 3) { continue; } ModifyWellSerial(pList->m_ID); ChangeWellSerial(); if (pList->m_lstNode.Length() > 1) { std::vector vecLongestList; std::vector vecPList; //遍历各个分支节点,得到每条分支的最长管线 for (int i = 0; i < pList->m_lstNode.Length(); i++) { SSearchPipeList *pListBra = pList->m_lstNode[i]; if (!pListBra->m_bNeedCale) { iLen = 0; dLen = 0; vecPList.clear(); CalcNodeNum(pListBra, iLen, dLen, vecPList); std::sort(vecPList.begin(), vecPList.end(), CompareList); pListBra = vecPList.back(); vecLongestList.push_back(pListBra); } } //以每个分支的最长管线作为主干进行递归编号 std::sort(vecLongestList.begin(), vecLongestList.end(), CompareList); while (!vecLongestList.empty()) { SSearchPipeList *pLongList = vecLongestList.back(); vecLongestList.pop_back(); UpdateSerialType2or3(pLongList, true, bAdd); } } } } void CWellSerial::UpdateSerialType4( SSearchPipeList *pEndWell, bool bBraSerial) { UpdateSerialType4or5(pEndWell, bBraSerial, m_bAdd); } void CWellSerial::UpdateSerialType5( SSearchPipeList *pEndWell, bool bBraSerial) { UpdateSerialType4or5(pEndWell, bBraSerial, !m_bAdd); } void CWellSerial::CalcNodeNum( SSearchPipeList *pList, int iLen, double dLen, std::vector &vecPList) { if (pList->m_lstNode.Length() == 0) { pList->m_iSpare = iLen; pList->m_nSpare = dLen; vecPList.push_back(pList); return; } if (pList->m_iType == 3) { iLen ++; } else if(pList->m_iType == 0) {//获取管长 OPENOBJ_BEGIN(pList->m_ID, AcDb::kForRead, CDbPipe, pEnt); if(pEnt) { XPoint ptS, ptE; pEnt->getStartPoint(ptS); pEnt->getEndPoint(ptE); dLen += ptS.Distance2d(ptE); } OPENOBJ_END(); } for (int i = 0; i < pList->m_lstNode.Length(); i++) { CalcNodeNum(pList->m_lstNode[i], iLen, dLen, vecPList); } } void CWellSerial::UpdateSerialType6( SSearchPipeList *pEndWell) { std::vector vecWell; std::vector vecPipe; GetMainWell(pEndWell, vecWell, vecPipe); // 获得主干上的井 SetPipeDirection(vecPipe, vecWell); std::vector::reverse_iterator it; for (it = vecWell.rbegin(); it != vecWell.rend(); it++) { SSearchPipeList *pList = *it; if (pList->m_iType != 3) { continue; } ModifyWellSerial(pList->m_ID); ChangeWellSerial(); } } // 判断该井是否和起始井是同一系统 zxl 2013.04.25 add bool CWellSerial::IsSameSys(const AcDbObjectId &id) { bool bIsSame = false; OPENOBJ_BEGIN(id, AcDb::kForRead, AecXDbWell, pEnt); if(pEnt != NULL) { CString sLayer = pEnt->layer(); if (sLayer.Compare(m_sWellLayer) == 0) { bIsSame = true; } } OPENOBJ_END(); return bIsSame; } void CWellSerial::GetMainWell( SSearchPipeList *pEndWell, std::vector &vecWell, std::vector &vecPipe) { while(pEndWell != NULL) { if (pEndWell->m_bNeedCale) { return; } if (pEndWell->m_iType == 3 || pEndWell->m_iType == 4) { vecWell.push_back(pEndWell); } else if (pEndWell->m_iType == 0) { vecPipe.push_back(pEndWell); } pEndWell->m_bNeedCale = true; pEndWell = pEndWell->m_pPrevious; } } void CWellSerial::ModifyWellSerial(const AcDbObjectId &idWell) { OPENOBJ_BEGIN(idWell, AcDb::kForWrite, AecXDbWell, pEnt); if(pEnt) { pEnt->SetWellName(m_sWellSerial); pEnt->EnableDrawLabel(true);//zxl 2011.12.05 add 显示井编号 } OPENOBJ_END(); // 调整井编号角度和距离 ads_name name; Acad::ErrorStatus es = acdbGetAdsName(name,idWell); Entity ent = name; ModifyWellDimPosAngle(ent); // 实施躲避更新 if (m_bEvade) { EvadeUpdating(ent); } } //判断井编号是否小于1 bool CWellSerial::IsLessEqual1() { TCHAR chText; CString strText1 = _T(""); for (int i = m_sWellSerial.GetLength(); i >0; i--) { chText = m_sWellSerial[i - 1]; if(chText <= _T('9') && chText >= _T('0')) { strText1.Insert(0, chText); } else { break; } } double dNo = 0.0; dNo = _tstof(strText1); if (dNo <= 1.0) { return true; } return false; } //判断递增还是递减,重设井编号名字 void CWellSerial::ChangeWellSerial() { if (m_bAdd)//井编号递增 { m_sWellSerial = GlobalFunc::PlusString(m_sWellSerial, 1, TRUE); m_bUpdateSerial= true; } else//井编号递减 { if (IsLessEqual1())//井编号递减为1时 { m_bUpdateSerial = false; } else { m_sWellSerial = GlobalFunc::PlusString(m_sWellSerial, -1,TRUE); m_bUpdateSerial = true; } } }