zoukankan      html  css  js  c++  java
  • (5)一步一步开发一个简单CAD之线,圆及矩形类

    为了实现捡选,平称及旋转命令,必需对实体进行这些动作的操作

    分别开发了线,圆及矩形类

    class CMyrect;
    class CLine : public CSolid
    {
    public:
     CLine();
     CLine(CPosition &pos1, CPosition &pos2);
     CSolid *CopySolid(){ return new CLine(this->m_begin, this->m_end);}//深复制直线
     virtual ~CLine();
    public:
     CSolid* Explan(CPosition pos,short zDelta);
        CSolid* Rotate(const CPosition &base, float angle);
        CSolid* Move(CPosition first, CPosition second);
     BOOL PickSolid(CPosition &pos, float dis);
     void DrawSolid(CDC *pDC, int drawMode);
     void GetBox(CBox2D &box);//包围盒
     void DrawRect(BOOL br, CPosition &pos, CPosition *bpos = NULL);
     void GetEnd(CPosition &end){end = m_end;}
     CSolid *Mirror(CPosition &first, CPosition &second);
      
    protected:
     CPosition m_begin, m_end;

    };

    class CCircle : public CSolid//圆形对像,中心和圆上一点
    {
    public:
     CCircle(){};
     CCircle(const CPosition begin, const CPosition end);
     CSolid *CopySolid(){ return new CCircle(this->m_begin, this->m_end);}
     virtual ~CCircle(){};
    public:
     CSolid* Explan(CPosition pos,short zDelta);
        CSolid* Rotate(const CPosition &base, float angle);
        CSolid* Move(CPosition first, CPosition second);
     void DrawSolid(CDC *pDC, int drawMode);//画圆形
     BOOL PickSolid(CPosition &pos, float dis);
     void DrawRect(BOOL br, CPosition &pos, CPosition *bpos = NULL);
     CSolid *Mirror(CPosition &first, CPosition &second);
    private:
        CPosition m_begin, m_end;

    };

    class CCRect : public CSolid//两个对角点
    {
    public:
     CCRect(){};
     CCRect(const CPosition begin, const CPosition end);
     CSolid *CopySolid(){ return new CCRect(this->m_begin, this->m_end);}
     virtual ~CCRect(){};
    public:
     CSolid* Explan(CPosition pos,short zDelta);
        CSolid* Rotate(const CPosition &base, float angle);
        CSolid* Move(CPosition first, CPosition second);
     void DrawSolid(CDC *pDC, int drawMode);//画圆形
     BOOL PickSolid(CPosition &pos, float dis);
     void DrawRect(BOOL br, CPosition &pos, CPosition *bpos = NULL);
     CSolid *Mirror(CPosition &first, CPosition &second);
     
    private:
        CPosition m_begin, m_end;

    };

    CLine::CLine()
    {
      
    }

    CLine::CLine(CPosition &pos1, CPosition &pos2)
    {
     m_begin = pos1;
       m_end = pos2;
      
     m_Style = PS_SOLID;
     m_Width = 0;
        m_color = RGB(255, 255, 255);

     
    }

    CLine::~CLine()
    {
     
    }

    void CLine::DrawSolid(CDC *pDC, int drawMode)
    {
     CPoint point1, point2;

     g_pView->WPTODP(m_begin, point1);
     g_pView->WPTODP(m_end, point2);


     
        CPen pen;
      if (drawMode == Normal)//根据输入模式生居画笔
      {
     pen.CreatePen(m_Style, m_Width, m_color);

      }
      else
      {
         GSetDrawMode(pDC, drawMode, &pen);
      }
     int n = pDC->GetROP2();
      CPen *Oldpen = NULL;
      Oldpen = pDC->SelectObject(&pen);

     pDC->MoveTo(point1.x, point1.y);
     pDC->LineTo(point2.x, point2.y);


     pDC->SetROP2(n);
     pDC->SelectObject(Oldpen);
    }

    BOOL CLine::PickSolid(CPosition &pos, float dis)
    {
        CBox2D box;
     GetBox(box);
     box.GetExBox2D(dis);//得到扩张包围盒,考虑直线是水平或者竖直的情况
     if (!pos.IsBox(box))
     {
      return FALSE;
     }
     else
     {
      return  ( pos.verdistance(m_begin, m_end) <= dis );//小于给定距离
     }
     

    }

    void CLine::GetBox(CBox2D &box)
    {
       box.m_min.m_x = min(m_begin.m_x, m_end.m_x);
       box.m_min.m_y = min(m_begin.m_y, m_end.m_y);

       box.m_max.m_x = max(m_begin.m_x, m_end.m_x);
       box.m_max.m_y = max(m_begin.m_y, m_end.m_y);
    }

    CSolid* CLine::Rotate(const CPosition &base, float angle)//
    {
     m_begin.Rotate(base, angle);
     m_end.Rotate(base, angle);
     return (CSolid*)this;
    }

    CSolid* CLine::Explan(CPosition pos, short zDelta)
    {
     float scale = 0.0;
     if (zDelta > 0)
     scale = 0.7;
     else
     scale = 1.3;
     
        m_begin.Explan(pos, scale);
     m_end.Explan(pos, scale);
        return (CSolid*)this;
    }

    CSolid* CLine::Move(CPosition first, CPosition second)
    {
         m_begin.Move(first, second);
      m_end.Move(first, second);
      return (CSolid*)this;
    }

    CSolid *CLine::Mirror(CPosition &first, CPosition &second)
    {
      CPosition pos1 = m_begin.Mirror(first, second);
      CPosition pos2 = m_end.Mirror(first, second);
      return new CLine(pos1, pos2);
    }

    void CLine::DrawRect(BOOL br, CPosition &pos, CPosition *bpos)//直线带有三个矩形标记
    {
      CMyrect* rect1 = new CMyrect(m_begin);
         CMyrect* rect2 = new CMyrect(m_end);
      CMyrect* center = new CMyTri( (m_begin + m_end ) * 0.5);
     

     CDC *pDC = g_pView->GetDC();
      
     rect1->DrawRect(pDC, rect1->PisRect(pos), 1, pos, bpos);
      rect2->DrawRect(pDC, rect2->PisRect(pos), 1, pos, bpos);
        center->DrawRect(pDC, center->PisRect(pos), 1, pos, bpos);

       g_pView->ReleaseDC(pDC);

     delete rect1, rect2, center;


     

    }

    CCircle::CCircle(const CPosition begin, const CPosition end)
    {
     m_begin = begin;
       m_end = end;

      
     m_Style = PS_SOLID;
     m_Width = 0;
        m_color = RGB(255, 255, 255);
    }
    BOOL CCircle::PickSolid(CPosition &pos, float dis)//认为圆是有宽度的线,宽度为6个像素
    {
       dis = 3 * ( g_pView->m_scale );
       float r = m_begin.Distance(m_end);
       float dis1 = r - dis;
     
       float dis2 = r + dis;

       float ro = m_begin.Distance(pos);
      

       if (ro >= dis1 && ro <= dis2)
       {
        return TRUE;
       }
       else
       {
        return FALSE;
       }

    }
    CSolid* CCircle::Rotate(const CPosition &base, float angle)//
    {
     m_begin.Rotate(base, angle);
     m_end.Rotate(base, angle);
     return (CSolid*)this;
    }

    CSolid* CCircle::Explan(CPosition pos, short zDelta)
    {
     float scale = 0.0;
     if (zDelta > 0)
     scale = 0.7;
     else
     scale = 1.3;
     
        m_begin.Explan(pos, scale);
     m_end.Explan(pos, scale);
        return (CSolid*)this;
    }

    CSolid* CCircle::Move(CPosition first, CPosition second)
    {
         m_begin.Move(first, second);
      m_end.Move(first, second);
      return (CSolid*)this;
    }

    CSolid *CCircle::Mirror(CPosition &first, CPosition &second)
    {
       CPosition pos1 = m_begin.Mirror(first, second);
       CPosition pos2 = m_end.Mirror(first, second);
       return new CCircle(pos1, pos2);
    }

    class CMyCircle;
    class CCros;
    void CCircle::DrawRect(BOOL br, CPosition &pos, CPosition *bpos)//多边形带有五个矩形标记
    {

      float dis = m_begin.Distance(m_end);

      CDC *pDC = g_pView->GetDC();

     CPosition Numpos[4];
     Numpos[0] = (CPosition(0, 1) * dis + m_begin);
     
     Numpos[1] = (CPosition(0, -1) * dis + m_begin);
     Numpos[2] = (CPosition(1, 0) * dis + m_begin);
     Numpos[3] = (CPosition(-1, 0) * dis + m_begin);
       
     CMyrect *circle = new CMyCircle(m_begin);//画圆心
        circle->DrawRect(pDC, circle->PisRect(pos), 1, pos, bpos);
     delete circle;

     CMyrect *rect = new CCros[4];
     CMyrect::DrawMRect(pDC, 4, Numpos, &pos, bpos, rect);
        delete [] rect;
        g_pView->ReleaseDC(pDC);
    }

    void CCircle::DrawSolid(CDC *pDC, int drawMode)
    {
         CPosition pos[2];
      float dis = m_begin.Distance(m_end);
      pos[0] = CPosition(-1, 0) * dis  + CPosition(0, 1) * dis+ m_begin;
      pos[1] = m_begin * 2 - pos[0];
          
      CPoint point1, point2;

      g_pView->WPTODP(pos[0], point1);
      g_pView->WPTODP(pos[1], point2);

     CPen pen;
      if (drawMode == Normal)//根据输入模式生居画笔
      {
     pen.CreatePen(m_Style, m_Width, m_color);

      }
      else
      {
         GSetDrawMode(pDC, drawMode, &pen);
      }
       
     CBrush brush;
     LOGBRUSH logbrush;
     logbrush.lbStyle = BS_NULL;
     
     brush.CreateBrushIndirect(&logbrush);

     int n = pDC->GetROP2();
      CPen *Oldpen = NULL;
     CBrush *Oldbrush = NULL;
     Oldbrush = pDC->SelectObject(&brush);
      Oldpen = pDC->SelectObject(&pen);

        pDC->Ellipse(&CRect(point1, point2));

     pDC->SetROP2(n);
     pDC->SelectObject(Oldpen);
     pDC->SelectObject(Oldbrush);
       

       
    }

    CCRect::CCRect(const CPosition begin, const CPosition end)
    {
     m_begin = begin;
       m_end = end;

      
     m_Style = PS_SOLID;
     m_Width = 0;
        m_color = RGB(255, 255, 255);
    }
    BOOL CCRect::PickSolid(CPosition &pos, float dis)//分别对四个边捡选,可以直接利用CLine 类
    {
        CPosition Arraypos[5];
           Arraypos[0] = m_begin;
        Arraypos[1] = CPosition(m_begin.m_x, m_end.m_y);//左下
           Arraypos[2] = m_end;
        Arraypos[3] = CPosition(m_end.m_x, m_begin.m_y);//右上
        Arraypos[4] = m_begin;
      
        for (int i = 0; i <4; i++)
        {
               CLine *line = new CLine(Arraypos[i], Arraypos[i + 1]);
         if (line->PickSolid(pos, dis))
         {
                  delete line;
         return TRUE;
         }
        
        
        }
        return FALSE;
      

    }
    CSolid* CCRect::Rotate(const CPosition &base, float angle)//
    {
     m_begin.Rotate(base, angle);
     m_end.Rotate(base, angle);
     return (CSolid*)this;
    }

    CSolid* CCRect::Explan(CPosition pos, short zDelta)
    {
     float scale = 0.0;
     if (zDelta > 0)
     scale = 0.7;
     else
     scale = 1.3;
     
        m_begin.Explan(pos, scale);
     m_end.Explan(pos, scale);
        return (CSolid*)this;
    }

    CSolid* CCRect::Move(CPosition first, CPosition second)
    {
         m_begin.Move(first, second);
      m_end.Move(first, second);
      return (CSolid*)this;
    }

    CSolid *CCRect::Mirror(CPosition &first, CPosition &second)
    {
          CPosition pos1 = m_begin.Mirror(first, second);
       CPosition pos2 = m_end.Mirror(first, second);
       return new CCRect(pos1, pos2); 
    }

    void CCRect::DrawRect(BOOL br, CPosition &pos, CPosition *bpos)//矩形带有9个标记
    {

      CDC *pDC = g_pView->GetDC();

           CPosition Arraypos[4];
           Arraypos[0] = m_begin; //0
        Arraypos[1] = CPosition(m_begin.m_x, m_end.m_y);//左下1///端点
           Arraypos[2] = m_end;//2
        Arraypos[3] = CPosition(m_end.m_x, m_begin.m_y);//右上3

           CPosition CtrArraypos[4];
        CtrArraypos[0] = (Arraypos[0] + Arraypos[3]) * 0.5;//03//中点
        CtrArraypos[1] = (Arraypos[0] + Arraypos[1]) * 0.5;//01
        CtrArraypos[2] = (Arraypos[1] + Arraypos[2]) * 0.5;//12
        CtrArraypos[3] = (Arraypos[2] + Arraypos[3]) * 0.5;//23

       CPosition cenArraypos[1];
       cenArraypos[1] = (Arraypos[0] + Arraypos[2]) * 0.5;//02//圆心

          CMyrect *circle = new CMyCircle(cenArraypos[0]);//画圆心
          circle->DrawRect(pDC, circle->PisRect(pos), 1, pos, bpos);
       delete circle;

       CMyrect *myrect = new CMyrect[4];//端点
          CMyrect::DrawMRect(pDC, 4, Arraypos, &pos, bpos, myrect);
       delete [] myrect;

          CMyrect *rect = new CMyTri[4];
       CMyrect::DrawMRect(pDC, 4, CtrArraypos, &pos, bpos, rect);
       delete [] rect;

        g_pView->ReleaseDC(pDC);
    }

    void CCRect::DrawSolid(CDC *pDC, int drawMode)
    {
      
          
      CPoint point1, point2;

      g_pView->WPTODP(m_begin, point1);
      g_pView->WPTODP(m_end, point2);

     CPen pen;
      if (drawMode == Normal)//根据输入模式生居画笔
      {
     pen.CreatePen(m_Style, m_Width, m_color);

      }
      else
      {
         GSetDrawMode(pDC, drawMode, &pen);
      }
       
     CBrush brush;
     LOGBRUSH logbrush;
     logbrush.lbStyle = BS_NULL;
     
     brush.CreateBrushIndirect(&logbrush);

     int n = pDC->GetROP2();
      CPen *Oldpen = NULL;
     CBrush *Oldbrush = NULL;
     Oldbrush = pDC->SelectObject(&brush);
      Oldpen = pDC->SelectObject(&pen);

        pDC->Rectangle(&CRect(point1, point2));

     pDC->SetROP2(n);
     pDC->SelectObject(Oldpen);
     pDC->SelectObject(Oldbrush);
       

       
    }

  • 相关阅读:
    Codeforces 1105D Kilani and the Game【BFS】
    Codeforces 1096D Easy Problem 【DP】
    Codeforces 920F
    Codeforces 1076D Edge Deletion 【最短路+贪心】
    POJ 3090 Visible Lattice Points 【欧拉函数】
    POJ 1284 Primitive Roots (欧拉函数+原根)
    HDU 2841-Visible Trees 【容斥】
    HDU 1796 How many integers can you find 【容斥】
    HDU 4135 Co-prime (容斥+分解质因子)
    CodeForces 161D Distance in Tree【树形DP】
  • 原文地址:https://www.cnblogs.com/lizhengjin/p/1289226.html
Copyright © 2011-2022 走看看