Windows 图形设备接口(Graphics Device Interface, GDI)使应用程序能够在视频显示器使用图形和格式化文本。
设备环境是Windows中内部使用的数据结构,它定义了GDI函数在显示设备特定区域的工作方式。要想在某个区域输出文字或绘制图形,必须先获取该区域的设备句柄。
首先看下面的部分代码:
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = ::BeginPaint(hwnd, &ps);
::TextOut(hdc, 0, 0, TEXT("Hello GDI"), strlen("Hello GDI"));
::EndPaint(hwnd, &ps);
return 0;
}
表示在客户区绘制文字,Hello GDI
如果不想在 WM_PAINT 消息中绘制,可以使用函数 GetDC 函数
case WM_LBUTTONDOWN:
{
HDC hdc = ::GetDC(hwnd);
::SetTextColor(hdc, RGB(255, 0, 0));
::SetBkColor(hdc, RGB(0, 255, 255));
::TextOut(hdc, 0, 20, TEXT("Hello GDI"), strlen("Hello GDI"));
::ReleaseDC(hwnd, hdc);
return 0;
}
表示按下鼠标时在坐标 (0,20)的位置绘制 Hello GDI,下面说一下 GetDC 和 BeginPaint 函数的区别
当响应鼠标点击函数的时候,DC 结构成员的设置并没有被保存下来,下一次使用GDI函数的时候设备环境仍然使用Windows 的默认值,要想让Windows每次对DC的设置保存下来,只要在注册窗口时,向 WNDCLASSEX 的结构的 style 成员添加一个 CS_OWNDC 标志就可以了。
wndClass.style = CS_HREDRAW | CS_VREDRAW | CS_OWNDC;
颜色使用宏 RGB(r, g, b) 表示
宏 GetRValue、GetGValue、
GetBValue 可以从 COLORREF 获取各分量值
使用函数 SetPixel 函数设置一个像素值
使用函数 GetPixel 获取获取一个像素值
绘制线条的函数有绘制单条直线 LineTo 、绘制多条直线 Polyline 和 PolylineTo 、画贝塞尔曲线 PolyBezier 和 PolyBezierTo 、绘制弧线 Arc 和 ArcTo
绘制直线只需要指定开始坐标,然后以直线的另一个坐标为参数调用 LineTo 函数,下面时绘制一条坐标从(0, 0)到(100,100)的直线
::MoveToEx(hdc, 0, 0, nullptr);
::LineTo(hdc, 100, 100);
DC的数据结构中有一个当前点,LineTo 函数就是从当前点绘制一条直线到参数指定点, 并把这个点设置为新的当前点。如果要设置当前点的位置可以使用函数 MoveToEx
DC 结构还有一个画笔句柄,每次绘画时,GDI 函数都会使用此句柄
设置画笔。画笔对象规定了线条的宽度、颜色和风格。
要想改变DC中默认的画笔,可以使用Windows中预定义的画笔对象,也可以创建新的画笔对象。预定义的画笔对象仅有三种
BLACK_PEN、WHITE_PEN、
NULL_PEN 分别为黑色画笔、白色画笔和空画笔。
HPEN hPen = (HPEN)::GetStockObject(BLACK_PEN);
HPEN oldPen = (HPEN)::SelectObject(hdc, hPen);
使用函数 GetStockObject 函数选择好对象句柄后,就可以使用函数 SelectObject 将对象选入DC中。
使用函数 CreatePen 函数可以创建自定义画笔对象
下面代码绘制一条直线:
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = ::BeginPaint(hwnd, &ps);
//::TextOut(hdc, 0, 0, TEXT("Hello GDI"), strlen("Hello GDI"));
HPEN nPen = ::CreatePen(PS_SOLID, 1, RGB(255, 255, 0));
HPEN nOldPen = (HPEN)::SelectObject(hdc, nPen);
::MoveToEx(hdc, 10, 10, nullptr);
::LineTo(hdc, 100, 100);
::SelectObject(hdc, nOldPen);
::DeleteObject(nPen);
::EndPaint(hwnd, &ps);
return 0;
}
绘制直线得时候使用画笔,填充区域使用画刷。绘制时,使用当前画笔绘制边线,使用当前画刷填充区域。
跟画笔一样可以使用系统默认得画刷,也可以使用自定义画刷
HBRUSH hBrush = ::CreateSolidBrush(RGB(255, 0, 0));
HBRUSH hOldBrush = (HBRUSH)::SelectObject(hdc, hBrush);
::Rectangle(hdc, 10, 10, 200, 200);
::SelectObject(hdc, hOldBrush);
::DeleteObject(hBrush);
函数 CreateSolidBrush 输入唯一得参数就是画刷得颜色。函数 CreateHatchBrush 函数创建得画刷可以指定特定风格得线条:
HBRUSH CreateHatchBrush(
int fnStyle, // 线条的风格
COLORREF clrref // 图案线条的颜色
)
可以使用 GetStockObject 函数获取一些常用的画刷对象,常用的预定义对象有 BLACK_BRUSH(黑色画刷)、 DKGRAY_BRUSH(深黑色画刷)、 GRAY_BRUSH(灰色画刷)、 LTGRAY_BRUSH(浅灰色画刷)、 WHITE_BRUSH(白色画刷)、 NULL_BRUSH(空画刷)