使用Qt开发桌面程序,经常会有标绘的需求,一般有以下几点:

  • 新建:圆、矩形、椭圆、文字标注,插入图像等;
  • 编辑:指对已标绘内容的属性编辑修改功能;
  • 删除:指对已标绘内容的删除功能;
  • 浏览:指提供对已标绘内容的平移、放大缩小等浏览操作。

包含标绘功能的最典型的应用是地图标绘系统。一个简易的地图标绘系统demo如下图所示:

Qt中,标绘功能有不同的实现方式,通常有以下几种。

基于QPainter的面向过程的实现方式

此种方式下,实现一个标绘系统,通常需要创建一个QWidget子类,在子类中实现鼠标、键盘等事件响应以及界面刷新显示。

具体的做法为:

  • 新建QWidget子类
  • 根据需求,选择重载鼠标移动mouseMoveEvent、鼠标点击mousePressEvent、鼠标释放mouseReleaseEvent等鼠标事件响应函数,选择重载按键按下keyPressEvent、按键释放keyReleaseEvent等按键事件响应函数。
  • 重载paintEvent界面刷新响应函数,根据输入实时绘制图元,刷新界面,响应用户的操作,实现流畅的交互过程。

此种实现方式最大的优点是简洁,仅仅新建一个类以及重载几个必要的函数即可实现简单的标绘功能。但是它的缺点也是显而易见的,主要有以下几点:

  • 维护问题。当标绘元素种类增多时,所有的标绘元素的实现代码都糅合在一个QWidget子类中,这会导致此类逐渐难以维护。如果代码结构不清晰,容易出现bug。
  • 功能问题。一些高级功能特性,例如坐标计算/转换、仿射变换、层叠特性、裁剪优化、图元命中/索引算法,需要自己来实现,实现难度大,工作量也很大。
  • 性能问题。如果对性能要求较高,就需要做大量优化,自己实现难度大。

所以基于QPainter的面向过程的实现方式比较适用于构建小规模、功能简易的标绘系统。
为了克服以上缺点,可以尝试采用基于QGraphicsView的面向对象的实现方式。

基于QGraphicsView的面向对象的实现方式

基于QGraphicsView的面向对象的实现方式,是指使用Qt库内置的QGraphicsView模块构建标绘系统的方法。文章开始部分介绍的地图标绘系统demo就是基于QGraphicsView实现的。

QGraphicsView库对标绘业务进行了建模,抽象出了场景画布及图元类,并提供了常用的高级特性。采用面向对象的方式,可以将不同部分的业务代码分散到不同的类中,并通过对象间通信完成协作,从而构建出结构清晰,易于维护的系统。

基于QGraphicsView,使用者可以把更多的精力放在业务实现上。在构建比较复杂的标绘系统时,使用QGraphicsView是首选方案。

QGraphicsView具体在性能、功能方面的特点,在官方文档中有详细描述。除文档外,官方还提供了“40000 Chips”、“Diagram Scene Example”等完整可用的demo供学习。

QGraphicsView相对于QPainter的区别在于,它需要一定的学习成本,对面向对象的编码能力有一定的要求。

结语

通过系统地分析,我们研究了两种标绘的实现方案。不同实现方案适用于不同的使用场景,实际使用时根据需求权衡方案即可。


本文原创首发于微信公众号“Qt未来工程师”。

