Draw rectangle on CView and Track using CRectTracker

This blog will be helpful for those who want to draw a rectangle using mouse dragging feature and show a re-sizing handler and also want to move a rectangle from one position to another.
 
Step 1

Open the .h header file of subclass of CView in editor.

Eg: In this example , using CDrawViewView.h header file which is subclass of CView.

Step 2

Declare a protected variable in .h file.

CRectTracker                               m_RectTracker;              // Rect Tracker
CArray<CRect, CRect&>            m_RectArray;              // Contains reference of Rect

Step 3

Declare a protected method in .h file.
  1. bool LMouseButtonDown(CPoint point); // Method called from left mouse buton down event.  
  2. afx_msg void OnLButtonDown(UINT flags, CPoint point);  
  3. afx_msg BOOL OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message);  
  4. afx_msg void OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags);  
Step 4

Open .m file such as CDrawViewView.m in editor and modify begin message map and declare message block.
  1. BEGIN_MESSAGE_MAP(CDrawViewView, CView)  
  2. ON_WM_LBUTTONDOWN()  
  3. ON_WM_SETCURSOR()  
  4. END_MESSAGE_MAP()  
Step 5

And placed following code in .m file.
  1.   CDrawViewView::CDrawViewView()  
  2.   {     
  3.            m_RectTracker.m_rect.SetRect(-1,-1,-1,-1);     
  4.            m_RectTracker.m_nStyle = CRectTracker::resizeOutside|CRectTracker::dottedLine;  
  5.   }         
  6.   
  7.      /* Method invoked to check whether user selected rectangle or not */  
  8.      bool CDrawViewView::LMouseButtonDown(CPoint point)  
  9.      {  
  10.                  bool status = false;  
  11.                  int rectCount = m_RectArray.GetCount();  
  12.                   
  13.                   if (rectCount <= 0)  
  14.                           return status;  
  15.                  for (int i = 0; i < rectCount; ++i)  
  16.                  {  
  17.                           CRect rect = m_RectArray[i];  
  18.                           if (rect.PtInRect(point))  
  19.                           {  
  20.                                    m_RectTracker.m_rect = rect;  
  21.                                    m_RectArray.RemoveAt(i);  
  22.                                    status = true;  
  23.                                    break;  
  24.                           }  
  25.                  }  
  26.                  return status;  
  27.            }  
  28.   
  29.   
  30.  void CDrawViewView::OnLButtonDown(UINT nFlags, CPoint point)  
  31.  {  
  32.      if (!LMouseButtonDown(point))  
  33.      {  
  34.        
  35.            if (m_RectTracker.TrackRubberBand(this, point, true))  
  36.            {  
  37.                     CRect rect = new CRect(m_RectTracker.m_rect);  
  38.                     m_RectArray.Add(rect);  
  39.            }  
  40.      }  
  41.      else  
  42.      {  
  43.               m_RectTracker.Track(this, point, true);  
  44.               CRect rect = new CRect(m_RectTracker.m_rect);  
  45.               m_RectArray.Add(rect);  
  46.      }  
  47.   
  48.   Invalidate();  
  49.   CView::OnLButtonDown(nFlags, point);  
  50.   
  51.   
  52.   void CDrawViewView::OnDraw(CDC* pDC)  
  53.   {  
  54.               CDrawViewDoc* pDoc = GetDocument();  
  55.               ASSERT_VALID(pDoc);  
  56.               if (!pDoc)  
  57.                     return;  
  58.   
  59.     
  60.               int rectCount = m_RectArray.GetCount();  
  61.               if (rectCount > 0)  
  62.               {  
  63.                        for (int i = 0; i < rectCount; ++i)  
  64.                        {  
  65.                                       CRect currentRect = m_RectArray[i];  
  66.                                       pDC->Rectangle(currentRect);  
  67.                         }  
  68.                          m_RectTracker.Draw(pDC);  
  69.                  }  
  70.       }