当我在兼容DC中进行绘图操作 相应的绘图会保存在之前选入的位图中吗?比如以下代码
它是如何进行存储的?其中m_bmpbuf 及m_bmpsave是存储的位图,这些代码怎么实现将在内存中的绘图操作保存在位图中的?
谢谢~
void CToDrawView::OnMouseMove(UINT nFlags, CPoint point) 
{
// TODO: Add your message handler code here and/or call default CDC* pDC = GetDC(); CPoint pOrig = GetScrollPosition();
point += pOrig; // Change screen point to logical point

CToDrawDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);

// Update status bar状态栏坐标显示
if (point.x <= pDoc->m_CanvasRect.right && point.y <= pDoc->m_CanvasRect.bottom)
{
CMainFrame* pMf = static_cast<CMainFrame*>(::AfxGetMainWnd());
pMf->UpdateStatusBar(point);
} if (m_pLMouseDown)
{
CDC dcMemSave;
dcMemSave.CreateCompatibleDC(NULL);
dcMemSave.SelectObject(&pDoc->m_bmpSave); CDC dcMem;
dcMem.CreateCompatibleDC(NULL);
dcMem.SelectObject(&pDoc->m_bmpBuf); dcMem.BitBlt(0, 0, pDoc->m_CanvasRect.Width(), pDoc->m_CanvasRect.Height(), &dcMemSave, 0, 0, SRCCOPY);
dcMem.SetBkColor(pDoc->m_BackgroundColor);
dcMem.SetBkMode(pDoc->m_BackgroundMode);
dcMem.SetROP2(R2_COPYPEN); switch (pDoc->m_Mode)
{
case DRAW_SELECT: // Select something
if (pDoc->m_isDrawOn)
{
pDoc->m_pDrawObject->m_pEnd = point;
pDoc->m_pDrawObject->Draw(&dcMem);
}
else if (pDoc->m_isInSelect)
{
CDC dcMemSelect;
dcMemSelect.CreateCompatibleDC(NULL);
dcMemSelect.SelectObject(&pDoc->m_bmpSelect);
dcMem.BitBlt(pDoc->m_SelectRect.left+point.x-pDoc->m_SelectPoint.x, pDoc->m_SelectRect.top+point.y-pDoc->m_SelectPoint.y, pDoc->m_SelectRect.Width(), pDoc->m_SelectRect.Height(), &dcMemSelect, 0, 0, SRCCOPY);

pDoc->SetModifiedFlag();
}
break;
case DRAW_ERASER: // Erase something
pDoc->m_pDrawObject->m_pEnd = point;
pDoc->m_pDrawObject->Draw(&dcMem);
dcMemSave.BitBlt(0, 0, pDoc->m_CanvasRect.Width(), pDoc->m_CanvasRect.Height(), &dcMem, 0, 0, SRCCOPY);
pDoc->m_pDrawObject->m_pBegin = point;
break;
case DRAW_FILLING: // Fill a region
break;
case DRAW_SAMPLING: // Get color information of the poin
pDoc->m_PenColor = pDC->GetPixel(point);
break;

case DRAW_PEN: // Draw freely using a pen将dcmem中的图显示于屏幕 dcmemsave的储存 并且在dcmem中绘图
pDoc->m_pDrawObject->m_pEnd = point;//综上所述 即先在dcmem中绘图,然后将dcmem中的图拷贝到dcmemsave,最后用dcmem显示
pDoc->m_pDrawObject->Draw(&dcMem);
dcMemSave.BitBlt(0, 0, pDoc->m_CanvasRect.Width(), pDoc->m_CanvasRect.Height(), &dcMem, 0, 0, SRCCOPY);
pDoc->m_pDrawObject->m_pBegin = point;
break;
case DRAW_BRUSH: // Draw freely using a brush
pDoc->m_pDrawObject->m_pEnd = point;
pDoc->m_pDrawObject->Draw(&dcMem);
dcMemSave.BitBlt(0, 0, pDoc->m_CanvasRect.Width(), pDoc->m_CanvasRect.Height(), &dcMem, 0, 0, SRCCOPY);
pDoc->m_pDrawObject->m_pBegin = point;
break;
case DRAW_CURVE: // Draw Bezier curve
switch (pDoc->m_MouseDownTime)
{
case 1:
pDoc->m_pDrawObject->m_pEnd = point;
pDoc->m_pDrawObject->Draw(&dcMem);
break;
case 2:
pDoc->m_pDrawObject->m_pHelp1 = point;
pDoc->m_pDrawObject->m_pHelp2 = point;
pDoc->m_pDrawObject->Draw(&dcMem);
break;
case 3:
pDoc->m_pDrawObject->m_pHelp2 = point;
pDoc->m_pDrawObject->Draw(&dcMem);
break;
}
break;
case DRAW_LINE: // Line
case DRAW_RECTANGLE: // Rectangle
case DRAW_POLYGON: // Polygon
case DRAW_ELLIPSE: // Ellipse
case DRAW_ROUNDRECT: // Round rectangle
pDoc->m_pDrawObject->m_pEnd = point;
pDoc->m_pDrawObject->Draw(&dcMem);
break;
} // Copy memory to screen
CRect rect;
GetClientRect(&rect);
pDC->BitBlt(0, 0, rect.Width(), rect.Height(), &dcMem, pOrig.x, pOrig.y, SRCCOPY);
} CScrollView::OnMouseMove(nFlags, point);
}

解决方案 »

  1.   

    所谓“在内存DC”(或者叫兼容DC)中绘图,实际上就是在被你选入该DC中的位图上绘图。只要这个位图没有被删除(即使内存DC已经被删除掉),那么你在上面所绘的图就不会消失。
      

  2.   

    再问一下啊  为什么这些又显示出来黑的一片
    void CBoardView::OnInitialUpdate()
    {
    CView::OnInitialUpdate(); // TODO: 在此添加专用代码和/或调用基类
    membitmap.CreateBitmap(1000,300,NULL,NULL,NULL);}
    void CBoardView::OnLButtonDown(UINT nFlags, CPoint point)
    {
    // TODO: 在此添加消息处理程序代码和/或调用默认值
    pt = point; CView::OnLButtonDown(nFlags, point);
    }
    void CBoardView::OnMouseMove(UINT nFlags, CPoint point)
    {
    // TODO: 在此添加消息处理程序代码和/或调用默认值 if(nFlags == MK_LBUTTON)
    {
    // *pdc = GetDC();
    CDC memdc;
    memdc.CreateCompatibleDC(NULL);
    memdc.SelectObject(&membitmap);
    memdc.MoveTo(pt.x,pt.y);
    memdc.LineTo(point.x,point.y);
    pt = point;
    }}
    void CBoardView::OnDraw(CDC* pDC)
    {
    CBoardDoc* pDoc = GetDocument();
    ASSERT_VALID(pDoc);
    if (!pDoc)
    return; // TODO: 在此处为本机数据添加绘制代码
    CDC memdc;
    memdc.CreateCompatibleDC(NULL);
    memdc.SelectObject(&membitmap);
    pDC->BitBlt(0,0,1000,300,&memdc,0,0,SRCCOPY);
    }
      

  3.   

    membitmap.CreateBitmap(1000,300,NULL,NULL,NULL);
    你的后三个参数全是NULL,还怎么可能正确地生成出位图?位图没生成你往哪里画?
    建议不要用CreateBitmap,而要用CreateCompatibleBitmap。
      

  4.   

    我也有类似问题,一个内存dc先后选择不同的Bitmap,结果后面画的图出现在前面的Bitmap上。所以一个dc对应一个bitmap最好。