Windows 编程基础
十、绘制直线 返回
学会了画点,下一步就该是画线了,线是由点组成的,每个点的位置用两个数来表示(x,y),即平面直角坐标系,
一条直线有两个点,或者说两点确定一条直线,一个是起点,一个是终点,如果连续画线,上一次的终点就是下一次的起点,弄明白了这两个点,我们就来来学习一下,怎样在自己的窗口中画出漂亮的线条来;
画线也用到设备,画线的函数是LineTo(hdc,(x,y));其中的(x,y)是终点,起点用上次的终点,第一次起点是(0,0),屏幕的左上角,
另一个是移动函数MoveToEx(hdc,(x,y),NULL);把起点设为上一次的终点,下面我们来编制程序:
1、启动VC,新建一个名为Line的Win32 Application工程,再新建一个相同名称的头文件和源程序文件,在头文件中输入函数的申明,在源程序中输入窗口框架代码;
2、画线的鼠标指针是十字形的,把第3课中的指针文件curMouse拷贝到Line文件夹中,
在头文件中加入一句标识符申明#define IDC_MYCUR 201
再用记事本新建一个相同文件名的资源文件Line.rc输入鼠标指针的定义:IDC_MYCUR CURSOR DISCARDABLE "curMouse.cur" 保存并关闭文件;
3、使用工程菜单中的“添加工程”命令将资源文件Line.rc加入到工程中,
再在InitApplication函数中修改加载鼠标指针一句为wcexLine.hCursor=LoadCursor(hInstance,MAKEINTRESOURCE(201));
其中wcexLine是窗口类名,根据自己的代码修改一致,注意标识符前后一致;
4、加入消息处理函数过程,画线是用鼠标,因此需要处理鼠标按键消息WM_LBUTTONDOWN以及鼠标拖动的消息WM_MOUSEMOVE,还有鼠标抬起WM_LBUTTONUP消息;
消息处理过程MainWndProc(绿色双斜杠部分是注释),有的一行太长会自动折到下一行,代码如下,细细品味每一行的作用是铺垫呢,还是操作;是给谁铺垫,操作结果又是什么呢?
   
LRESULT APIENTRY MainWndProc(
       
    HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)
       
{
    HDC hdc;
   
     
    static HPEN hpenBlue;//申明一支彩色笔;
      
    static POINT pointBegin,pointEnd,point;//保存起点和终点,当前点;
      
    static  int       
x1,y1;//单击鼠标画线的终点位置
      
    switch (message)
       
    {
      
      case WM_CREATE:   // 创建一支彩色笔 
      
        hpenBlue = CreatePen(PS_SOLID, 1, RGB(0,0,255));
       
        break;
      case WM_LBUTTONDOWN://左键按下
      
        pointBegin.x =LOWORD(lParam);//初始化起点x
      
        pointBegin.y=HIWORD(lParam);//初始化起点y
      
        pointEnd.x=LOWORD(lParam);//初始化终点x
      
        pointEnd.y=HIWORD(lParam);//初始化终点y
      
        //当前点的位置用默认为屏幕左上角(0,0)      
    
        SetCapture(hWnd);//一直跟着鼠标 
     
        break;
      
      case WM_MOUSEMOVE://进入鼠标移动消息;
      
        if(wParam & MK_LBUTTON)//检测左键是否按下;
      
        {//进入鼠标拖动;
      
          point.x =LOWORD(lParam);//当前鼠标的位置x;
      
          point.y=HIWORD(lParam);//当前鼠标的位置y;
      
          hdc=GetDC(hWnd); 
      
          SetROP2(hdc,R2_NOT);//使用与背景色相反的颜色;
      
                
//第二次用与背景色相反的颜色绘制,可以擦去原来的线条(双重否定);
          MoveToEx(hdc,pointBegin.x,pointBegin.y,NULL);
      
                
//画线起点是单击左键时的鼠标的位置
                
LineTo(hdc,pointEnd.x,pointEnd.y);
                
//擦除上次绘出的直线; 
          //第二次移动时,先把第一次的线擦除,然后下面画这次移动的线;
      
          MoveToEx(hdc,pointBegin.x,pointBegin.y,NULL);//原来鼠标的位置
      
          LineTo(hdc,point.x,point.y);//point是当前鼠标的位置
      
          
//这两条语句将绘制一条从起点到当前鼠标位置的线;
      
          pointEnd.x=point.x;  pointEnd.y=point.y;
       
                
//这两条语句保存当前鼠标位置,以便于鼠标移动后可以擦除这次绘制的直线
                
ReleaseDC(hWnd,hdc); 
        }
      
        break;
      
        case WM_LBUTTONUP:
       
        //如果是单击画图将会用彩色笔     
   
               
ReleaseCapture();//解除鼠标跟踪
          hdc=GetDC(hWnd);
     
          SelectObject(hdc, hpenBlue);//换上彩色笔
     
          MoveToEx(hdc,point.x,point.y,NULL);
     
          //设定起点,在鼠标移动消息中修改了point
     
          x1=LOWORD(lParam);//画线终点x;
     
          y1=HIWORD(lParam);//画线终点y;
     
          LineTo(hdc,x1,y1);//从起点到当前点画线
     
          //point.x=x1;//修改当前点的位置为这次的结束位置,
     
          //point.y=y1;//不修改就一直用同一个起点(星形)
     
          ReleaseDC(hWnd,hdc); 
     
          break;
     
        case WM_DESTROY://退出应用程序;
     
          PostQuitMessage(0);//向系统发送一条WM_QUIT消息,
     
          break;
     
        default:      
 //让系统帮着处理的消息
          return (DefWindowProc(hWnd,message,wParam,lParam));
      
    }
     
    return 0; 
     
}
 保存一下文件
,单击编译条上的“构建”按钮
,如果出现错误就仔细检查一下,然后单击“执行”按钮
,看看又前进一步的程序窗口;
本节学习了在用户区用鼠标画线的代码设计,如果你成功地完成了练习,请继续学习下一课内容;
余音绕梁 (在弹出的对话框中选择“运行”、“运行”)
本教程由86团学校TeliuTe制作|著作权所有
基础教程网:http://teliute.org/
美丽的校园……
转载和引用本站内容,请保留作者和本站链接。