Qt开发技术:QtSVG介绍、使用和Demo

简介: Qt开发技术:QtSVG介绍、使用和Demo

Qt开发专栏:开发技术(点击传送门)

 

前话

     红胖子,来也!

     Qt的SVG介绍、基本使用和Demo演示。

 

Demo

Demo1:QSvgGenerator

     保存后的SVG文件为:

Demo2:QSvgRenderer

Demo3:QSvgWidget

 

Qt SVG

可缩放矢量图形(SVG)是一种基于XML的二维矢量图形描述语言。Qt提供了用于在小部件和其他绘制设备中呈现和显示SVG图形的类。

概述

Qt SVG提供了用于呈现SVG文件的类。要包含模块类的定义,请使用以下指令:

#include <QtSvg>

要链接到模块,请将此行添加到qmake.pro文件中:

QT += svg

许可证和属性

Qt SVG在Qt公司的商业许可下可用。此外,它还可以在GNU Lesser General Public License(第3版)或GNU General Public License(第2版)下使用。有关更多详细信息,请参阅Qt许可。

     此外,Qt SVG在以下许可证下包含第三方代码。

XSVG许可

 

渲染SVG文件

概述

可缩放矢量图形(SVG)是一种用XML描述二维图形和图形应用的语言。

SVG 1.1是W3C的推荐标准,它构成了Qt中当前SVG开发的核心。

SVG 1.2是SVG工作组目前正在开发的规范,它以草稿的形式提供。移动SVG配置文件(SVG Basic和SVG Tiny)针对资源有限的设备,是第三代移动电话3GPP平台的一部分。您可以在about SVG上阅读有关SVG的更多信息。

Qt支持SVG 1.2tiny的静态特性。目前不支持ECMA脚本和DOM操作。

SVG图形可以呈现到任何QPaintDevice子类上。这种方法使开发人员能够灵活地进行测试,以便为每个应用程序找到最佳解决方案。

呈现SVG文件的最简单方法是构造一个QSvgWidget并使用QSvgWidget::load()函数之一加载一个SVG文件。

QSvgRenderer是负责为QSvgWidget呈现SVG文件的类,它可以直接用于为自定义小部件提供SVG支持。若要加载SVG文件,请使用文件名或文件内容构造一个QSvgRenderer,或在现有渲染器上调用QSvgRenderer::load()。如果成功加载SVG文件,QSvgRenderer::isValid()将返回true。

成功加载SVG文件后,可以使用QSvgRenderer::render()函数呈现它。注意,此方案允许您在Qt支持的所有绘画设备上呈现SVG文件,包括QWidget、QGLWidget和QImage。

Qt SVG相关类

可缩放矢量图形(SVG)是一种基于XML的二维矢量图形描述语言。Qt提供了用于在小部件和其他绘制设备中呈现和显示SVG图形的类。

序号

描述

1

QGraphicsSvgItem

QGraphicsItem,可用于呈现SVG文件的内容,可以细化拆分Svg的元素

2

QSvgGenerator

用于创建SVG图形的绘制设备,主要用于保存的时候使用,注意保存到时候直接使用局部变量即可,使用全局变量其没有析构反倒不会保存

3

QSvgRenderer

用于将SVG文件的内容绘制到绘图设备上,其是打开svg将其渲染到QPixmap等上面

4

QSvgWidget

用于显示可缩放矢量图形(SVG)文件内容的小部件,直接加载svg文件,即可显示

 

QGraphicsSvgItem

概述

QGraphicsSvgItem类是一个QGraphicsItem,可用于呈现SVG文件的内容。

QGraphicsSvgItem提供了一种在QGraphicsView上呈现SVG文件的方法。QGraphicsSvgItem可以通过将要呈现的SVG文件传递给其构造函数或通过在其上显式设置共享的QSvgRenderer来创建。

请注意,在QGraphicsSvgItem上设置QSvgRenderer不会使项获得呈现器的所有权,因此,如果使用setSharedRenderer()方法,则必须确保QSvgRenderer对象的生存期至少与QGraphicsSvgItem的生存期相同。

QGraphicsSvgItem提供了一种通过setElementId只呈现部分SVG文件的方法。如果调用setElementId()方法,则只有具有传递的id的SVG元素(及其子元素)将是呈现器。这为有选择地呈现包含许多离散元素的大型SVG文件提供了一种方便的方法。例如,以下代码仅呈现包含整个卡片组的SVG文件中的小丑:

