QGraphicsView实现图片放大、缩小、鼠标拖动、以鼠标点放大缩小

news/2024/4/29 7:31:02/文章来源:https://blog.csdn.net/qq_35662333/article/details/137004945

1. 工程配置文件 pro

1 QT       += core gui2 3 greaterThan(QT_MAJOR_VERSION, 4): QT += widgets4 5 CONFIG += c++116 7 # The following define makes your compiler emit warnings if you use8 # any Qt feature that has been marked deprecated (the exact warnings9 # depend on your compiler). Please consult the documentation of the
10 # deprecated API in order to know how to port your code away from it.
11 DEFINES += QT_DEPRECATED_WARNINGS
12 
13 # You can also make your code fail to compile if it uses deprecated APIs.
14 # In order to do so, uncomment the following line.
15 # You can also select to disable deprecated APIs only up to a certain version of Qt.
16 #DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000    # disables all the APIs deprecated before Qt 6.0.0
17 
18 SOURCES += \
19     ImageWidget.cpp \
20     main.cpp \
21     mainwindow.cpp
22 
23 HEADERS += \
24     ImageWidget.h \
25     mainwindow.h
26 
27 FORMS += \
28     mainwindow.ui
29 
30 # Default rules for deployment.
31 qnx: target.path = /tmp/$${TARGET}/bin
32 else: unix:!android: target.path = /opt/$${TARGET}/bin
33 !isEmpty(target.path): INSTALLS += target
34 
35 RESOURCES += \
36

2. main.cpp

1 #include "mainwindow.h"2 3 #include <QApplication>4 5 int main(int argc, char *argv[])6 {7     QApplication a(argc, argv);8     MainWindow w;9     w.show();
10     return a.exec();
11

3. mainwindow.h

1 #ifndef MAINWINDOW_H2 #define MAINWINDOW_H3 4 #include <QMainWindow>5 #include <QPixmap>6 #include <QGraphicsScene>7 #include <QGraphicsPixmapItem>8 #include <QWheelEvent>9 
10 #include "ImageWidget.h"
11 
12 QT_BEGIN_NAMESPACE
13 namespace Ui { class MainWindow; }
14 QT_END_NAMESPACE
15 
16 class MainWindow : public QMainWindow
17 {
18     Q_OBJECT
19 
20 public:
21     MainWindow(QWidget *parent = nullptr);
22     ~MainWindow();
23 
24     void recvShowPicSignal(QImage image);//接收并显示图片的函数
25 private:
26     Ui::MainWindow *ui;
27     ImageWidget *m_Image;
28 };
29 #endif // MAINWINDOW_H

4. mainwindow.cpp

