VC++开发GIS系统(236)边界删点类的设计及实现

本文介绍另外一个GIS系统操作:边界删点。主要的功能演示如下:

GIS系统边界删点类的定义

在_malaPolygon.h中定义GIS边界删点的类,代码如下:

/*
*边界删点
*/
class malapolygondll CmalaPolysDeletePoint :public CmalaMouseAction
{
public:
  CmalaPolysDeletePoint(CView* mView, malaScreen *pScreen, CString &fileFullPath);
  virtual ~CmalaPolysDeletePoint();
  void LButtonDown(UINT nFlags, malaPoint point);
  void LButtonUp(UINT nFlags, malaPoint point);
  void MouseMove(UINT nFlags, malaPoint point);
private:

  bool mSelected;
  vector<malaPoint> mSPoly;//选择的区
  vector<malaPoint> mPerPoly;//临时的区
  malaPolyPro mSPolyPro;//选择的区的属性
  CmalaPolysSelect mSelectPoly;
  bool callSel;//控制是否触发选择区

  int mPos;//标记点位置
  malaScreen *mScreen;
  CString mPath;//文件路径
};
  • m_Selected 用来定义区是否被选中
  • mSPoly 记录选择的区的点序列
  • mPerPoly 临时的区
  • mSPolyPro 记录选择区的属性
  • mSelectPoly 一个选择区对象,用来选择区
  • callSel 控制是否触发选择区
  • mPos 标记选中点的序列位置
  • *m_Screen 屏幕坐标变换变量
  • mPath 文件路径

类的实现

在_malaPolygon.cpp中实现上述的类定义,代码如下:

/*
* 边界删点实现
*/
CmalaPolysDeletePoint::CmalaPolysDeletePoint(CView* mView, malaScreen *pScreen, CString &fileFullPath)
{
  mBaseView = mView;
  mPath = fileFullPath;
  mScreen = pScreen;
  CmalaPolysSelect obj(mView, pScreen, fileFullPath);
  mSelectPoly = obj;
  mSelected = FALSE;
  callSel = FALSE;
  mPos = 0;
}

CmalaPolysDeletePoint::~CmalaPolysDeletePoint()
{
  if (mSPoly.size())
    mSPoly.clear();
  if (mPerPoly.size())
    mPerPoly.clear();
}

void CmalaPolysDeletePoint::LButtonDown(UINT nFlags, malaPoint point)
{
  if (!mSelected&&!callSel)
    mSelectPoly.LButtonDown(nFlags, point);
  if (mSelected&&!callSel)
  {
    if (mSPoly.size() > 2)
    {
      malaLogic math;
      mPos = math.getPointPosInLine(point, mSPoly);
      if (mPos >= 0)
      {
        for (size_t i = 0; i < mSPoly.size(); i++)
        {
          if (i != mPos)
            mPerPoly.push_back(mSPoly[i]);
        }

        CPolyIO lio;
        lio.polyUpdate(mPerPoly, mSPolyPro, mPath);

        mSPoly.clear();
        mPerPoly.clear();
        mSelectPoly.m_Selected = FALSE;
        mBaseView->Invalidate(TRUE);//+
        callSel = true;
      }
    }
    else
    {
      callSel = true;
      MessageBox(mBaseView->m_hWnd, L"无法删除", L"警告", MB_ICONQUESTION);
      mSelectPoly.m_Selected = FALSE;
    }
    
  }
}

void CmalaPolysDeletePoint::LButtonUp(UINT nFlags, malaPoint point)
{
  if (!mSelected&&!callSel)
    mSelectPoly.LButtonUp(nFlags, point);

  mSelected = mSelectPoly.m_Selected;
  if (mSelected)
  {
    mSPoly = mSelectPoly.mSPoly;
    mSPolyPro = mSelectPoly.mSPolyPro;
  }
}

void CmalaPolysDeletePoint::MouseMove(UINT nFlags, malaPoint point)
{
  if (!mSelected&&!callSel)
    mSelectPoly.MouseMove(nFlags, point);
}

主要思路是:LButtonDown的时候,判断选中的点是不是在区的边上,如果是将其他的点重新组成区的序列,并更新。

其中,getPointPosInLine函数用于获取选中点的位置,参考文章《VC++开发GIS系统(188)线上移点之获取点在线的位置》。函数 polyUpdate 用于实现更新一个区的属性,可以参考文章《VC++开发GIS系统(223)移动区之更新区参数

详细代码可以参考:GitHub

VC++开发GIS系统(235)边界移点之菜单响应 VC++开发GIS系统(237)边界删点之菜单响应

作者:,GIS爱好者。
分享本文,请您带上本文链接
分享到:

发表评论