QSvgRenderer *renderer = new QSvgRenderer(QLatin1String("SvgCardDeck.svg"));
QGraphicsSvgItem *black = new QGraphicsSvgItem();
QGraphicsSvgItem *red = new QGraphicsSvgItem();
black->setSharedRenderer(renderer);
black->setElementId(QLatin1String("black_joker"));
red->setSharedRenderer(renderer);
red->setElementId(QLatin1String("red_joker"));

项目的大小可以通过直接操作项目转换矩阵来设置。

默认情况下,使用QGraphicsItem::DeviceCoordinateCache模式缓存SVG呈现,以加快项目的显示速度。通过将QGraphicsItem::NoCache传递给QGraphicsItem::setCacheMode()方法,可以禁用缓存。

 

QSvgGenerator

概述

QSvgGenerator类提供了一个用于创建SVG图形的绘制设备。

此绘制设备表示可缩放矢量图形(SVG)绘图。像QPrinter一样,它被设计成一个只写的设备,生成特定格式的输出。

要编写SVG文件,首先需要通过设置文件名或outputDevice属性来配置输出。通常需要通过设置“大小”特性来指定图形的大小,在某些情况下,如果图形将包含在另一个图形中,则还需要设置“viewBox”特性。

QSvgGenerator generator;
generator.setFileName(path);
generator.setSize(QSize(200, 200));
generator.setViewBox(QRect(0, 0, 200, 200));
generator.setTitle(tr("SVG Generator Example Drawing"));
generator.setDescription(tr("An SVG drawing created by the SVG Generator "
                       "Example provided with Qt."));

其他元数据可以通过设置标题、描述和分辨率属性来指定。

与其他QPaintDevice子类一样,QPainter对象用于绘制此类的实例:

// 无需在paintEvent函数中
QPainter painter;
painter.begin(&generator);
// 此处绘制的内容就是保存为svg文件的内容
...
painter.end();

绘制方式与其他绘制设备相同。但是,必须使用QPainter::begin()和end()在设备上显式地开始和结束绘制。

测试Demo1

void SVGShow3Widget::on_pushButton_saveAs_clicked()
{
    QString filePath = QFileDialog::getSaveFileName(0, "打开文件", ".", "SVG(*.svg)");
    if(filePath.isEmpty())
    {
        return;
    }
    QSvgGenerator svgGenerator;
    svgGenerator.setFileName(filePath);
    svgGenerator.setSize(QSize(rect().width(), rect().height()));
    svgGenerator.setViewBox(rect());
    svgGenerator.setTitle("测试QSvgGenerator");
    svgGenerator.setDescription("另存为绘制测试");
    QPainter painter;
    painter.begin(&svgGenerator);
    painter.setPen(Qt::red);
    painter.drawPixmap(rect(), _pixmapSvg);
    painter.drawText(rect(), "红胖子测试Svg");
    painter.end();
}

 

QSvgRenderer

概述

QSvgRenderer类用于将SVG文件的内容绘制到绘制设备上。

使用QSvgRenderer,可缩放矢量图形(SVG)可以呈现到任何QPaintDevice子类上,包括QWidget、QImage和QGLWidget。

QSvgRenderer提供了一个API,它支持SVG呈现的基本特性,比如加载和呈现静态图形,以及更多的交互特性,比如动画。由于渲染是使用QPainter执行的,因此可以在QPaintDevice的任何子类上渲染SVG图形。

SVG图形可以在构造QSvgRenderer时加载,也可以稍后使用load()函数加载。数据可以直接作为序列化XML提供,也可以间接使用文件名提供。如果加载了有效的文件,则无论是在构造呈现器时还是以后某个时间,isValid()都将返回true;否则将返回false。QSvgRenderer提供render()插槽,用于使用给定的绘制器渲染当前文档或动画文档的当前帧。

函数的作用是:提供有关呈现当前加载的SVG文件所需的空间量的信息。这对于绘制设备(如QWidget)非常有用,这些设备通常需要向其父布局提供大小提示。图形的默认大小可能与其使用viewBox特性找到的可见区域不同。

支持动画SVG图形,可以通过简单的函数和属性集合进行控制:

  • animated()函数:指示图形是否包含动画信息;
  • framesPerSecond属性:包含播放动画的速率;

最后,QSvgRenderer类提供repainNeeded()信号,该信号在文档呈现需要更新时发出。

测试Demo2

SVGShow2Widget.h

