Windows编程,画笔画刷的介绍

画笔,可以用以下代码新建一个画笔对象:

HPEN hpen = CreatePen(PS_SOLID, 1, RGB(255,0,0));

可以看到,画笔的CreatePen()有三个参数(parameter),第一个参数表示画笔类型,第二个参数表示画笔宽度(注意以pixel为单位),第三个参数是画笔颜色。
除了上述的方法之外,还可以通过这两种方法获得画笔对象:
GetStockObject(WHITE_PEN),CreatePenIndirect(CONST LOGPEN*lplgpn)。
这三种方式的返回值都是HPEN,而他们的区别就是,Stock Pen,系统库存的pen的颜色,比如WHITE_PEN, BLACK_PEN, NULL_PEN,这些样式都可以直接从GetStockObject()函数中获得。
为了使我们要画的图形的线是我们设置好的画笔类型画出的线,就要在代码中使用SelectObject()函数,来具体调用画笔。
由于每次画笔的产生都要分配存储空间,故在使用完之后(程序结束后),使用DeleteObject()函数删除画笔对象。

那么,画笔类型有多少种呢?下面附上画笔的基本类型:

PS_DOT               //点状线
PS_DASHDOT   // 线段加点
PS_DASHDOTDOT//线段加点再加点
PS_DASH         //线段
PS_SOLID            //直线
PS_NULL           //无

想要使用不同类型的画笔,只需更改第一个参数即可

画刷,可以用以下代码新建一个画刷:

hBrush = CreateSolidBrush (crColor) ;//单色填充hBrush = CreateHatchBrush (iHatchStyle,crColor) ; //阴影填涂CreatePatternBrushCreateDIBPatternBrushPthBrush = CreateBrushIndirect(&logbrush) ; //逻辑画刷

Windows提供了五种函数用于构建 画刷对象。
当然,同画笔一样,画刷也可以用GetStockObject()函数来获得windows自身所存的画刷类型(NULL_BRUSH 等)。
而画刷的类型如下:

     //HS_VERTICAL,    /* ||||| 垂直 *///  HS_HORIZONTAL,  /* ----- 水平 *///    HS_BDIAGONAL    /* 左斜线 */// HS_FDIAGONAL    /* \\\\ 右斜线 *///    HS_CROSS,       /* +++++ 正十字 *///  HS_DIAGCROSS    /* xxxxx 斜十字 */

同样,为了使我们要画的图形的用上我们所设置的画刷类型,就要在代码中使用SelectObject()函数,来具体调用画刷。
由于每次画刷的产生都要分配存储空间,故在使用完之后(程序结束后),使用DeleteObject()函数删除画刷对象。

初步了解画笔和画刷后,让我们开始尝试绘制几何图形

几何图形的绘制

首先我们得明确在windows中提供的绘制几何图形的各类函数:

直角矩形:Rectangle()
具体:
WINGDIAPI BOOL WINAPI Rectangle(In HDC hdc, In int left, In int top, In int right, In int bottom);

椭圆 :Ellipse ()
具体:
WINGDIAPI BOOL WINAPI Ellipse( In HDC hdc, In int left, In int top, In int right, In int bottom);

圆角矩形:RoundRect()
具体:
WINGDIAPI BOOL WINAPI RoundRect(In HDC hdc, In int left, In int top, In int right, In int bottom, In int width, In int height);

椭圆周上的弧,两端以弦连接:Chord ()
具体:
WINGDIAPI BOOL WINAPI Chord( In HDC hdc, In int x1, In int y1, In int x2, In int y2, In int x3, In int y3, In int x4, In int y4);

椭圆上的饼图:Pie ()
具体:
WINGDIAPI BOOL WINAPI Pie(In HDC hdc, In int left, In int top, In int right, In int bottom, In int xr1, In int yr1, In int xr2, In int yr2);

多边形:Polygon ()
具体:
WINGDIAPI BOOL WINAPI Polygon(In HDC hdc, In_reads(cpt) CONST POINT *apt, In int cpt);

多个多边形:PolyPolygon()
具体:
WINGDIAPI BOOL WINAPI PolyPolygon(In HDC hdc, In CONST POINT *apt, In_reads(csz) CONST INT *asz, In int csz);