1 #include "mainwindow.h"2 #include "ui_mainwindow.h"3 4 MainWindow::MainWindow(QWidget *parent)5     : QMainWindow(parent)6     , ui(new Ui::MainWindow)7 {8     ui->setupUi(this);9 
10     setWindowTitle(QStringLiteral("QtQGraphicsView实现图片放大、缩小、鼠标拖动、以鼠标点放大缩小"));
11 
12     QPixmap *backgroundPixmap = new QPixmap(":/new/prefix1/QtImage.png");
13     QImage sizedImage = QImage(backgroundPixmap->toImage());
14     recvShowPicSignal(sizedImage);
15 }
16 
17 MainWindow::~MainWindow()
18 {
19     delete ui;
20 }
21 
22 void MainWindow::recvShowPicSignal(QImage image)
23 {
24     ui->graphicsView->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
25     ui->graphicsView->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
26 
27     QPixmap ConvertPixmap = QPixmap::fromImage(image);//The QPixmap class is an off-screen image representation that can be used as a paint device
28     QGraphicsScene  *qgraphicsScene = new QGraphicsScene;//要用QGraphicsView就必须要有QGraphicsScene搭配着用
29     m_Image = new ImageWidget(&ConvertPixmap);//实例化类ImageWidget的对象m_Image,该类继承自QGraphicsItem,是自己写的类
30     int nwith = ui->graphicsView->width();//获取界面控件Graphics View的宽度
31     int nheight = ui->graphicsView->height();//获取界面控件Graphics View的高度
32     m_Image->setQGraphicsViewWH(nwith,nheight);//将界面控件Graphics View的width和height传进类m_Image中
33     qgraphicsScene->addItem(m_Image);//将QGraphicsItem类对象放进QGraphicsScene中
34     ui->graphicsView->setSceneRect(QRectF(-(nwith/2),-(nheight/2),nwith,nheight));//使视窗的大小固定在原始大小,不会随图片的放大而放大(默认状态下图片放大的时候视窗两边会自动出现滚动条,并且视窗内的视野会变大),防止图片放大后重新缩小的时候视窗太大而不方便观察图片
35     ui->graphicsView->setScene(qgraphicsScene);//Sets the current scene to scene. If scene is already being viewed, this function does nothing.
36     ui->graphicsView->setFocus();//将界面的焦点设置到当前Graphics View控件
37

5. mainwindow.ui

1 <?xml version="1.0" encoding="UTF-8"?>2 <ui version="4.0">3  <class>MainWindow</class>4  <widget class="QMainWindow" name="MainWindow">5   <property name="geometry">6    <rect>7     <x>0</x>8     <y>0</y>9     <width>600</width>
10     <height>400</height>
11    </rect>
12   </property>
13   <property name="windowTitle">
14    <string>MainWindow</string>
15   </property>
16   <widget class="QWidget" name="centralwidget">
17    <widget class="QGraphicsView" name="graphicsView">
18     <property name="geometry">
19      <rect>
20       <x>0</x>
21       <y>0</y>
22       <width>600</width>
23       <height>400</height>
24      </rect>
25     </property>
26    </widget>
27   </widget>
28  </widget>
29  <resources/>
30  <connections/>
31

6. ImageWidget.h

1 #ifndef IMAGEWIDGET_H2 #define IMAGEWIDGET_H3 4 #include <QWidget>5 #include <QtGui>6 #include <QPixmap>7 #include <QPainter>8 #include <QRectF>9 #include <QMouseEvent>
10 #include <QPointF>
11 #include <QDragEnterEvent>
12 #include <QGraphicsSceneWheelEvent>
13 #include <QGraphicsItem>
14 
15 enum Enum_ZoomState{
16     NO_STATE,
17     RESET,
18     ZOOM_IN,
19     ZOOM_OUT
20 };
21 // class ImageWidget :public QObject, QGraphicsItem
22 class ImageWidget :public QGraphicsItem
23 {
24     //Q_OBJECT
25 public:
26     ImageWidget(QPixmap *pixmap);
27     QRectF  boundingRect() const;
28     void    paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget);
29     void    wheelEvent(QGraphicsSceneWheelEvent *event);
30     void    ResetItemPos();
31     void    mousePressEvent(QGraphicsSceneMouseEvent *event);
32     void    mouseMoveEvent(QGraphicsSceneMouseEvent *event);
33     void    mouseReleaseEvent(QGraphicsSceneMouseEvent *event);
34     qreal   getScaleValue() const;
35     void    setQGraphicsViewWH(int nwidth,int nheight);
36 private:
37     qreal       m_scaleValue;
38     qreal       m_scaleDafault;
39     QPixmap     m_pix;
40     int         m_zoomState;
41     bool        m_isMove;
42     QPointF     m_startPos;
43 };
44 #endif // IMAGEWIDGET_H

7. ImageWidget.cpp