#ifndef SVGSHOW2WIDGET_H
#define SVGSHOW2WIDGET_H
#include <QWidget>
#include <QSvgRenderer>
namespace Ui {
class SVGShow2Widget;
}
class SVGShow2Widget : public QWidget
{
    Q_OBJECT
public:
    explicit SVGShow2Widget(QWidget *parent = 0);
    ~SVGShow2Widget();
protected:
    void paintEvent(QPaintEvent *event);
private slots:
    void on_pushButton_openFile_clicked();
    void on_pushButton_load_clicked();
private:
    Ui::SVGShow2Widget *ui;
    QPixmap _pixmap;
    QPixmap _pixmapSvg;
    QSvgRenderer *_pSvgRenderer;
};
#endif // SVGSHOW2WIDGET_H
SVGShow2Widget.cpp
#include "SVGShow2Widget.h"
#include "ui_SVGShow2Widget.h"
#include <QFileDialog>
#include <QPainter>
#include <QDebug>
SVGShow2Widget::SVGShow2Widget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::SVGShow2Widget),
    _pSvgRenderer(0)
{
    ui->setupUi(this);
    QString version = "v1.0.0";
    setWindowTitle(QString("使用QSvgRenderer加载svgDemo %1 (作者:红模仿(红胖子) QQ:21497936 博客地址: blog.csdn.net/qq21497936").arg(version));
    _pixmap.load(":/images/1.png");
    _pSvgRenderer = new QSvgRenderer(this);
    _pSvgRenderer->load(QString(":/images/2.svg"));
}
SVGShow2Widget::~SVGShow2Widget()
{
    delete ui;
}
void SVGShow2Widget::paintEvent(QPaintEvent *event)
{
    QPainter painter(this);
    painter.drawPixmap(ui->label_png->geometry(), _pixmap);
    _pixmapSvg = QPixmap(ui->label_svg->width(), ui->label_svg->height());
    _pixmapSvg.fill(Qt::white);
    QPainter painter2(&_pixmapSvg);
    _pSvgRenderer->render(&painter2, _pixmapSvg.rect());
    painter.drawPixmap(ui->label_svg->geometry(), _pixmapSvg);
}
void SVGShow2Widget::on_pushButton_openFile_clicked()
{
    QString filePath = QFileDialog::getOpenFileName(0, "打开文件", ".", "SVG(*.svg)");
    if(filePath.isEmpty())
    {
        return;
    }
    ui->lineEdit_path->setText(filePath);
}
void SVGShow2Widget::on_pushButton_load_clicked()
{
    _pSvgRenderer->load(ui->lineEdit_path->text());
    update();
}

 

QSvgWidget

概述

     QSvgWidget类提供了一个小部件,用于显示可缩放矢量图形(SVG)文件的内容。

这个类使开发人员能够将SVG图形与标准小部件一起显示,并且使用的方式与QLabel用于显示文本和位图图像的方式基本相同。

由于QSvgWidget是QWidget的一个子类,SVG图形是使用显示的属性呈现的。使用QSvgRenderer类可以对渲染过程进行更多的控制,因为这可以用于在其他绘制设备(如QImage和QGLWidget)上绘制。小部件使用的渲染器可以通过renderer()函数获得。

每个QSvgWidget都可以用SVG文件的文件名构造,也可以在没有要呈现的特定文件的情况下构造,并且可以在以后提供一个。load()函数提供了两种加载SVG文件的不同方法:它们接受SVG文件的文件名或包含SVG文件的序列化XML表示形式的QByteArray。

默认情况下,小部件提供大小提示以反映其显示的图形的大小。如果没有加载数据,小部件将提供默认的QWidget大小提示。如果需要自定义此行为,请子类化此类并重新实现sizeHint()。

测试Demo3

MySvgWidget.h

#ifndef MYSVGWIDGET_H
#define MYSVGWIDGET_H
#include <QWidget>
#include <QSvgWidget>
#include <QSvgRenderer>
namespace Ui {
class MySvgWidget;
}
class MySvgWidget : public QWidget
{
    Q_OBJECT
public:
    explicit MySvgWidget(QWidget *parent = 0);
    ~MySvgWidget();
public:
    void load(const QString &file);
protected:
    void resizeEvent(QResizeEvent *event);
private:
    Ui::MySvgWidget *ui;
private:
    QString _filePath;
    QSvgWidget *_pSvgWidget;
    QSvgRenderer *_pSvgRenderer;
};
#endif // MYSVGWIDGET_H

MySvgWidget.cpp