Qt中标绘功能的实现方法对比相关推荐

  1. Qt 2D绘图功能简单总结

    文章目录 Qt 2D绘图功能简单总结 Qt 2D绘图功能简单总结 Qt 的绘图功能非常强大,它可以绘制一切想要的图形,从最简单的一条直线到其他任何复杂的图形,还可以用来绘制文本和图片. Qt的绘图系统 ...

  2. Qt 程序获取各种文件路径方法

    Qt 程序获取程序所在路径.用户目录路径.临时文件夹等特殊路径的方法 经常我们的程序中需要访问一些特殊的路径,比如程序所在的路径.用户目录路径.临时文件夹等.在 Qt 中实现这几个功能所用的方法虽然都 ...

  3. Qt创建多线程的两种方法

    来源:https://github.com/czyt1988/czyBlog/tree/master/tech/QtThread 1.摘要 Qt有两种多线程的方法,其中一种是继承QThread的run ...

  4. 传统情感分类方法与深度学习的情感分类方法对比

    标注:本博客是参考论文有<传统情感分类方法与机遇深度学习的情感分类方法对比分析>.<自然语言处理中的深度学习:方法及应用> 情感分类是自然语言处理的重要分支,传统情感分类主要有 ...

  5. 基于Flink的实时数据消费应用、功能质量保障方法

    前言:由于最近公司的实时数据处理引擎再向Flink迁移,所以专门设计.总结了一篇"基于Flink的实时数据消费应用.功能质量保障方法".欢迎大家一起分享探讨在大数据方面的测试方法和 ...

  6. 功能连接分析方法及其解释缺陷的综述

    文章来源于微信公众号(茗创科技),欢迎有兴趣的朋友搜索关注. 本文是一篇关于功能连接分析方法及其相关注意事项的综述,于2016年发表在Frontiers in Systems Neuroscience ...

  7. 实战: 对GBDT(lightGBM)分类任务进行贝叶斯优化, 并与随机方法对比

    目录: 一. 数据预处理 1.1 读取&清理&切割数据 1.2 标签的分布 二. 基础模型建立 2.1 LightGBM建模 2.2 默认参数的效果 三. 设置参数空间 3.* 参数空 ...

  8. Qt中添加背景图片的方法

    Qt中添加背景图片的方法 QPalette的方法 #include #include int main(int argc, char *argv[]) { QApplication app(argc, ...

  9. 最简易的Qt白板绘图功能

    由于最近工作项目中涉及到了Qt自绘高级控件等知识,因此写一篇博客来记录一下Qt最简单的绘图功能的实现过程: 以下是自制白板的demo运行结果:(Win 11 + Qt 5.12.3 + VS 2017 ...

最新文章

  1. iOS 代码实现获得应用的版本号(Version/Build)
  2. python销售管理系统_python实现手机销售管理系统
  3. 新基建来了!5G边缘计算如何展现勃勃生机?
  4. 7-3 欢迎参加贵工程2021年C语言程序设计大赛! (5 分)
  5. 许可证密钥_如何激活和停用NVivo的许可证
  6. Linux学习-11月13日(PHP安装)
  7. Eclipse中添加Windows Builder进行Swing图形界面设计
  8. matlab ss2ss,Zemax+DDE+toolbox+for+Matlab 该工具箱可实现matlab编程和zemax通信 - 下载 - 搜珍网...
  9. 信息学奥赛一本通|1179:奖学金
  10. Android中调用百度翻译Demo
  11. NOIP原题 斗地主(20190804)
  12. 浅墨博客《Real Time Rendering 3rd》提炼总结 截取(一)
  13. 6、spss做logistic回归
  14. php计算素数,质数素数计算器
  15. bzoj4416 阶乘字符串 子集dp
  16. 突发!中国顶级程序员左耳朵耗子(陈皓)去世
  17. Hadoop集群搭建之SSH无密码登录配置
  18. 从量变到质变,新华三不求最大但求最强
  19. php个人网盘搭建,一键式搭建私人网络硬盘、个人网盘,百度网盘——owncloud安装指南...
  20. 求助,为什么苹果系统安装了endnote了WPS检测不到

热门文章

  1. Visual Studio调试之断点基础篇
  2. HDU 2042:不容易系列之二
  3. 【Python笔记】异常处理
  4. 902. 最短编辑距离
  5. exception日志 php_PHP 错误与异常的日志记录
  6. drools动态配置规则_关于规则引擎
  7. java上传组件_java上传组件FileUpload
  8. java integer最大值_五分钟学会java中的基础类型封装类
  9. linux系统安装佳能打印机驱动,在ubuntu16.04 64-bit上安装佳能打印机驱动Linux_UFRII_PrinterDriver_V320_us_EN...
  10. 如何设置打印的时候不加上页面链接_excel表格的这10个打印小技巧,办公室财务人员记得收藏...