1 #include "ImageWidget.h"2 3 #include <QDebug>4 #include <QGraphicsSceneMouseEvent>5 #include <QPointF>6 #include <QGraphicsSceneDragDropEvent>7 #include <QDrag>8 #include <math.h>9 10 ImageWidget::ImageWidget(QPixmap *pixmap)11 {12     m_pix = *pixmap;13     setAcceptDrops(true);//If enabled is true, this item will accept hover events; otherwise, it will ignore them. By default, items do not accept hover events.14     m_scaleValue = 0;15     m_scaleDafault = 0;16     m_isMove = false;17 }18 19 QRectF ImageWidget::boundingRect() const20 {21     return QRectF(-m_pix.width() / 2, -m_pix.height() / 2,22                   m_pix.width(), m_pix.height());23 }24 25 void ImageWidget::paint(QPainter *painter, const QStyleOptionGraphicsItem *,26                     QWidget *)27 {28     painter->drawPixmap(-m_pix.width() / 2, -m_pix.height() / 2, m_pix);29 }30 31 void ImageWidget::mousePressEvent(QGraphicsSceneMouseEvent *event)32 {33     if(event->button()== Qt::LeftButton)34     {35         m_startPos = event->pos();//鼠标左击时,获取当前鼠标在图片中的坐标,36         m_isMove = true;//标记鼠标左键被按下37     }38     else if(event->button() == Qt::RightButton)39     {40         ResetItemPos();//右击鼠标重置大小41     }42 43 }44 45 void ImageWidget::mouseMoveEvent(QGraphicsSceneMouseEvent *event)46 {47     if(m_isMove)48     {49         QPointF point = (event->pos() - m_startPos)*m_scaleValue;50         moveBy(point.x(), point.y());51     }52 }53 54 void ImageWidget::mouseReleaseEvent(QGraphicsSceneMouseEvent *)55 {56     m_isMove = false;//标记鼠标左键已经抬起57 }58 59 60 void ImageWidget::wheelEvent(QGraphicsSceneWheelEvent *event)//鼠标滚轮事件61 {62     if((event->delta() > 0)&&(m_scaleValue >= 50))//最大放大到原始图像的50倍63     {64         return;65     }66     else if((event->delta() < 0)&&(m_scaleValue <= m_scaleDafault))//图像缩小到自适应大小之后就不继续缩小67     {68         ResetItemPos();//重置图片大小和位置,使之自适应控件窗口大小69     }70     else71     {72         qreal qrealOriginScale = m_scaleValue;73         if(event->delta() > 0)//鼠标滚轮向前滚动74         {75             m_scaleValue*=1.1;//每次放大10%76         }77         else78         {79             m_scaleValue*=0.9;//每次缩小10%80         }81         setScale(m_scaleValue);82         if(event->delta() > 0)83         {84             moveBy(-event->pos().x()*qrealOriginScale*0.1, -event->pos().y()*qrealOriginScale*0.1);//使图片缩放的效果看起来像是以鼠标所在点为中心进行缩放的85         }86         else87         {88             moveBy(event->pos().x()*qrealOriginScale*0.1, event->pos().y()*qrealOriginScale*0.1);//使图片缩放的效果看起来像是以鼠标所在点为中心进行缩放的89         }90     }91 }92 93 void ImageWidget::setQGraphicsViewWH(int nwidth, int nheight)//将主界面的控件QGraphicsView的width和height传进本类中,并根据图像的长宽和控件的长宽的比例来使图片缩放到适合控件的大小94 {95     int nImgWidth = m_pix.width();96     int nImgHeight = m_pix.height();97     qreal temp1 = nwidth*1.0/nImgWidth;98     qreal temp2 = nheight*1.0/nImgHeight;99     if(temp1>temp2)
100     {
101         m_scaleDafault = temp2;
102     }
103     else
104     {
105         m_scaleDafault = temp1;
106     }
107     setScale(m_scaleDafault);
108     m_scaleValue = m_scaleDafault;
109 }
110 
111 void ImageWidget::ResetItemPos()//重置图片位置
112 {
113     m_scaleValue = m_scaleDafault;//缩放比例回到一开始的自适应比例
114     setScale(m_scaleDafault);//缩放到一开始的自适应大小
115     setPos(0,0);
116 }
117 
118 qreal ImageWidget::getScaleValue() const
119 {
120     return m_scaleValue;
121

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.luyixian.cn/news_show_1028321.aspx

如若内容造成侵权/违法违规/事实不符,请联系dt猫网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

网站业务对接DDoS高防

准备需要接入的网站域名清单&#xff0c;包含网站的源站服务器IP&#xff08;仅支持公网IP的防护&#xff09;、端口信息等。所接入的网站域名必须已完成ICP备案。如果您的网站支持HTTPS协议访问&#xff0c;您需要准备相应的证书和私钥信息&#xff0c;一般包含格式为.crt的公…

公链角逐中突围,Solana 何以成为 Web3 世界的流量焦点?

在众多区块链公链中&#xff0c;Solana 凭借其创纪录的处理速度和极低的交易费用&#xff0c;成为了众多开发者和投资者的宠儿。就像网络上流行的那句话所说&#xff1a;“Why slow, when you can Solana?”&#xff0c;Solana 正以它的速度和强大的生态系统&#xff0c;重新定…

Github 2024-03-26 Python开源项目日报 Top10

根据Github Trendings的统计,今日(2024-03-26统计)共有10个项目上榜。根据开发语言中项目的数量,汇总情况如下: 开发语言项目数量Python项目10Open Interpreter: 本地代码运行和自然语言界面 创建周期:254 天开发语言:Python协议类型:GNU Affero General Public License …

Spring-ThreadLocal内存泄漏原因及解决办法

ThreadLocal原理回顾 ThreadLocal的原理&#xff1a;每个Thread内部维护着一个ThreadLocalMap&#xff0c;它是一个Map。这个映射表的Key是一个弱引用&#xff0c;其实就是ThreadLocal本身&#xff0c;Value是真正存的线程变量Object。 也就是说ThreadLocal本身并不真正存储线…

react使用ant desgin 组件实现便利开发

1.使用Form.item的方法和语法规则 先导入文件 import {Form} from antd; const [form] Form.useForm(); <Form form{form} name"dynamic_rule" width"100%" onFinish{onFinish} onFinishFailed{onFinishFailed} > 接写来就是渲染内容了 // 点击…

【爬虫开发】爬虫从0到1全知识md笔记第2篇:requests模块,知识点:【附代码文档】

爬虫开发从0到1全知识教程完整教程&#xff08;附代码资料&#xff09;主要内容讲述&#xff1a;爬虫课程概要&#xff0c;爬虫基础爬虫概述,,http协议复习。requests模块&#xff0c;requests模块1. requests模块介绍,2. response响应对象,3. requests模块发送请求,4. request…

CISP 4.2备考之《物理与网络通信安全》知识点总结

文章目录 第 1 节 物理与环境安全第 2 节 网络安全基础第 3 节 网络安全技术与设备第 1 部分 防火墙第 2 部分 入侵检测系统第 3 部分 其他安全产品 第 4 节 网络安全设计规划 第 1 节 物理与环境安全 1.场地选择 1.1 场地选择:自然条件、社会条件、其他条件。1.2 抗震和承重&…

服务器被挖矿了怎么办,实战清退

当我们发现服务器资源大量被占用的时候&#xff0c;疑似中招了怎么办 第一时间重启服务是不行的&#xff0c;这些挖矿木马一定是会伴随着你的重启而自动重启&#xff0c;一定时间内重新霸占你的服务器资源 第一步检查高占用进程 top -c ps -ef 要注意这里%CPU&#xff0c;如果…

R语言使用dietaryindex包计算NHANES数据多种营养指数(2)

健康饮食指数 (HEI) 是评估一组食物是否符合美国人膳食指南 (DGA) 的指标。Dietindex包提供用户友好的简化方法&#xff0c;将饮食摄入数据标准化为基于指数的饮食模式&#xff0c;从而能够评估流行病学和临床研究中对这些模式的遵守情况&#xff0c;从而促进精准营养。 该软件…

python(一)网络爬取

在爬取网页信息时&#xff0c;需要注意网页爬虫规范文件robots.txt eg:csdn的爬虫规范文件 csdn.net/robots.txt User-agent: 下面的Disallow规则适用于所有爬虫&#xff08;即所有用户代理&#xff09;。星号*是一个通配符&#xff0c;表示“所有”。 Disallow&…

达梦数据库自动备份(全库)+还原(全库) 控制台

一 前提 1.安装达梦数据库DB8(请参照以前文章) 我的数据库安装目录是 /app/dmDB8 2.已创建实例 (请参照上一篇文章) 二 准备测试数据 三 自动备份步骤 1.开启归档模式 开启DM管理工具管理控制台 弹不出来工具的 输入命令 xhost 第一步 将服务器转换为配置状态 右键-&g…

【数据结构】顺序表习题之移除元素和合并两个有效数组

&#x1f451;个人主页&#xff1a;啊Q闻 &#x1f387;收录专栏&#xff1a;《数据结构》 &#x1f389;道阻且长&#xff0c;行则将至 前言 嗨呀&#xff0c;今天的博客是关于顺序表的两道题目&#xff0c;是力扣的移除元素和合并有序数组的题目。 一.移除…

面试笔记——框架篇Spring系列(Spring、SpringMVC、SpringBoot)

Spring 线程安全 singleton : bean在每个Spring IOC容器中只有一个实例。 prototype&#xff1a;一个bean的定义可以有多个实例。 问题一&#xff1a; Spring中的单例bean是否是线程安全的&#xff1f; ControllerRequestMapping("/user")public class UserContro…

JavaSE day14笔记

第十四天课堂笔记 课上: 适当做笔记课下 : 总结 , 读代码 , 反复敲代码 , 做练习 数组★★★ 数组 : 存储多个 同一类型 的容器格式 :数组类型 : 引用数据类型, new运算符在堆中 分配一块连续的存储空间 , 系统会给数组元素默认初始化 , 将该数组的引用赋值给数组名 引用数据…

开源 OLAP 及其在不同场景下的需求

目录 一、开源 OLAP 综述 二、OLAP场景思考 2.1 面向客户的报表 2.2 面向经营的报表 2.3 末端运营分析 2.4 用户画像 2.5 订单分析 2.6 OLAP技术需求思考 三、开源数据湖/流式数仓解决方案 3.1 离线数仓体系——Lambda架构 3.2 实时数据湖解决方案 3.3 实时分析解决…

PPP+VPN综合实验

一、实验拓扑 二、实验划分 三、实验需求 四、实验结果 1.配置各端口和pc的IP&#xff1a; pc1&#xff1a; pc2&#xff1a; pc3&#xff1a; pc4&#xff1a; R1: [r1]inter g0/0/0 [r1-GigabitEthernet0/0/0]ip ad 192.168.1.2 24 [r1-GigabitEthernet0/0/0]int s4/0/0…

HCIP —— 多生成树 (MSTP)

MSTP --- Multiple Spanning Tree Protocol --- 802.1s 在 MSTP 中 &#xff0c;提出了实例的概念&#xff0c;相当于可用让多个VLAN同时属于一个实例&#xff0c;然后只需要一个实例生成一棵树。 --- 一种 VLAN 分流的思想 实例ID &#xff1a;instance ID 由 12位 二进制…

【Chrome控制台】network选项卡的使用

首先打开调试面板「windows:F12&#xff1b;mac&#xff1a;commandoptioni」&#xff0c;找到Network选项卡&#xff0c;其中是对网络相关的数据信息。 录制 控制台内容区域左上角红色按钮就是录制按钮&#xff0c;默认是开启状态&#xff0c;表示监听整个页面运行过程中所产…

Delphi模式编程

文章目录 Delphi模式编程涉及以下几个关键方面&#xff1a;**设计模式的应用****Delphi特性的利用****实际开发中的实践** Delphi模式编程的实例 Delphi模式编程是指在使用Delphi这一集成开发环境&#xff08;IDE&#xff09;和Object Pascal语言进行软件开发时&#xff0c;采用…

九河云荣获“华为2024·亚太区年度杰出合作伙伴奖”

2024年3月26日~27日&#xff0c;以“加速智能化&#xff0c;一切皆服务”为主题的华为亚太生态伙伴大会在东莞隆重开幕&#xff0c;九河云作为专业的多云管理服务商&#xff0c;凭借多年来在云领域的赋能发展应邀出席并荣获“亚太区年度杰出伙伴奖”&#xff0c;这不仅彰显了九…