11.04.2014 Views

Advanced MFC Programming

Advanced MFC Programming

Advanced MFC Programming

SHOW MORE
SHOW LESS

You also want an ePaper? Increase the reach of your titles

YUMPU automatically turns print PDFs into web optimized ePapers that Google loves.

Chapter 11. Sample: Simple Paint<br />

……<br />

……<br />

m_ptPrevious=point;<br />

if(m_rgnFreeSel.GetSafeHandle() != NULL)<br />

{<br />

m_rgnFreeSel.DeleteObject();<br />

}<br />

m_dcMem.MoveTo(m_ptMouseDown);<br />

m_dcMem.BeginPath();<br />

For WM_MOUSEMOVE message, we need to draw the freeform outline in the client window and do the<br />

same thing to CGDIView::m_bmpDraw. Note since the current image ratio may not be 1:1, we must use<br />

normalized points when recording path:<br />

……<br />

……<br />

pPenOld=dc.SelectObject(&m_penDot);<br />

dc.MoveTo(m_ptPrevious);<br />

dc.LineTo(point);<br />

m_ptPrevious=point;<br />

dc.SelectObject(pPenOld);<br />

m_dcMem.LineTo(pt);<br />

For WM_LBUTTONUP message, we need to draw the last segment of outline, close the figure, and end the<br />

path. Then we need to create the region from path, and set the dimension of the tracker to the dimension of<br />

the bounding box of the selected region. Again we must consider ratio conversion here: since the path is<br />

recorded with a ratio of 1:1, we must scale its bounding box to the current image ratio. In the sample,<br />

function CGDIView::UnnormalizeTrackerRect(…) is added to scale a normalized rectangle to the current<br />

image ratio. The rest thing needs to be done is the same with that of rectangular selection: we need to back<br />

up the whole image as well as the selected area:<br />

……<br />

……<br />

pPenOld=dc.SelectObject(&m_penDot);<br />

dc.MoveTo(m_ptPrevious);<br />

dc.LineTo(point);<br />

dc.SelectObject(pPenOld);<br />

m_dcMem.LineTo(pt);<br />

m_dcMem.CloseFigure();<br />

m_dcMem.EndPath();<br />

m_rgnFreeSel.CreateFromPath(&m_dcMem);<br />

m_rgnFreeSel.GetRgnBox(rect);<br />

m_trackerSel.m_rect=UnnormalizeTrackerRect(rect);<br />

BackupCurrentBmp();<br />

BackupSelection();<br />

Invalidate(FALSE);<br />

Resizing and Moving the Freeform Selection<br />

Resizing and moving the freeform selection is almost the same with that of rectangular selection,<br />

except that before copying the selected area, we must offset or resize the region and select it into the target<br />

DC. The following portion of function CGDIView::OnLButtonDown(…) shows how the region is resized and<br />

selected into the target memory DC, and how the selected image is copied back:<br />

……<br />

::ReleaseCapture();<br />

m_trackerSel.Track(this, point);<br />

ResumeBackupBmp();<br />

m_rgnFreeSel.GetRgnBox(rectOrgTracker);<br />

rectCurTracker=NormalizeTrackerRect(m_trackerSel.m_rect);<br />

nCount=m_rgnFreeSel.GetRegionData(NULL, 0);<br />

lpRgnData=(LPRGNDATA)new BYTE[nCount];<br />

360

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!