便于更好的理解和运用,我会逐个分析各个几何图形函数中参数的意义。
Rectangle()
它有5个参数,第一个参数(剩下的各个函数的第一个参数也都相同)是指设备描述表句柄,即在WM_PAINT中定义的一个HDC类的句柄,为了使函数能正常作用,必须将设备描述表句柄信息提供给函数。,这个函数剩余的四个参数的功能非常简单,就如定义所简写,表示两个点,矩形的左上角端点的横纵坐标和矩形的右下角端点的横纵坐标。

Ellipse()
几乎和矩形一样,注意,windows中的构建椭圆(圆形),是通过先建立矩形确定范围,再画出椭圆,所以后四个参数也是先构建的矩形的左上角端点坐标和右下角端点坐标。

RoundRect()
圆角矩形,比起普通的矩形函数多了最后两个参数,这两个参数也是 int类型,具体功能是改变圆角矩形圆角的弯曲程度,数值设置的较高,则弯曲程度越强。

Pie(),
饼图,它有八个int类型的参数,前四个也是表示先构建的矩形左上角端点和右下角端点。后四个,注意,是由圆心衍生的两条半径的端点的坐标。或者说是坐标点 与 圆心 相连的线,在运行后会保留线在圆内的部分,从而实现饼图。

Polygon()
其中,第二个参数 是一个 POINT 结构的数组,第三个参数 是点的个数。如果数组中最后一个点与第一个点不同,则 Windows 会再加一条线连接最后一个点与第一个点。(在 Polyline 函数中不会这么做。)

PolyPolygon()
最后一个参数是绘制的多边形的个数。对每个多边形,第二个参数数值给出了多边形顶点的个数。数组中含有全部多边形的所有顶点。

了解上述基础知识后,以下是一个使用visual studio 2017 编写的 实现 基本几何图形绘制 和 画笔画刷类型应用的程序;

