基于MFC 开发的截图工具 文件名:Draw 创建单个文档,MFC标准 一.将视图显示 1.MainFrm.cpp 中 int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct) SetMenu(NULL); 去掉菜单 CBRS_BOTTOM 将工具栏现实在下面 将状态显示的代码去掉 BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs) cs.style=WS_POPUP; 2.Draw.cpp(App类) BOOL CDrawApp::InitInstance() m_pMainWnd->ShowWindow(SW_MAXIMIZE); 3.添加按ESC退出界面 在类视图CDrawView添加消息OnKeyDown if(nChar ==VK_ESCAPE) { ::PostQuitMessage(0); } 4.在资源视图新创建一个ToolBar,并添加消息处理 在CDrawView.h afx_msg void OnQuit();//退出 afx_msg void OnCureve(); afx_msg void OnLine(); afx_msg void OnEllipse(); afx_msg void OnRect(); afx_msg void OnTriangle(); afx_msg void OnFill(); afx_msg void OnColor(); afx_msg void OnSave(); 在CDrawView.cpp ON_COMMAND(ID_QUIT,&CMainFrame::OnQuit) ON_COMMAND(ID_CURVE,&CMainFrame::OnCureve) ON_COMMAND(ID_ONLINE,&CMainFrame::OnLine) ON_COMMAND(ID_ELS,&CMainFrame::OnEllipse) ON_COMMAND(ID_RECT,&CMainFrame::OnRect) ON_COMMAND(ID_TRA,&CMainFrame::OnTriangle) ON_COMMAND(ID_RECT,&CMainFrame::OnRect) ON_COMMAND(ID_FILL,&CMainFrame::OnFill) ON_COMMAND(ID_SAVE,&CMainFrame::OnSave) ON_COMMAND(ID_COLOR,&CMainFrame::OnColor) 5.将桌面图片显示到视图上 在CMainFram.h list<CBitmap *> m_lstDesktopBmp;//每次画一笔都要装到链表里 int m_nScreenX; int m_nScreenY; 在CMainFrame.cpp CMainFrame::CMainFrame() { m_nScreenX=GetSystemMetrics(SM_CXSCREEN); m_nScreenY=GetSystemMetrics(SM_CYSCREEN); //获取桌面的图片 CWindowDC m_dcDesktop(GetDesktopWindow()); //保存这张图片 CBitmap *bitmap=new CBitmap; bitmap->CreateCompatibleBitmap(&m_dcDesktop,m_nScreenX,m_nScreenY); //创建一个DC CDC cdc; cdc.CreateCompatibleDC(&m_dcDesktop); cdc.SelectObject(bitmap); //把桌面的图片放到cdc里 cdc.BitBlt(0,0,m_nScreenX,m_nScreenY,&m_dcDesktop,0,0,SRCCOPY); //把bitmap放到链表里 m_lstDesktopBmp.push_back(bitmap); } 在CDrawView.h中 void CDrawView::OnDraw(CDC* /*pDC*/) // 把 链表的 尾节点的图片 放到 view 上 CMainFrame* frame = (CMainFrame*)AfxGetMainWnd(); CClientDC dc(this); // 窗口 CDC cdc; // 装 链表 尾节点里的 图片 cdc.CreateCompatibleDC(&dc); cdc.SelectObject(frame->m_lstDesktopBmp.back()); // 把 链表 尾节点里的 图片 装到 cdc dc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&cdc,0,0,SRCCOPY); 二.画图 1,鼠标左键抬起保存图片到链表尾部(m_nDrawStyle判断画的是什么图形,m_nbDrawFlag判断是否画图,要在构造函数初始化) void CDrawView::OnLButtonUp(UINT nFlags, CPoint point) { // TODO: 在此添加消息处理程序代码和/或调用默认值 m_bDrawFlag=false; //保存图片到链表 CMainFrame *frame=(CMainFrame*)AfxGetMainWnd(); CClientDC dc(this); CBitmap *bitmap=new CBitmap; bitmap->CreateCompatibleBitmap(&dc,frame->m_nScreenX,frame->m_nScreenY); CDC cdc; cdc.CreateCompatibleDC(&dc); cdc.SelectObject(bitmap); cdc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&dc,0,0,SRCCOPY); frame->m_lstDesktopBmp.push_back(bitmap); CView::OnLButtonUp(nFlags, point); } 2.画图 void CDrawView::OnMouseMove(UINT nFlags, CPoint point) { // TODO: 在此添加消息处理程序代码和/或调用默认值 if(m_bDrawFlag==true) { CMainFrame *frame=(CMainFrame*)AfxGetMainWnd(); CClientDC dc(this); //创建兼容性 DC //拿链表的最后一张图片刷新 CDC cdc; cdc.CreateCompatibleDC(&dc); cdc.SelectObject(frame->m_lstDesktopBmp.back()); //创建一个位图Bitmap //复制链表尾结点的图片 CBitmap bitmap; bitmap.CreateCompatibleBitmap(&dc,frame->m_nScreenX,frame->m_nScreenY); CDC tempdc; tempdc.CreateCompatibleDC(&dc); tempdc.SelectObject(bitmap); tempdc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&cdc,0,0,SRCCOPY); //不能传输dc到tempdc //看画什么图形 switch (m_nDrawStyle) { case ID_CURVE: dc.MoveTo(m_pointMouseDown.x,m_pointMouseDown.y); dc.LineTo(point.x,point.y); m_pointMouseDown=point; break; case ID_ONLINE: //不能用cdc画图,因为cdc就是链表的最后一张位图,更改cdc就是更改最后一张图片 //所以在tempdc上面画图 //移动一次创建的Bitmap就删除,没有改变 tempdc.MoveTo(m_pointMouseDown.x,m_pointMouseDown.y); tempdc.LineTo(point.x,point.y); dc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&tempdc,0,0,SRCCOPY); break; case ID_ELS: tempdc.SelectStockObject(NULL_BRUSH); tempdc.Ellipse(m_pointMouseDown.x,m_pointMouseDown.y,point.x,point.y); dc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&tempdc,0,0,SRCCOPY); break; case ID_RECT: tempdc.Rectangle(m_pointMouseDown.x,m_pointMouseDown.y,point.x,point.y); dc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&tempdc,0,0,SRCCOPY); break; case ID_TRA: tempdc.SelectStockObject(NULL_BRUSH); POINT rect[3]={{(point.x+m_pointMouseDown.x)/2,m_pointMouseDown.y},{m_pointMouseDown.x,point.y},{point.x,point.y}}; tempdc.Polygon(rect,3); dc.BitBlt(0,0,frame->m_nScreenX,frame->m_nScreenY,&tempdc,0,0,SRCCOPY); break; } } CView::OnMouseMove(nFlags, point); }