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

487 lines
13 KiB
C++

#include "StdAfx.h"
#include "SequentialPoint.h"
#include "GlobalFunction.h"
#include "GlobalDrawMgr.h"
#include "DrawSimpleShape.h"
#include "WorkFileLable.h"
#include "WorkFileMgr.h"
#include "LogMgr.h"
CSequentialPoint::CSequentialPoint(void)
{
}
CSequentialPoint::~CSequentialPoint(void)
{
}
#if 1
void CSequentialPoint::WriteWorkFile(vector<CLab> &LabVec)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
LabVec.push_back(CLab(LAB_POINT_START));//数据点开始
Dbxy pt = (*iter).GetPt();
LabVec.push_back(CLab(LAB_POINT_X,pt.x));
LabVec.push_back(CLab(LAB_POINT_Y,pt.y));
LabVec.push_back(CLab(LAB_POINT_IS_NODE,(*iter).IsNode()));//是否为节点
LabVec.push_back(CLab(LAB_POINT_END));//数据点结束
}
}
void CSequentialPoint::ReadWorkFile(CLabVecRang &LabVecRang)
{
//分离数据点---------------------------------------------------
vector<CLabVecRang> LabVecRangVec;
CWorkFileMgr WorkFileMgr;
WorkFileMgr.SeparateStrVec(LabVecRang,LabVecRangVec,LAB_POINT_START,LAB_POINT_END);
//处理每个点
if(!LabVecRangVec.empty())
{
vector<CLabVecRang>::iterator iter = LabVecRangVec.begin();
vector<CLabVecRang>::iterator iter_end = LabVecRangVec.end();
for(;iter!=iter_end;iter++)
{
Dbxy pt;
bool bIsNode;
{//X坐标
CLab Lab = WorkFileMgr.FindLab((*iter),LAB_POINT_X);
if(Lab.m_ValType != _TYPE_NULL)
{
pt.x = Lab.m_Double;
}
}
{//Y坐标
CLab Lab = WorkFileMgr.FindLab((*iter),LAB_POINT_Y);
if(Lab.m_ValType != _TYPE_NULL)
{
pt.y = Lab.m_Double;
}
}
{//是否为NODE 点
CLab Lab = WorkFileMgr.FindLab((*iter),LAB_POINT_IS_NODE);
if(Lab.m_ValType != _TYPE_NULL)
{
bIsNode = Lab.m_Bool;
}
}
CDataPoint DataPoint(pt);
DataPoint.SetIsNode(bIsNode);
AddDataPoint(DataPoint);
}
}
}
#endif
#if 1
void CSequentialPoint::AddDataPoint(CDataPoint DataPt)
{
m_PtContainer.push_back(DataPt);
}
//导入另一个容器的数据
void CSequentialPoint::Load(CSequentialPoint &rhs)
{
vector<CDataPoint>::iterator iter = rhs.m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = rhs.m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
m_PtContainer.push_back(*iter);
}
}
bool CSequentialPoint::Empty()//是否有数据点
{
return m_PtContainer.empty();
};
void CSequentialPoint::DelAllPt()//删除所有数据点
{
m_PtContainer.clear();
};
void CSequentialPoint::DelLastDataPoint()//删除最后一个节点
{
if(!Empty())
{
m_PtContainer.pop_back();
}
}
//设置最后一个节点
void CSequentialPoint::SetLastPoint(CDataPoint &pt)
{
if(!Empty())
{
CDataPoint &LastPt = m_PtContainer[m_PtContainer.size()-1];
LastPt = pt;
}
}
//使用时需要保证m_Container 非空
Dbxy CSequentialPoint::GetFirstPt()
{
return m_PtContainer[0].GetPt();
}
//使用时需要保证m_Container 非空
Dbxy CSequentialPoint::GetLastPt()
{
return m_PtContainer[m_PtContainer.size()-1].GetPt();
}
//获取node 点的序号
int CSequentialPoint::GetNodePtIdx(Dbxy pt)
{
int idx = -1;
int size = m_PtContainer.size();
for(int i=0;i<size;i++)
{
if(pt==m_PtContainer[i].GetPt())
{
idx = i;
break;
}
}
return idx;
}
//通过索引值删除node 点
void CSequentialPoint::DelNodePtByIdx(int idx)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
int i=0;
for(;iter!=iter_end;iter++)
{
if(i==idx && (*iter).IsNode())
{
m_PtContainer.erase(iter);
break;
}
i++;
}
}
//设置idx 对应的node 点的值为pt
void CSequentialPoint::SetNodePtByIdx(int idx,Dbxy pt)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
int i=0;
for(;iter!=iter_end;iter++)
{
if(i==idx && (*iter).IsNode())
{
(*iter).SetPt(pt);
break;
}
i++;
}
}
void CSequentialPoint::InsertNode(int idx,Dbxy pt)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
int i=0;
for(;iter!=iter_end;iter++)
{
if(i==idx)
{
CDataPoint DataPoint(pt);
DataPoint.SetIsNode(true);
m_PtContainer.insert(iter,DataPoint);
break;
}
i++;
}
}
#endif
#if 1
//是否在矩形区域内
bool CSequentialPoint::IsInRect(DbRect rect,bool bNeedAllIn)
{
//检查所有线段
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
if(iter != m_PtContainer.begin())
{
Dbxy pt1 = (*(iter-1)).GetPt();
Dbxy pt2 = (*iter).GetPt();
if(bNeedAllIn)//需要全部在矩形范围内
{
if(!IsPointInRect(pt1,rect)||!IsPointInRect(pt2,rect))
{
return false;
}
}
else //(挂到边也算)
{
if(IsLineInRect(pt1,pt2,rect))
return true;
}
}
}
}
if(bNeedAllIn)
return true;
else
return false;
}
//获取边界矩形
DbRect CSequentialPoint::GetRect()
{
DbRect rect;
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
AdjustRectByPoint(rect,(*iter).GetPt());
}
return rect;
}
//是否有节点在rect 中
bool CSequentialPoint::HasNodeInRect(DbRect rect)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
if((*iter).IsNode()&&IsPointInRect((*iter).GetPt(),rect))
{
return true;
}
}
return false;
}
#endif
#if 1
void CSequentialPoint::Operate(SObjOperatePar par)
{
if(par.OpType == _OP_REVERSE)
{
//反转节点
Reverse();
}
else
{
OperateExt(par);
}
}
void CSequentialPoint::OperateExt(SObjOperatePar par)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
(*iter).Operate(par);
}
}
//反转节点
void CSequentialPoint::Reverse()
{
//先保存起来
vector<CDataPoint> vec;
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
vec.push_back((*iter));
}
//清空
m_PtContainer.clear();
//逆向倒回
int size = vec.size();
for(int i=size-1;i>=0;i--)
{
m_PtContainer.push_back(vec[i]);
}
}
#endif
#if 1//绘制
//绘制连续线段
void CSequentialPoint::DrawDataPointVec(CDC* pDC,vector<CDataPoint> &vec)
{
if(vec.size()>1)//最少两个点起绘
{
//绘制每条线段
vector<CDataPoint>::iterator iter = vec.begin();
vector<CDataPoint>::iterator iter_end = vec.end();
for(;iter!=iter_end;iter++)
{
CDataPoint &DataPt = (*iter);
CPoint pt = DataPt.GetDevicePt();
if(iter == vec.begin())
{
pDC->MoveTo(pt.x,pt.y);
}
else
{
pDC->LineTo(pt.x,pt.y);
}
}
}
}
void CSequentialPoint::Draw(CDC* pDC,CPen&Pen)
{
CPen *pOldPen;
pOldPen = pDC->SelectObject(&Pen);
//绘制连续线段
DrawDataPointVec(pDC,m_PtContainer);
pDC->SelectObject(pOldPen);
}
//绘制最后一条线段
void CSequentialPoint::DrawLastLine(CDC* pDC,CPen &Pen)
{
CPen *pOldPen;
pOldPen = pDC->SelectObject(&Pen);
if(!Empty())
{
vector<CDataPoint> &vec = m_PtContainer;
int size = vec.size();
if(size>=2)
{
CPoint pt1 = vec[size-2].GetDevicePt();
pDC->MoveTo(pt1.x,pt1.y);
CPoint pt2 = vec[size-1].GetDevicePt();
pDC->LineTo(pt2.x,pt2.y);
}
}
pDC->SelectObject(pOldPen);
}
//绘制节点
void CSequentialPoint::DrawNode(CDC* pDC)
{
int size = m_PtContainer.size();
for(int i=0;i<size;i++)
{
//如果obj 闭合则不要绘制最后一个节点
if(i==size-1 && m_PtContainer[i].GetPt() == m_PtContainer[0].GetPt())
{
break;
}
if(m_PtContainer[i].IsNode())
{
if(i==0)//首节点
{
DrawSolidRect(pDC,gDraw->GetObjFirstNodeColor(),gDraw->GetCurPointRect(m_PtContainer[i].GetPt()));
}
else
{
DrawSolidRect(pDC,gDraw->GetObjNodeColor(),gDraw->GetCurPointRect(m_PtContainer[i].GetPt()));
}
}
}
}
#endif
#if 1
void CSequentialPoint::GetLineInRect(DbRect &rect,vector<DbLine> &DataPtLineVec)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
if(iter != m_PtContainer.begin())
{
Dbxy pt1 = (*(iter-1)).GetPt();
Dbxy pt2 = (*iter).GetPt();
if(IsLineInRect(pt1,pt2,rect))
{
DataPtLineVec.push_back(DbLine((*(iter-1)),(*iter)));
}
}
}
}
//获取捕获结点的线段
void CSequentialPoint::GetNodePtLineInRect(DbRect &rect,vector<DbLine> &DataPtLineVec)
{
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
Dbxy pt1 = (*iter).GetPt();
Dbxy pt2 = (*iter).GetPt();
if(IsLineInRect(pt1,pt2,rect))
{
DataPtLineVec.push_back(DbLine((*iter),(*iter)));
}
}
}
#endif
//搜集点的数据到vec (如果和上一段是连接的则连上) (PenNum为笔号)
void CSequentialPoint::GetPtData(vector<vector<Dbxy>> &vec,int PenNum)
{
bool bhasLastPt = false;//是否有最后一个点
Dbxy LastPt;
//获取之前的最后一个点
int size = vec.size();
if(size>0)
{
if(vec[size-1].empty()==false)
{
int size1 = vec[size-1].size();
LastPt = vec[size-1][size1-1];
bhasLastPt = true;
}
}
vector<Dbxy> VecTmp;
bool bNeedConnect = false;//是否需要连接
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
if(iter == m_PtContainer.begin() && bhasLastPt)//判断是否连接
{
if((*iter).GetPt() == LastPt)
{
bNeedConnect = true;
}
}
Dbxy pt = (*iter).GetPt();
pt.PenNum = PenNum;//设置点所在的笔号
VecTmp.push_back(pt);
}
if(!VecTmp.empty())
{
#if 0//不要将数据连起来
if(bNeedConnect)
{
vector<Dbxy>::iterator iter = VecTmp.begin();
vector<Dbxy>::iterator iter_end = VecTmp.end();
for(;iter!=iter_end;iter++)
{
vec[size-1].push_back(*iter);
}
}
else
#endif
{
vec.push_back(VecTmp);
}
}
}
//是否和line 相交
bool CSequentialPoint::IntersectWithLine(DbLine &line)
{
Dbxy pt1 = line.GetPt1();
Dbxy pt2 = line.GetPt2();
vector<CDataPoint>::iterator iter = m_PtContainer.begin();
vector<CDataPoint>::iterator iter_end = m_PtContainer.end();
for(;iter!=iter_end;iter++)
{
if(iter != m_PtContainer.begin())
{
if(IsTwoLineIntersect(pt1,pt2,(*(iter-1)).GetPt(),(*iter).GetPt()))
{
return true;
}
}
}
return false;
}