#include "MySvgWidget.h"
#include "ui_MySvgWidget.h"
#include <QDebug>
MySvgWidget::MySvgWidget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::MySvgWidget),
    _pSvgWidget(0),
    _pSvgRenderer(0)
{
    ui->setupUi(this);
    _pSvgWidget = new QSvgWidget(this);
    _pSvgRenderer = _pSvgWidget->renderer();
}
MySvgWidget::~MySvgWidget()
{
    delete ui;
}
void MySvgWidget::load(const QString &file)
{
    _filePath = file;
    _pSvgWidget->load(_filePath);
    _pSvgWidget->repaint();
    update();
}
void MySvgWidget::resizeEvent(QResizeEvent *event)
{
    if(_pSvgWidget)
    {
        _pSvgWidget->setGeometry(rect());
    }
}

 

工程模板v1.0.0

     工程模板v1.0.0:3个demo子工程打包

 

下载工程模板

CSDNhttps://download.csdn.net/download/qq21497936/12328539

QQ群:1047134658(点击“文件”搜索“qtSVGDemo”,群内与博文同步更新所有可开源的源码模板)


相关文章
|
17天前
|
编解码 UED
Qt侧边栏的动态切换:隐藏与显示技术详解
在现代用户界面设计中,侧边栏(Sidebar)是一个常见的组件,它为用户提供了导航和工具面板的功能。在某些应用场景下,我们可能需要动态地隐藏或显示侧边栏,以优化界面布局或提供更灵活的用户体验。本文将分享如何在Qt框架下实现侧边栏的隐藏与呈现,包括技术细节和代码示例。
79 3
|
17天前
|
UED
Qt侧边栏的动态展示:隐藏与呈现技术详解
在现代用户界面设计中,侧边栏(Sidebar)是一个常见的组件,它为用户提供了便捷的导航和操作入口。在Qt框架中,实现侧边栏的隐藏与呈现不仅能够提升应用的美观度,还能增强用户体验。本文将详细介绍如何在Qt中实现侧边栏的动态隐藏与呈现,包括技术要点和代码实现。
33 0
|
3月前
|
开发工具 C++
qt开发技巧与三个问题点
本文介绍了三个Qt开发中的常见问题及其解决方法,并提供了一些实用的开发技巧。
|
3月前
自己动手写QT多线程demo
本文是作者关于如何编写Qt多线程demo的教程,介绍了如何实现多线程功能,包括可暂停和继续的功能。文章提供了部分示例代码,展示了如何创建线程类、启动和管理线程,以及线程间的通信。同时,还提供了相关参考资料和免费下载链接。
|
3月前
|
4月前
|
C++
C++ Qt开发:QUdpSocket网络通信组件
QUdpSocket是Qt网络编程中一个非常有用的组件,它提供了在UDP协议下进行数据发送和接收的能力。通过简单的方法和信号,可以轻松实现基于UDP的网络通信。不过,需要注意的是,UDP协议本身不保证数据的可靠传输,因此在使用QUdpSocket时,可能需要在应用层实现一些机制来保证数据的完整性和顺序,或者选择在适用的场景下使用UDP协议。
191 2
Qt开发网络嗅探器02
Qt开发网络嗅探器02
|
4月前
|
网络协议 容器
Qt开发网络嗅探器03
Qt开发网络嗅探器03
|
5月前
|
数据安全/隐私保护 C++ 计算机视觉
Qt(C++)开发一款图片防盗用水印制作小工具
文本水印是一种常用的防盗用手段,可以将文本信息嵌入到图片、视频等文件中,用于识别和证明文件的版权归属。在数字化和网络化的时代,大量的原创作品容易被不法分子盗用或侵犯版权,因此加入文本水印成为了保护原创作品和维护知识产权的必要手段。 通常情况下,文本水印可以包含版权声明、制作者姓名、日期、网址等信息,以帮助识别文件的来源和版权归属。同时,为了增强防盗用效果,文本水印通常会采用字体、颜色、角度等多种组合方式,使得水印难以被删除或篡改,有效地降低了盗用意愿和风险。 开发人员可以使用图像处理技术和编程语言实现文本水印的功能,例如使用Qt的QPainter类进行文本绘制操作,将文本信息嵌入到图片中,
191 1
Qt(C++)开发一款图片防盗用水印制作小工具
|
4月前
|
监控 C++ 容器
【qt】MDI多文档界面开发
【qt】MDI多文档界面开发
97 0