//WindowsProject3.cpp: 定义应用程序的入口点。
//#include "stdafx.h"
#include "WindowsProject3.h"#define MAX_LOADSTRING 100// 全局变量:
HINSTANCE hInst;                                // 当前实例
WCHAR szTitle[MAX_LOADSTRING] = TEXT("2_1");                  // 标题栏文本
WCHAR szWindowClass[MAX_LOADSTRING];            // 主窗口类名// 此代码模块中包含的函数的前向声明:
ATOM                MyRegisterClass(HINSTANCE hInstance);
BOOL                InitInstance(HINSTANCE, int);
LRESULT CALLBACK    WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK    About(HWND, UINT, WPARAM, LPARAM);int APIENTRY wWinMain(_In_ HINSTANCE hInstance,_In_opt_ HINSTANCE hPrevInstance,_In_ LPWSTR    lpCmdLine,_In_ int       nCmdShow)
{UNREFERENCED_PARAMETER(hPrevInstance);UNREFERENCED_PARAMETER(lpCmdLine);// TODO: 在此放置代码。// 初始化全局字符串//LoadStringW(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);LoadStringW(hInstance, IDC_WINDOWSPROJECT3, szWindowClass, MAX_LOADSTRING);MyRegisterClass(hInstance);// 执行应用程序初始化: if (!InitInstance (hInstance, nCmdShow)){return FALSE;}HACCEL hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_WINDOWSPROJECT3));MSG msg;// 主消息循环: while (GetMessage(&msg, nullptr, 0, 0)){if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg)){TranslateMessage(&msg);DispatchMessage(&msg);}}return (int) msg.wParam;
}//
//  函数: MyRegisterClass()
//
//  目的: 注册窗口类。
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{WNDCLASSEXW wcex;wcex.cbSize = sizeof(WNDCLASSEX);wcex.style          = CS_HREDRAW | CS_VREDRAW;wcex.lpfnWndProc    = WndProc;wcex.cbClsExtra     = 0;wcex.cbWndExtra     = 0;wcex.hInstance      = hInstance;wcex.hIcon          = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_WINDOWSPROJECT3));wcex.hCursor        = LoadCursor(nullptr, IDC_ARROW);wcex.hbrBackground  = (HBRUSH)(COLOR_WINDOW+1);wcex.lpszMenuName   = MAKEINTRESOURCEW(IDC_WINDOWSPROJECT3);wcex.lpszClassName  = szWindowClass;wcex.hIconSm        = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));return RegisterClassExW(&wcex);
}//
//   函数: InitInstance(HINSTANCE, int)
//
//   目的: 保存实例句柄并创建主窗口
//
//   注释:
//
//        在此函数中,我们在全局变量中保存实例句柄并
//        创建和显示主程序窗口。
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{hInst = hInstance; // 将实例句柄存储在全局变量中HWND hWnd = CreateWindowW(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, nullptr, nullptr, hInstance, nullptr);if (!hWnd){return FALSE;}ShowWindow(hWnd, nCmdShow);UpdateWindow(hWnd);return TRUE;
}//
//  函数: WndProc(HWND, UINT, WPARAM, LPARAM)
//
//  目的:    处理主窗口的消息。
//
//  WM_COMMAND  - 处理应用程序菜单
//  WM_PAINT    - 绘制主窗口
//  WM_DESTROY  - 发送退出消息并返回
//
//
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{switch (message){/* case WM_COMMAND:{int wmId = LOWORD(wParam);// 分析菜单选择: switch (wmId){case IDM_ABOUT:DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);break;case IDM_EXIT:DestroyWindow(hWnd);break;default:return DefWindowProc(hWnd, message, wParam, lParam);}}break;*/case WM_PAINT:{//hBru[i] = CreateHatchBrush(sBru[i], RGB(255, 0, 0))HBRUSH hBrush;//添加画刷//HBRUSH hBrush2;//添加画刷HPEN  hPen;static HPEN hPen2;PAINTSTRUCT ps;HDC hdc = BeginPaint(hWnd, &ps);// TODO: 在此处添加使用 hdc 的任何绘图代码...//hBrush2 = (HBRUSH)GetStockObject(NULL_BRUSH);//空心,画刷取空//SelectObject(hdc, hBrush2);hPen = CreatePen(PS_DASH, 1, RGB(255, 0, 0));//redSelectObject(hdc, hPen);//SelectObject(hdc, hBrush);Ellipse(hdc, 0, 150,150,0);hPen = CreatePen(PS_DASHDOT, 1, RGB(0, 255, 0));//greenSelectObject(hdc, hPen);hBrush = (HBRUSH)GetStockObject(NULL_BRUSH);//空心,画刷取空SelectObject(hdc, hBrush);Ellipse(hdc, 50, 0, 200, 150);hPen = CreatePen(PS_DOT, 1, RGB(0, 255, 255));//blueSelectObject(hdc, hPen);//hBrush = (HBRUSH)GetStockObject(NULL_BRUSH);//空心,画刷取空//SelectObject(hdc, hBrush);Ellipse(hdc, 50, 50, 200, 200);hPen = CreatePen(PS_DASHDOTDOT, 1, RGB(0, 0, 255));// blueSelectObject(hdc, hPen);Ellipse(hdc, 0, 50, 150, 200);////以上圆圈绘制完毕////开始饼图绘制//////hBrush = CreateHatchBrush(HS_VERTICAL, RGB(255, 255, 255));hPen2 = CreatePen(PS_SOLID, 1, RGB(0, 0, 0));//redSelectObject(hdc, hPen2);hBrush = CreateSolidBrush(RGB(0, 255, 255));//设置画刷,纯色填充 蓝SelectObject(hdc, hBrush);Pie(hdc, 50, 300, 250, 500, 100, 300, 80, 500);hBrush = CreateSolidBrush(RGB(255, 0, 0)); //红SelectObject(hdc, hBrush);Pie(hdc, 50, 300, 250, 500, 80, 500, 250, 400);hBrush = CreateSolidBrush(RGB(255, 255, 0));//SelectObject(hdc, hBrush);Pie(hdc, 50, 300, 250, 500, 250, 400, 100, 300);//以上饼图的绘制结束////////开始绘制正方形//下排正方形的绘制//////hPen2 = CreatePen(PS_SOLID, 1, RGB(0, 0, 0));//redSelectObject(hdc, hPen2);//第一排圆角正方形////hBrush = CreateSolidBrush(RGB(0, 0, 0));//1SelectObject(hdc, hBrush);RoundRect(hdc, 600, 0, 700, 100, 30, 30);hBrush = CreateSolidBrush(RGB(50, 50, 50));//2SelectObject(hdc, hBrush);RoundRect(hdc, 700, 0, 800, 100, 30, 30);hBrush = CreateSolidBrush(RGB(130, 130, 130));//3SelectObject(hdc, hBrush);RoundRect(hdc, 800, 0, 900, 100, 30, 30);hBrush = CreateSolidBrush(RGB(255, 255, 255));//4SelectObject(hdc, hBrush);RoundRect(hdc, 600, 100, 700, 200, 30, 30);hBrush = CreateSolidBrush(RGB(180, 180, 180));//5SelectObject(hdc, hBrush);RoundRect(hdc, 700, 100, 800, 200, 30, 30);hBrush = CreateSolidBrush(RGB(255, 255, 255));//6SelectObject(hdc, hBrush);RoundRect(hdc, 800, 100, 900, 200, 30, 30);Pie();Rectangle();Ellipse();Chord();RoundRect();Polygon();PolyPolygon();//HS_VERTICAL,    /* ||||| 垂直 *///  HS_HORIZONTAL,  /* ----- 水平 *///    HS_BDIAGONAL    /* 左斜线 */// HS_FDIAGONAL    /* \\\\ 右斜线 *///    HS_CROSS,       /* +++++ 正十字 *///  HS_DIAGCROSS    /* xxxxx 斜十字 *///hBrush = CreateHatchBrush(HS_VERTICAL, RGB(220, 220, 220));//黄//SelectObject(hdc, hBrush);////第二排正方形//hBrush = CreateHatchBrush(HS_BDIAGONAL, RGB(200, 200, 200));//1SelectObject(hdc, hBrush);Rectangle(hdc, 600, 200, 700, 300);hBrush = CreateHatchBrush(HS_DIAGCROSS, RGB(200, 200, 200));//2SelectObject(hdc, hBrush);Rectangle(hdc, 700, 200, 800, 300);hBrush = CreateHatchBrush(HS_FDIAGONAL, RGB(200, 200, 200));//3SelectObject(hdc, hBrush);Rectangle(hdc, 800, 200, 900, 300);//hBrush = CreateHatchBrush(HS_CROSS, RGB(200, 200, 200));//4SelectObject(hdc, hBrush);Rectangle(hdc, 600, 300, 700, 400);hBrush = CreateHatchBrush(HS_HORIZONTAL, RGB(200, 200, 200));//5SelectObject(hdc, hBrush);Rectangle(hdc, 700, 300, 800, 400);hBrush = CreateHatchBrush(HS_VERTICAL, RGB(200, 200, 200));//6SelectObject(hdc, hBrush);Rectangle(hdc, 800, 300, 900, 400);//最后delete 画刷EndPaint(hWnd, &ps);}break;case WM_DESTROY:PostQuitMessage(0);break;default:return DefWindowProc(hWnd, message, wParam, lParam);}return 0;
}// “关于”框的消息处理程序。
/*
INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{UNREFERENCED_PARAMETER(lParam);switch (message){case WM_INITDIALOG:return (INT_PTR)TRUE;case WM_COMMAND:if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL){EndDialog(hDlg, LOWORD(wParam));return (INT_PTR)TRUE;}break;}return (INT_PTR)FALSE;
}*/

该程序我保留了部分默认初始化好的代码,运行结果如下图所示;

Windows 编程,画笔画刷以及几何图形的绘制相关推荐

  1. windows核心编程--2、windows的画笔画刷以及一些简单的应用

    一.前言     该系列前几篇:      windows核心编程–1.使用vs2019编写第一个win32项目 二.相关工具     IDE:vs2019     其他格式图片转ico脚本(贴在文末 ...

  2. Windows编程画太极图

    用Windows API 画太极图 重要的API函数 Ellipse() : 画椭圆 API原型  BOOL Ellipse(       HDC hdc,       int xLeft,     ...

  3. C#图形教程画笔画刷等

    C#图形编程 C#提供了一整套相当丰富的类库.方法以及事件以供开发者使用.C#还引入了GDI+,它是由GDI演变而来的,具有比GDI更强大的功能而且简化了程序员的编程工作.所以开发者运用这些,就可以很 ...

  4. MFC初学笔记之画线画笔画刷

    学习了WINdows程序的框架之后本来是要弄opengl的,后来想想还要在opengl上面添加按钮label什么的与用户交换,后来有考虑学了QT,感觉封装的太....又在学MFC,个人感觉用MFC 比 ...

  5. Qpointer画笔画刷等详细介绍

    以下内容转载自豆子老师博客. 多些大家对我的支持啊!有朋友也提出,前面的几节有关event的教程缺少例子.因为event比较难做例子,也就没有去写,只是把大概写了一下.今天带来的是新的部分,有关Qt的 ...

  6. QT基础之一文介绍QPainter绘制基础图形(画笔画刷设置,填充铺展渐变效果)

    更多参见 QT基础与实例应用目录 代码链接 GitHub链接 :QPainterSimpleExample 介绍 结合实例介绍如何利用QPainter绘制各种图形,可绘制不同形状,使用不同画笔颜色.画 ...

  7. Qt:QPainter重写mainwindows绘图事件绘制直线,弧线、设置画笔画刷

    //光标定位到QPainter类名上,然后按下键盘上的F1按键,这时会自动跳转到该类的帮助页面 1.新建Qt Gui应用,名为MainWindow,基类为QMainWindow. 2.修改mainwi ...

  8. Qt——多种风格的画笔画刷

    widget.h: widget.cpp:

  9. GUI编程基础学习(四)——常见几何图形的绘制

    绘制直线 在Java中可以使用以下方法绘画一条直线 drawLine(int x1,int y1,int x2,int y2); 其中参数(x1,y1)是直线的起点,(x2,y2)是直线的终点 绘制矩 ...

最新文章

  1. 华为提出十大数学挑战!解出一个就是年薪百万!
  2. 2!=5 or 0在python中是否正确-python 中 and or
  3. POJ 2299 Ultra-QuickSort(树状数组+离散化)
  4. jquery操作滚动条滚动到指定位置
  5. 监管码服务器维修,云风的 BLOG
  6. 【优化运行】基于matlab多目标粒子群算法求解冷热电联供综合能源系统运行优化问题【含Matlab源码 1747期】
  7. 大数据分析中的四大数据类型
  8. python语言的多行注释以什么开头_python实现多行注释的方法
  9. java小项目之简单聊天室
  10. 如何提升邮箱邮件安全性,邮箱管理制度有哪些?
  11. 17年社交网络老司机解读网红现象
  12. 数学建模国赛题型和获奖策略
  13. Unity动态天空shader实现
  14. uni-app开发app之一uni-app优缺点
  15. 51单片机 ADC0832酒精传感器
  16. 视频加密中令人头疼的录屏行为怎么防范?
  17. 你今天好帅用计算机,华师表白墙 | 计算机系最帅的男孩子,我喜欢你!
  18. Atitit 华为管理者内训书系 以奋斗者为本 华为公司人力资源管理纲要 attilax读后感...
  19. python解压多层压缩包,兼容tar.gz .tgz .zip .7z .gz
  20. 情人节礼物推荐,送给男朋友的情人节礼物

热门文章

  1. python 面试题目嗯哼
  2. 从Google Chrome 浏览器崩溃到“在树上吊死”
  3. 麒麟980和骁龙870的区别 哪个好
  4. 未来我们的付费网络人生去向
  5. Mybatis分页插件PageHelper失效
  6. elasticsearch实战三部曲之一:索引操作
  7. ftp/nfs卸载自定义文件系统数据
  8. 要如何搭配华硕路由器的WiFi使用时间机器(Time Machine)备份Macintosh设备?
  9. js时间YYYY-MM-DD转换为英文显示,其他日期处理函数
  10. Quratus II TimeQuest timing Analyzer 中网表模型设置分析介绍