GDI:
画画软件讲解:
1:GDI里面各种要做的非常多,每次使用GDI函数都需要GetDc,最后都需要回收,因此,完全可以封装一个自己的类,创建窗口,构造对象的时候就创建好Dc,之后一直用。
2:画线,可以通过记录整个鼠标移动过程的方式,每次更新的时候,按照这个步骤重画,也可以直接记录一整张图,每次冲刺年画一个图,再画当前画的,就好了。
3:要实现铅笔的功能,只需要在WM_MOUSEMOVE里面将每次移动的点用线连接起来,而不是一直画点,这样会不连续
4:双缓冲绘图:每次页面刷新的时候,是一个一个的画出来的,导致最后看起来页面非常的闪,双缓冲就是现在一个内存Dc上面画完,花完之后直接拿过来,一次性显示出来,这就算是双缓冲。不同需求可能有三缓冲,多缓冲等,因为绘图过程非常多,比较复杂。一般在贴图的时候,才需要缓冲,一般的简单的画,是不需要使用缓冲的。
Win32封装:
1:在使用Win32的时候,消息非常多,就鼠标消息和键盘消息而言, 我们可以做一定的封装,以鼠标消息为例:
按照程序需要实现的功能,将鼠标消息分成不同种,都继承于一个基类,当切换功能的时候,只需要重新new一个该功能的鼠标操作对象,在系统的回调函数里面就不需要对鼠标消息进行更改就能直接使用,在软件需要添加功能的时候,同样的,只需要多写一个子类即可,修改和维护都非常方便。
多鼠标消息的封装就只是对鼠标消息的处理和记录,不可以在这里面去绘图,处理外部的一些事情。
同样的,也可以对绘图,键盘消息等进行封装,因为在Win32的回调函数里面,这几个消息往往一写就是上千行,在做稍微大一点的程序的时候,就会显得非常乱。
2:GDI API:
1:CreateCompatibleDC,创建一个兼容DC,但是兼容DC只能是双色的DC,也就是说,只能是黑白的图,双缓冲的时候,会用到兼容DC。
2:CreateCompatibleBitmap:一般用于给创建的兼容DC创建一个兼容的BitMap,供兼容DC使用。
3:BitBlt:用于从指定的源设备上下文像素矩形到目标设备上下文的颜色数据的位块传输。可以将兼容DC的内容,拷贝到要显示的DC上面的一个地方去。
4:StretchBlt:与BitBlt类似,用于拷贝,但是,它可以改变原来的形状,拷贝从源矩形成目标矩形,拉伸或压缩位图以适应目标矩形的尺寸,必要的位图。系统根据目标设备上下文中设置的拉伸模式来拉伸或压缩位图。
打开文件对话框的创建:
函数示例:
OPENFILENAME ofn = { 0 };
ofn.lStructSize = sizeof(OPENFILENAME);
ofn.lpstrFile = g_PicFilePath;
ofn.nMaxFile = MAX_PATH;
ofn.hwndOwner = hWnd;
ofn.lpstrFilter = TEXT("位图(*.bmp)\0*.bmp\0"); // 显示\0过滤器\0显示\0过滤器\0 最后\0结尾
ofn.nFilterIndex = 1;
ofn.Flags = OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST;
if (GetOpenFileName(&ofn))
{
//打开成功后,对文件的处理
}
OPENFILENAME是打开文件对话框需要传递的结构体,用于指定打开文件的一些属性,限制
Win32加载图片:
1:加载图片可以使用LoadBiMap,也可以使用LoadImage。后者功能更强大。
HBITMAP SelBitmap = (HBITMAP)LoadImage(hInst, g_PicFilePath, IMAGE_BITMAP, 0, 0, LR_CREATEDIBSECTION | LR_LOADFROMFILE);
BITMAP bmp;
GetObject(SelBitmap, sizeof(BITMAP), &bmp);
2:从HBITMAO中获取到的BITMAP对象,可以冲BITMAP中获取到位图的长宽等信息,具体如下:
typedef struct tagBITMAP {
LONG bmType;//必须为0
LONG bmWidth;//宽
LONG bmHeight;//高
LONG bmWidthBytes;//一横排图像占用的的字节数
WORD bmPlanes;//色彩数
WORD bmBitsPixel;//指示像素颜色需要的位数
LPVOID bmBits;//指向该位图的指针。
} BITMAP, *PBITMAP;
3:LoadImage:
HANDLE WINAPI LoadImage(
_In_opt_ HINSTANCE hinst,//模块句柄,就是主函数传进来的当前进程的实例句柄。
_In_ LPCTSTR lpszName,//图片的路径和图片名
_In_ UINT uType,//图片类型
_In_ int cxDesired,//指定图标宽度
_In_ int cyDesired,//高度
_In_ UINT fuLoad//指定图标属性,可以输一系列的组合
);
1:图片类型:只能为IMAGE_BITMAP,IMAGE_CURSOR,或者IMAGE_ICON三种,指定加载的图标类型。
2:图标属性:可以指定图片为黑白,彩色,从文件加载等属性。
控件:
控件种类:
1:在MSDN的
Desktop technologies->Desktop App UI->Windows Controls里面,可以查看Windows提供的所有控件,他们均可以在Win32里面使用。
2:在Win32界面使用这些控件可以使用CreateWindow来创建,然后使用ShowWindow使控件显示出来,在控件创建的时候,会指定创建窗口(每个控件都是一个窗口)的属性,其中有一个HMENU的参数,适用于指定这个控件的ID,为之后处理这个控件的消息使用的。
3:使用示例:
HWND hButton7 = CreateWindow(L"BUTTON", L"7", WS_CHILD, 2, ParanH + 2, wx - 4, wy - 4, hWnd, (HMENU)IDC_NUM7, hInst, NULL);//里面的参数需在外部定义
ShowWindow(hButton7, SW_SHOW);
4:在响应这些控件的消息的时候,可能一个控件有多种消息需要响应,也需要获取这些控件传递给消息函数的参数,例如位置,鼠标键盘消息,具体的参考MSDN的例子。