Qt之绘图
一、QPainter绘图系统
1.QPainter与QPaintDevice
Qt的绘图系统使用户可以在屏幕或打印上用相同的API绘图,绘图系统基于QPainter、QPaintDevice和QPaintEngine类,QPainter是用来绘图操作的类,QPaintDevice是一个可以使用QOPainter进行绘图的抽象的二维界面,QPaintEngine给QPainter提供在不同设备上绘图的接口。QPaintEngine类由QPainter和APaintDevice内部使用,应用程序一般无需和QPaintEngine打交道,除非要创建自己的设备类型。一般的绘图设备包括QWidget、QPixmap、QImage等,这些绘图设备为QPainter提供一个"画布"
2.paintEvent事件和绘图区
QWidget类及其子类是最常用的绘图设备,从QWidget类继承的类都有paintEvent()事件,要在设备上绘图,只需重定义此事件并编写响应代码。创建一个QPainter对象获取绘图设备的接口,然后就可以在绘图设备的"画布"上绘图了。
在paintEvent()事件里绘图的基本程序结构是:
1 2 3 4 5 6 7 8 | void MainWindow::paintEvent(QPaintEvent * event) { QPainter painter( this ); //创建与绘图设备关联的QPainter对象 /* painter在设备的窗口上画图 */ QWidget::paintEvent(event); } |
首先创建一个属于本绘图设备的QPainter对象painter,然后使用整个painter在绘图设备的窗口上画图。
3.QPainter绘图的主要属性
用QPainter在绘图设备上绘图,主要是绘制一些基本的图像元素,包括点、直线、圆形、矩形、曲线、文字等,控制这些绘图元素特性的主要是QPainter的3个属性。
(1).pen属性:是一个QPen对象,用于控制线条的颜色、宽度、线型等
(2).brush属性:是一个QBrush对象,用于设置一个区域的填充特性,可以设置填充颜色、填充方式、渐变特性等,还可以采用图片做材质填充。
(3).font属性:是一个QFont对象,用于绘制文字时,设置文字的字体样式、大小等属性。
使用这3个属性基本就是控制了绘图的基本特点。
示例代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 | MainWindow::MainWindow(QWidget *parent) : QWidget(parent) { this ->setPalette(Qt::white); //设置窗口为白色背景色 this ->setAutoFillBackground( true ); } MainWindow::~MainWindow() { } void MainWindow::paintEvent(QPaintEvent * event) { QPainter painter( this ); //创建与绘图设备关联的QPainter对象 painter.setRenderHint(QPainter::Antialiasing); //启用反走样,使得绘图边缘更平滑,减少锯齿状边缘 painter.setRenderHint(QPainter::TextAntialiasing); //启用文本反走样,改善文本渲染的质量 QRect rect( this ->width() / 4, this ->height() / 4, this ->width() / 2, this ->height() / 2); QPen pen; //设置画笔 pen.setWidth(3); //线宽 pen.setColor(Qt::red); //划线颜色 pen.setStyle(Qt::SolidLine); //线端点样式 pen.setCapStyle(Qt::FlatCap); //线的样式,实践、虚线等 pen.setJoinStyle(Qt::BevelJoin); //线的连接点样式 painter.setPen(pen); QBrush brush; brush.setColor(Qt::yellow); //画刷颜色 brush.setStyle(Qt::SolidPattern); //画刷填充样式 painter.setBrush(brush); painter.drawRect(rect); //绘图 QWidget::paintEvent(event); } |
效果如下:
设置号painter的pen和brush属性后,调用QPainter类的drawRect()函数就可以绘制定义的矩形了,矩形框的线条特性由pen决定,填充特性由brush决定。
二、QPen的主要功能
QPen用于绘图时对线条进行设置,主要包括线宽、颜色、线型等,下表中是QPen类的主要接口函数,通常一个设置函数都有一个对应的读取函数,例如setColor()用于设置画笔颜色,对应的读取画笔颜色的函数为color()。

三、QBrush的主要功能
QBrush定义了QPainter绘图时的填充特性,包括填充颜色、填充样式、材质填充时的材质图片等。下表是QBrush的主要函数:

setStyle(Qt::BrushStyle style)函数设置画刷的样式,参数是Qt::BrushStyle style枚举类型:

下面是使用资源文件里的一个图片进行材质填充的示例程序:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | void MainWindow::paintEvent(QPaintEvent * event) { QPainter painter( this ); QRect rect( this ->width() / 4, this ->height() / 4, this ->width() / 2, this ->height() / 2); QPen pen; //设置画笔 pen.setWidth(3); //线宽 pen.setColor(Qt::red); //画线颜色 pen.setStyle(Qt::SolidLine); //线的类型 painter.setPen(pen); QPixmap texturePixmap( ":images/testure.jpg" ); QBrush brush; //设置画刷 brush.setStyle(Qt::TexturePattern); //画刷填充样式 brush.setTexture(texturePixmap); //设置材质图片 painter.setBrush(brush); painter.drawRect(rect); //绘图 QWidget::paintEvent(event); } |
四、QPainter绘制基本图形元件
1.绘制弧线
1 2 3 4 5 6 7 8 9 10 11 12 | void MainWindow::paintEvent(QPaintEvent * event) { QPainter painter( this ); QRect rect( this ->width() / 4, this ->height() / 4, this ->width() / 2, this ->height() / 2); int startAngle = 90 * 16; //起始90° int spanAngle = 90 * 16; //旋转90° painter.drawArc(rect, startAngle, spanAngle); QWidget::paintEvent(event); } |
2.绘制一段弦
1 2 3 4 5 6 7 8 9 10 11 12 | void MainWindow::paintEvent(QPaintEvent * event) { QPainter painter( this ); QRect rect( this ->width() / 4, this ->height() / 4, this ->width() / 2, this ->height() / 2); int startAngle = 90 * 16; //起始90° int spanAngle = 90 * 16; //旋转90° painter.drawChord(rect, startAngle, spanAngle); QWidget::paintEvent(event); } |
3.根据给定的点绘制凸多边形
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QPoint points[4] = { QPoint(5*w/12, h/4), QPoint(3*w/4, 5*h/12), QPoint(5*w/12, 3*h/4), QPoint(w/4, 5*h/12) }; painter.drawConvexPolygon(points, 4); QWidget::paintEvent(event); } |
4.绘制椭圆
1 2 3 4 5 6 7 8 9 10 11 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); painter.drawEllipse(rect); QWidget::paintEvent(event); } |
5.在指定的矩形区域内绘制图片
1 2 3 4 5 6 7 8 9 10 11 12 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); QImage image( ":/Images/painter.png" ); painter.drawImage(rect, image); QWidget::paintEvent(event); } |
6.绘制直线
1 2 3 4 5 6 7 8 9 10 11 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QLine line(w/4, h/4, w/2, h/2); painter.drawLine(line); QWidget::paintEvent(event); } |
7.绘制扇形
1 2 3 4 5 6 7 8 9 10 11 12 13 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); int startAngle = 40 * 16; //起始40° int spanAngle = 120 * 16; //旋转120° painter.drawPie(rect, startAngle, spanAngle); QWidget::paintEvent(event); } |
8.绘制Pixmap图片
1 2 3 4 5 6 7 8 9 10 11 12 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); QPixmap pixmap( ":/Images/painter.png" ); painter.drawPixmap(rect, pixmap); QWidget::paintEvent(event); } |
9.绘制一个点
1 2 3 4 5 6 7 8 9 10 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); painter.drawPoint(QPoint(w/2, h/2)); QWidget::paintEvent(event); } |
10.绘制矩形
1 2 3 4 5 6 7 8 9 10 11 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); painter.drawRect(rect); QWidget::paintEvent(event); } |
11.绘制圆角矩形
1 2 3 4 5 6 7 8 9 10 11 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); painter.drawRoundedRect(rect, 20, 20); QWidget::paintEvent(event); } |
12.绘制文本,只能绘制单行文字,字体的大小等属性由QPainter::font()决定
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); QFont font; font.setPointSize(30); font.setBold( true ); painter.setFont(font); painter.drawText(rect, "Hello,Qt" ); QWidget::paintEvent(event); } |
13.填充一个矩形,无边框框线
1 2 3 4 5 6 7 8 9 10 11 | void MainWindow::paintEvent(QPaintEvent * event) { int w = this ->width(); int h = this ->height(); QPainter painter( this ); QRect rect(w/4, h/4, w/2, h/2); painter.fillRect(rect, Qt::red); QWidget::paintEvent(event); } |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 全程不用写代码,我用AI程序员写了一个飞机大战
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了