01 画直线
按下是起点,松手是终点
- 鼠标按下和抬起
- 创建画家对象
cpaintdc 只能在onpaint中使用
cclientdc 在任何地方都可以使用 - 起点和终点
cdc::moveto
cdc:lineto
添加变量
类型直接手打就行
添加消息
属性->消息
- 鼠标左键按下
- 鼠标左键释放
添加代码
//鼠标按下
void CtestView::OnLButtonDown(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
m_Point = point;//保存点击的坐标
CView::OnLButtonDown(nFlags, point);
}
//鼠标抬起
void CtestView::OnLButtonUp(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
//创建画家 指定绘图设备
CClientDC dc(this);
dc.MoveTo(m_Point);
dc.LineTo(point);
CView::OnLButtonUp(nFlags, point);
}
02 画连续的线
不停地画点,移动的每一点都画出来
- 鼠标移动,移动的每一点都画出来
- 标志位,有没有按下
- 理清逻辑关系很重要
实现:
- 添加标志位:
- 鼠标左键按下时标志位为true
//鼠标左键按下
void CtestView::OnLButtonDown(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
m_Point = point;//保存点击的坐标
m_isPress = true;//鼠标左键按下
CView::OnLButtonDown(nFlags, point);
}
- 鼠标左键抬起时标志位为false
void CtestView::OnLButtonUp(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
m_isPress = false;//鼠标左键抬起时标志位变化
CView::OnLButtonUp(nFlags, point);
}
- 只有按下的时候才能画,画的时候应该放在鼠标移动事件中
属性->消息->MouseMove
void CtestView::OnMouseMove(UINT nFlags, CPoint point)
{
// TODO: 在此添加消息处理程序代码和/或调用默认值
//先做判断
if (m_isPress == true)//如果鼠标按下
{
//创建画家 指定绘图设备
CClientDC dc(this);
dc.MoveTo(m_Point);
dc.LineTo(point);
//终点作为起点,就是重新赋值即可
m_Point = point;//point为当前的点
}
CView::OnMouseMove(nFlags, point);
}
03 画笔和画刷的使用
流程:
定义画家CDC *pDC
定义画笔、画刷CPen CBrush
把画笔交给画家CDC::SelectObject选择画笔/画刷
- CDC *pDC;
- CPen myPen();
- CBrush brush;
- pDC->SelectObject(&myPen);//画家选择一支画笔
- CPen *oldPen = pDC->SelectObject(&myPen);
SelectObject返回值的作用:画笔使用过后得进行还原,恢复原来的GDI ,释放资源
void CtestView::OnDraw(CDC* pDC)
{
CtestDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
if (!pDoc)
return;
// TODO: 在此处为本机数据添加绘制代码
//pDC->TextOutW(100, 100, TEXT("This is OnDraw()"));
CPen myPen(PS_SOLID, 3, RGB(255, 0, 0));//定义一支画笔
CPen *oldPen = pDC->SelectObject(&myPen);//把画笔交给画家 SelectObject返回值的作用:画笔使用过后得进行还原,恢复原来的GDI 释放资源
pDC->MoveTo(10, 10);//起点坐标
pDC->LineTo(120, 10);//终点坐标
//画一个内切圆(画另一个图形)
pDC->SelectObject(oldPen); //重新定义一支画笔(如果不,则画出来的内切圆是上一个画笔的状态)
pDC->Ellipse(30, 30, 130, 130);//画一个内切圆(左上角,右下角坐标)
//画刷的使用
CBrush myBrush(RGB(255, 0, 0));//定义一个画刷
CBrush *oldBrush = pDC->SelectObject(&myBrush);//把画刷交给画家
pDC->Ellipse(30, 30, 130, 130);
}
04 位图加载
- 首先准备一张位图图片,后缀为.bmp的图片(QQ截图里可以设置)
- 将图片放进当前项目的res文件夹里
- 在资源视图中,右击->添加资源->选中Bitmap->导入->在res文件夹中选择刚才的图片(如果没有,右下角选择所有文件就会出来)
/*写在OnDraw函数中*/
//图片填充区域
CBitmap myBitmap;//定义一个位图对象
myBitmap.LoadBitmapW(IDB_BITMAP1);//加载位图,IDB_BITMAP1为刚才添加的位图的ID,报红也没关系,不影响(最好是添加头文件"resource.h")
CBrush myBrush2(&myBitmap);//位图放进画刷中
pDC->SelectObject(&myBrush2);//把画刷交给画家
pDC->Ellipse(0, 0, 100, 100);//图片填充内切圆
可以看到,后画的图会盖住先画的图,如果区域重合的话;