Qt示例 | 基本图型的绘制(二)
示例运行效果:
文件目录:
具体实现:
RenderArea类:
RenderArea类继承了QWidget,并使用QPainter渲染当前活动形状的多个副本。
首先,定义了一个公共的Shape枚举来保存小部件可以呈现的不同形状(即可以通过QPainter呈现的形状)。
然后重新实现构造函数以及QWidget的两个公共函数:minimumSizeHint()和sizeHint()。
还重新实现了QWidget::paintEvent()函数,以便能够根据指定的参数绘制当前活动的形状。
声明了几个私有的槽函数:setShape()改变RenderArea的形状;setPen()和setBrush()修改小部件的钢笔和画笔,setAntialiased()和setTransformed()修改小部件各自的属性。
构造函数:
- 构造函数主要进行初始化小部件的一些变量。
- 初始化它的形状为Polygon,它的抗锯齿属性设置为false,并将图像加载到小部件的pixmap变量中。最后,设置小部件的背景颜色,从小部件的调色板定义画笔,该画笔将用于呈现背景为白色。
minimumSizeHint函数:
- RenderArea继承了QWidget的minimumSizeHint属性,保存了小部件的建议最小大小。如果此属性的值为无效大小,则不建议设置大小。
- 如果小部件没有布局,QWidget::minimumSizeHint()的默认实现将返回无效的大小,否则将返回布局的最小大小。
- 函数的重新实现将返回一个宽度为100像素、高度为100像素的QSize。
sizeHint函数:
- RenderArea继承了QWidget的sizeHint属性,保存了小部件的推荐大小。如果此属性的值为无效大小,则不建议设置大小。
- 如果小部件没有布局,QWidget::sizeHint()函数的默认实现将返回无效的大小,否则将返回布局的首选大小。
- 函数的重新实现将返回一个宽度为400像素、高度为200像素的QSize。
设置形状、画笔、笔刷函数:
setShape(), setPen()和setBrush()槽函数在每当想要修改RenderArea部件的形状,钢笔或笔刷时进行调用。根据槽参数设置形状,钢笔或画笔,并调用QWidget::update()使改变后的图形在RenderArea小部件中可见。
注: QWidget::update()不会导致立即重绘;而是当Qt返回到主事件循环时,才会进行一个paint事件处理。
RenderArea类:
设置属性函数:
使用setAntialiased()和setTransformed()槽函数,可以根据槽函数的参数改变属性的状态,并调用QWidget::update()槽函数,让改变后的属性在RenderArea小部件中可见。
paintEvent函数:
重新实现QWidget::paintEvent()函数。要做的第一件事是创建图形对象,通过paintEvent函数将绘制各种形状。
- 首先创建了一个4个qpoint的矢量。使用这个矢量来渲染点、折线和多边形形状。然后创建了一个QRect,在平面中定义一个矩形,使用它作为所有形状的边界矩形,不包括Path和Pixmap。
- 还创建了一个QPainterPath。QPainterPath类为绘制操作提供了一个容器,使图形形状能够被构造和重用。QPainterPath是由许多图形构建块组成的对象,如矩形、椭圆、直线和曲线。在这个例子中,创建了一个由一条直线和贝塞尔曲线组成的绘制路径。
- 还定义了一个起始角和一个弧长,将在绘制arc, Chord和Pie形状时使用。
为RenderArea小部件创建一个QPainter,并根据RenderArea的钢笔和笔刷设置画家的钢笔和笔刷。如果抗锯齿参数选项被选中,设置QPainter的渲染提示。
- 渲染RenderArea的形状的多个副本。副本的数量取决于RenderArea小部件的大小,这里使用了两个for循环和小部件的高度和宽度来计算它们的位置。
- 对于每个副本,首先保存当前的画家状态(将状态压入堆栈)。然后使用QPainter::translate()函数将坐标系统转换到由for循环变量决定的位置。如果省略了坐标系统的转换,所有形状的副本将会在RenderArea小部件的左上角相互叠加呈现。
- 如果选中了transforms参数选项,那么在使用QPainter::rotate()函数将坐标系顺时针旋转60度并使用QPainter::scale()函数将其缩小之前,要将对坐标系进行额外的转换。最后,将坐标系平移回旋转和缩放之前的位置。
- 当渲染这个形状时,它看起来就像在三维空间中旋转一样。
- 确定RenderArea的形状,并使用相关的QPainter绘图功能渲染它。
- 在开始渲染之前,保存了当前的绘制器状态(将状态压入堆栈)。这样做的基本原理是,计算每个形状副本相对于坐标系统中的同一点的位置。当转换坐标系时,除非在开始转换过程前保存当前的绘制状态,否则会失去这一点的知识。
- 然后,完成渲染形状的副本时,可以使用QPainter::restore()函数,用它的相关坐标系统恢复原始的画家状态。通过这种方式,确保了下一个形状副本将被渲染在正确的位置。
- 可以使用QPainter::translate()将坐标系统转换回来,而不是保存painter状态。但是,由于除了平移坐标系(当选中Transformation参数选项时)还旋转和缩放坐标系,最简单的解决方案是保存当前的画家状态。
一点感想:
在实现绘图时,一定要充分利用提供的一些现有的方法。
- 点赞
- 收藏
- 关注作者
评论(0)