Arthur绘图系统=QPainter+QPaintDevice+QPainterEngine
QPainter:用来执行具体的绘图相关操作,如画点,画线,填充,变换,alpha通道等;
QPaintDevice是QPainter用来绘图的绘图设备,QT中有几种预定义的绘图设备,如QWidget,QPixmap,QPrinter等。它们都从QPaintDevice继承。
QPaintEngine类提供了不同类型设备的接口,QPaintEngine对程序员不透明,由QPainter,QPaintDevice类与其进行交互。
从QT4.2 开始,Graphics View框架使用了MVC模式,适合大量的2D图元的管理,在Graphics View框架中,场景存储了图像数据,它通过视图以多种形式表现,每个图元可以单独进行控制。
字体的属性可以使用QFontInfo类获取,字体的度量使用QFontMetrics类来获取,QFontDatabase类可以得到底层窗口系统的所有可用字体的信息。
通常情况下,QPainter以默认的坐标系统进行绘制,也可以使用QMatrix类对坐标进行变换;当绘制时,可以使用QPainter::RenderHint来告诉绘图引擎是否启用反锯齿功能使绘图更为平滑。
drawPicture()函数负责绘制QPicture中存储的QPainter指令,QPicture是可以记录QPainter绘图指令的类,它将QPainter的绘图指令串行化为平台无关的格式存储。使用如下:
QPicture picture;
picture.load("mypicture.pic");
QPainter painter(this);
painter.drawPicture(0,0,picture);
上面的代码片段装入绘图文件mypicture.pic,并在点(0,0)处重放绘图指令。也可以用QPicture::Play()函数来完成相同的功能。
QPen:
如果要使用自定义的线风格(Qt::CustomDashLine),则需要使用QPen的setDashPattern()函数来设置自定义风格。如:
QPen pen;
QVector
qreal blank=4;
dashes<<2<
pen.setDashPattern(customDashes);
QVector中奇数位置的数是实线的长度,偶数位置的数是空白的长度。
端点风格( cap style ):
Qt::SquareCap:方形并将端点延长至线宽的一半。
Qt::FlatCap:方形端点但没有将线延长。
Qt::RoundCap:圆形的端点。
连接风格(join style)
填充模式:
Qt::BrushStyle枚举变量包括基本模式填充、渐变填充、纹理填充。
1、渐变填充包括两个要素:颜色的变化和路径的变化。颜色变化可以指定从一种颜色渐变到另外一种颜色,也可以在变化的路径上指定一些点的颜色进行分段渐变。QT中有3种渐变填充:线性,圆形,锥形,所有类均从QGradient类继承。
线性填充例子:指定两个控制点,画刷在两个控制点之间进行颜色插值。
QLinearGradient linearGradient(0,0,200,100);
linearGradient.setColorAt(0,Qt::red);
linearGradient.setColorAt(0.5,Qt::green);
linearGradient.setColorAt(1, Qt::blue);
painter.setBrush( linearGradient );
painter.drawRect(0,0,200,100);
2、圆形渐变填充需要指定圆心,半径,焦点,画刷在焦点和圆上的所有点之间进行颜色插值。
QRadialGradient radialGradient(50,50,50,30,30);
radialGradient.setColorAt(0.2, Qt::cyan);
radialGradient.setColorAt(0.8, Qt::yellow);
radialGradient.setColorAt(1,Qt::magenta);
painter.setBrush(radialGradient);
painter.drawEllipse(0,0,100,100);
3、圆锥填充:指定圆心和开始角,画刷沿圆心逆时针对颜色进行插值。
QConicalGradient conicalGradient(60,40,30);
conicalGradient.setColorAt(0,Qt::gray);
conicalGradient.setColorAt(0.4, Qt::darkGreen);
conicalGradient.setColorAt(0.6, Qt::darkMagenta);
conicalGradient.setColorAt(1,Qt::darkBlue);
painter.setBrush(conicalGradient);
painter.drawEllipse(0,0,100,100);
关闭窗口部件的双缓冲:
myWidget->setAttribute(Qt::WA_PaintOnScreen);
在交互绘制过程中,程序将图像缓冲区复制到临时缓冲区,并在临时缓冲区上绘制,绘制完毕再将结果复制图像缓冲区。如果没有交互绘制,则直接将图像缓冲区显示到屏幕上。
QWidget类有一个属性windowOpacity,通过setWindowOpacity(qreal level)可以设置窗口的透明度。该属性和Aplha通道实现原理并不相同。
要实现自己的绘图设备,必须从QPaintDevice类继承并实现虚函数QPaintDevice::paintEngine()以告知QPainter能够在这个特定的设备上绘制图像。同时还需要从QPaintEngine类继承自定义的图像绘制引擎。
使用QImage的优点是可以获得与平台无关的绘制操作,另外一个好处是图像可以不必在GUI线程中处理。
QPixmap是后台显示的图像,它为在屏幕上显示图像提供优化。不同于QImage,pixmap的图像数据是用户不可见,而且由底层窗口系统管理。为了优化QPixmap绘图,QT提供了QPixmapCache类来存储临时的pixmap。
QT还提供了从QPixmap继承的QBitmap类,QBitmap表示单色的pixmap,主要用来创建自定义的QCursor和QBrush对象,构造QRegion对象,设置pixmap和窗口部件的掩码。
与QMatrix不同的是,QTransform支持透视变换,使用toAffine()函数可以将QTransform对象转换为QMatrix对象,但是这将丢失QTransform的透视变换数据。
绘图路径可以进行填充、显示轮廓和剪裁。要生成可填充的轮廓的绘图路径,可以使用QPainterPathStroker类。使用QPainterPath的优点是复杂图形只需创建一次,就可以多次使用。
QT提供4个处理图像的类:QImage,QPixmap,QBitmap,QPicture。
QImage:优化了I/O操作,可直接存取操作像素数据;提供与硬件无关的图像表示方法,支持的图像颜色有单色,8位,32位和Alpha混合格式。
QPixmap:主要用来在屏幕上显示图像;主要完成屏幕后台缓冲区绘图。QPixmap对象可以使用QLabel或QAbstractButton子类(QPushButton,QToolButton)显示,QLabel通过设置pixmap属性,QAbstractButton通过设置icon属性来完成。QPixmap对象还可以使用静态函数grabWidget()和grabWindow()函数创建,并绘制指定的窗口和窗口部件。
QPixmap中的像素数据是内部的,并且由底层的窗口系统进行管理,如果要存储像素,只有通过QPainter函数或将QPixmap对象转换在QImage对象,根据底层系统的不同,QPixmap可以RGB32或混合alpha格式存储。因此QPixmap是依赖底层系统的。
QBitmap:从QPixmap继承,只能表示两种颜色;
QPicture:可以记录和重放QPainter命令的类。
组合模式:用来指定如何合并源图像和一个图像。
Graphics View框架中包括三个主要的类:QGraphicScene,QGraphicsView和QGraphItem,分别是场景、视图和图元。
QGraphicsScene类实现Graphics View中的场景,场景类主要完成如下功能:
1、提供管理大量图元的快速接口;
2、传播事件给场景中的每个图元;
3、管理图元状态,如选择和焦点处理;
4、提供无变换的绘制功能,如打印。
场景是QGraphicsItem对象的容器,通过函数QGraphicsScene::addItem可以加入一个图元到场景中。图元可以过通多个函数进行检索。
QGraphicsItem具有下列功能:
1、处理鼠标按下,移动,释放,双击,悬停,滚轮和右键菜单事件;
2、处理键盘输入事件;
3、处理拖放事件;
4、分组;
5、碰撞检测;
6、图元可以包含子图元;
所有的鼠标事件最开始都是使用视图坐标。
QGraphicsItem支持图元特定的光标和工具提示。在鼠标进入图元区域时激活相应的光标和工具提示。