【Qt】绘图与绘图设备

文章目录

  • 绘图设备
  • QPainter绘图实例
    • 案例1
    • 案例2-高级设置
    • 案例3:利用画家画资源图片 点击按钮移动图片
  • QtPaintDevice实例
    • Pixmap绘图设备
    • QImage 绘图设备
    • QPicture 绘图设备

QPainter绘图

Qt 的绘图系统允许使用相同的 API 在屏幕和其它打印设备上进行绘制。整个绘图系统基于QPainter,QPainterDevice和QPaintEngine三个类

  • QPainter用来执行绘制的操作
  • QPaintDevice是一个二维空间的抽象,这个二维空间允许QPainter在其上面进行绘制,也就是QPainter工作的空间
  • QPaintEngine提供了画笔(QPainter)在不同的设备上进行绘制的统一的接口。QPaintEngine类应用于QPainter和QPaintDevice之间,通常对开发人员是透明的

可以把QPainter理解成画笔;把QPaintDevice理解成使用画笔的地方,比如纸张、屏幕等;而对于纸张、屏幕而言,肯定要使用不同的画笔绘制,为了统一使用一种画笔,我们设计了QPaintEngine类,这个类让不同的纸张、屏幕都能使用一种画笔

层次结构

img

**Qt 的绘图系统实际上是,使用QPainter在QPainterDevice上进行绘制,它们之间使用QPaintEngine进行通讯(也就是翻译QPainter的指令)


绘图设备

绘图设备是指继承QPainterDevice的子类,Qt一共提供了四个这样的类:QPixmap、QBitmap、QImage和 QPicture

  • QPixmap专门为图像在屏幕上的显示做了优化
  • QBitmap是QPixmap的一个子类,它的色深限定为1,可以使用 QPixmap的isQBitmap()函数来确定这个QPixmap是不是一个QBitmap,因为QBitmap色深小,因此只占用很少的存储空间,所以适合做光标文件和笔刷。
  • QImage专门为图像的像素级访问做了优化
  • QPicture则可以记录和重现QPainter的各条命令。 QPicture将QPainter的命令序列化到一个IO设备,保存为一个平台独立的文件格式

QPainter绘图实例

案例1

首先需要在Widget文件当中重写绘图事件:

image-20231005155422449


void MainWindow::paintEvent(QPaintEvent *)
{
    //实例化画家对象  this指定的是绘图设备 在当前窗口画画
    QPainter painter(this);

    //设置画笔
    QPen pen(QColor(255,0,0)); //RGB  目前是红笔
    //设置画笔宽度
    pen.setWidth(3);    
    //设置画笔风格
    pen.setStyle(Qt::DotLine);
    //让画家 使用这个笔
    painter.setPen(pen);


    //设置画刷=》对于封闭的图形内部会上色  Qt::cyan  Qt::green 也可以...
    QBrush brush(Qt::cyan); //QBrush brush(QColor(255,0,0)) 也可以
    //设置画刷风格
    brush.setStyle(Qt::Dense7Pattern);
    //让画家使用画刷
    painter.setBrush(brush);


    //画线 =>两点确定一线
    painter.drawLine(QPoint(0,0) , QPoint(100,100));

    //画圆 椭圆  ⚪也是椭圆的一种
    painter.drawEllipse( QPoint(100,100) , 50,50); //参数依次代表:圆心 左半径  上半径

    //画矩形
    painter.drawRect(QRect(20,20,50,50));//参数依次代表:左上角的点 宽 高

    //画文字 =>本质是在矩形框内部画文字
    painter.drawText(QRect(10,200,150,50) , "好好学习,天天向上");
}
image-20231005155857200

案例2-高级设置

QPainter painter(this);
painter.drawEllipse(QPoint(100,50) , 50,50); //画圆

//设置 抗锯齿能力=>画的更好  但是效率较低
painter.setRenderHint(QPainter::Antialiasing);
painter.drawEllipse(QPoint(200,50) , 50,50);//画圆


// 画图1->保存点->画图2->恢复到保存点->画图3  所以最后只有画图1和3的矩形
painter.drawRect(QRect(20,20,50,50));

//移动画家位置开始画画的位置
painter.translate(100,0);

//保存画家状态
painter.save();

painter.drawRect(QRect(20,20,50,50));

painter.translate(100,0);//移动画家位置开始画画的位置

//还原画家保存状态 =>在这里的代码当中,只打印了两个矩形,有一个被覆盖了
painter.restore();

painter.drawRect(QRect(20,20,50,50));

image-20231005160220261


案例3:利用画家画资源图片 点击按钮移动图片

前置工作:

1.在ui界面当中新增加一个按钮:移动图片

2.在mainWidget.h当中新增一个成员:int posX = 0

3.引入资源文件

构造函数

MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    //点击移动按钮,移动图片
    connect(ui->pushButton,&QPushButton::clicked,[=](){

        posX+=20;
        //如果要手动调用绘图事件 用update更新
        update();//更新绘图事件
    });

    //开启定时器
    QTimer * timer = new QTimer(this);
    timer->start(10);

    connect(timer,&QTimer::timeout,[=](){
        posX++;
        update();//更新绘图事件
    });

}
void MainWindow::paintEvent(QPaintEvent *)
{
    /利用画家 画资源图片 ///
     QPainter painter(this); //画在当前窗口
     QPixmap pix = QPixmap(":/image/tree.png");

     //如果超出屏幕,重新从0位置开始往右移动
     if(posX >= this->width()) //this->width()屏幕的宽度  this->height()屏幕的高度
     {
         posX = 0;
     }

     painter.drawPixmap(posX,0,pix); //posX:类的成员
}

QtPaintDevice实例

同理也需要重写绘图事件

//绘图事件
void paintEvent(QPaintEvent *);

Pixmap绘图设备

//Pixmap绘图设备 会专门为平台做了显示的优化
QPixmap pix(300,300);//相当于300*300的宽 高的纸张

//填充背景颜色
pix.fill(Qt::white);

//声明画家
QPainter painter(&pix);//往pix当中画画

painter.setPen(QPen(Qt::green));//设置画笔颜色
painter.drawEllipse(QPoint(150,150) , 100,100);//画圆

//保存到磁盘的某个位置
pix.save("E:\\pix.png");

QImage 绘图设备

实例1

QImage img(300,300,QImage::Format_RGB32); //宽 高
img.fill(Qt::white);

QPainter painter(&img);
painter.setPen(QPen(Qt::blue));
painter.drawEllipse(QPoint(150,150) , 100,100);

//保存
img.save("E:\\img.png");

可以对像素进行访问

void MainWindow::paintEvent(QPaintEvent *)
{
        QPainter painter(this);

        //利用QImage 对像素进行修改
        QImage img;
        img.load("E:/img.png"); //加载图片

        //修改像素点
        for(int i = 50 ;i < 100 ; i++)
        {
            for(int j = 50 ; j < 100;j++)
            {
                QRgb value = qRgb(255,0,0); //像素点类型
                img.setPixel(i,j,value);//第i行第j列变为value该像素
            }
        }

        painter.drawImage(0,0,img);
}

image-20231005202013208


QPicture 绘图设备

//QPicture 绘图设备  可以记录和重现 绘图指令
QPicture pic;
QPainter painter; //可以后面再指定绘图设备
painter.begin(&pic);  //=>指定绘图设备=>开始往pic上画
painter.setPen(QPen(Qt::cyan));
painter.drawEllipse(QPoint(150,150) , 100,100);
painter.end(); //结束画画

//保存到磁盘
pic.save("E:\\pic.zt"); //名称和后缀名任意

然后可以在绘图事件当中进行重现:

void MainWindow::paintEvent(QPaintEvent *)
{
    //重现QPicture的绘图指令
    QPainter painter(this);

    QPicture pic;
    pic.load("E:\\pic.zt");//加载上述保存的图片的路径
    painter.drawPicture(0,0,pic);
}

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

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

相关文章

云安全—K8S API Server 未授权访问

0x00 前言 master节点的核心就是api服务&#xff0c;k8s通过REST API来进行控制&#xff0c;在k8s中的一切都可以抽象成api对象&#xff0c;通过api的调用来进行资源调整&#xff0c;分配和操作。 通常情况下k8s的默认api服务是开启在8080端口&#xff0c;如果此接口存在未授…

RPC与HTTP的关系

首选理清楚关系 RPC与HTTP是两个不同维度的东西 HTTP 协议&#xff08;Hyper Text Transfer Protocol&#xff09;&#xff0c;又叫做超文本传输协议&#xff0c;是一种传输协议&#xff0c;平时通过浏览器浏览网页网页&#xff0c;用到的就是 HTTP 协议。 而 RPC&#xff0…

【java】【MyBatisPlus】【三】【完】MyBatisPlus扩展

目录 一、分页查询lambdaQueryWrapper 二、自定义分页查询 1、UserMapper 2、UserMapper.xml 3、测试方法 三、MybatisX插件 1、安装 2、MybatisX代码快速生成 2.1 连接数据库 2.2 操作需要生成代码的表 3、MybatisX快速生成CRUD&#xff08;前提步骤2生成&#xff…

【算法练习Day32】 斐波那契数爬楼梯使用最小花费爬楼梯

​&#x1f4dd;个人主页&#xff1a;Sherry的成长之路 &#x1f3e0;学习社区&#xff1a;Sherry的成长之路&#xff08;个人社区&#xff09; &#x1f4d6;专栏链接&#xff1a;练题 &#x1f3af;长路漫漫浩浩&#xff0c;万事皆有期待 文章目录 斐波那契数爬楼梯使用最小花…

探讨下前端测试的常见场景

前端测试 场景 这边指的测试是指白盒测试&#xff0c;用代码来测试代码。 测试有利于提升代码质量。 代码功能和需求一致。根据需求&#xff0c;写测试。测试通过了&#xff0c;则表明需求实现了。保证代码重构后&#xff0c;未改坏以前的功能。代码重构后&#xff0c;能通过…

[C++入门系列]——类和对象下篇

​作者主页 &#x1f4da;lovewold少个r博客主页 ⚠️本文重点&#xff1a;C类和对象下篇知识点讲解 &#x1f449;【C-C入门系列专栏】&#xff1a;博客文章专栏传送门 &#x1f604;每日一言&#xff1a;宁静是一片强大而治愈的神奇海洋&#xff01; 目录 前言 再谈构造函数…

解决方案|法大大电子合同加速互联网家装服务升级

随着互联网的快速发展以及政策的不断推动&#xff0c;家装行业“互联网”趋势也不断凸显。行业内很多企业已经开始在全链条业务中使用电子合同&#xff0c;基于电子合同合规化、无纸化、线上化、智能化的价值赋能&#xff0c;实现家装从需求沟通、家装设计、选材、装修施工、验…

【MySQL--->内外连接】

文章目录 [TOC](文章目录) 一、内连接二、左外连接三、右外连接 一、内连接 内连接就是将两个表连接进行笛卡尔积查询 显示SMITH的名字和部门名称 二、左外连接 左外连接就是以左面的表为主&#xff0c;即便是右边的表没有而左边表项中有的&#xff0c;依然显示 查询所有学…

jenkins详细安装教程

这里写目录标题 一、Jenkins安装与部署1-1、Jenkins的简介1-2、下载需要的软件1-2-1 jekins.war1-2-2 tomcat安装方式 1-3、使用11版本的jdk1-4、开启jenkins1-5、获取密码1-5 修改镜像(可改可不改) 二、卸载Jenkins 一、Jenkins安装与部署 1-1、Jenkins的简介 Jenkins是一个…

Linux 基础入门

Linux 简介 Linux 是一种自由和开放源码的类 UNIX 操作系统。 Linux 英文解释为 Linux is not Unix。 Linux 是在 1991 由林纳斯托瓦兹在赫尔辛基大学上学时创立的&#xff0c;主要受到 Minix 和 Unix 思想的启发。 Linux 内核最初只是由芬兰人林纳斯托瓦兹&#xff08;Linus T…

基于SSM的n省出口基地公共信息服务平台设计与实现

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;采用JSP技术开发 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#x…

Spring Cloud Gateway + Knife4j 4.3 实现微服务网关聚合接口文档

目录 前言Spring Cloud 整合 Knife4jpom.xmlapplication.ymlSwaggerConfig.java访问单服务接口文档 Spring Cloud Gateway 网关聚合pom.xmlapplication.yml访问网关聚合接口文档 接口测试登录认证获取登录用户信息 结语源码 前言 youlai-mall 开源微服务商城新版本基于 Spring…

评估在线不平衡学习的PAUC

评估在线不平衡学习的PAUC 原始论文《Prequential AUC: properties of the area under the ROC curve for data streams with concept drift》 由于正常的AUC需要计算整体数据集上&#xff0c;每个数据的预测置信度的排名。那么我们首先要求我们的在线学习算法在进行预测时也返…

node实战——后端koa结合jwt连接mysql实现权限登录(node后端就业储备知识)

文章目录 ⭐前言⭐ 环境准备⭐ 实现过程⭐ mysql 配置⭐路由前的准备⭐账号注册生成token⭐账号登录生成token⭐token登录 ⭐ 自测过程截图⭐总结⭐结束 ⭐前言 大家好&#xff0c;我是yma16&#xff0c;本文分享关于node实战——后端koa项目配置jwt实现登录注册&#xff08;n…

博客模板博客模板

xservices-bpm-6.2.1.1.jar 本人详解 作者&#xff1a;王文峰&#xff0c;参加过 CSDN 2020年度博客之星&#xff0c;《Java王大师王天师》作者 公众号&#xff1a;山峯草堂&#xff0c;非技术多篇文章&#xff0c;专注于天道酬勤的 Java 开发问题、中国国学、传统文化和代码爱…

智慧矿山AI算法助力护帮板支护监测,提升安全与效率

在智慧矿山AI算法系列中&#xff0c;护帮板支护监测是保障矿山安全和提高生产效率的重要环节。护帮板作为矿山支护体系中的重要组成部分&#xff0c;在矿山生产中起到了关键的作用。那么&#xff0c;护帮板在哪种状态下是正常打开的呢&#xff1f;本文将对此进行介绍。 护帮板的…

LeetCode热题100 240.搜索二维矩阵||

题目描述&#xff1a; 编写一个高效的算法来搜索 m*n 矩阵 matrix 中的一个目标值 target 。该矩阵具有以下特性&#xff1a; 每行的元素从左到右升序排列。每列的元素从上到下升序排列。 示例1&#xff1a; 输入&#xff1a;matrix [[1,4,7,11,15],[2,5,8,12,19],[3,6,9,16,2…

「实验记录」CS144 Lab0 networking warmup

文章目录 一、Motivation二、SolutionsS1 - Writing webgetS2 - An in-memory reliable byte stream 三、Results四、Source 一、Motivation 第一个小测试 webget 是想让我们体验并模拟一下在浏览器中键入 URL 后获得远程服务器传来的内容&#xff0c;这并没有太大的难度&…

【IDEA】设置sql提示

第一步&#xff1a;注入SQL语言 1.首先选择任意一条sql语句&#xff0c;右击&#xff0c;选择 ‘显示上下文操作’ 2.选择 ‘注入语言或引用’ 3. 往下翻&#xff0c;找到MySQL 第二步&#xff1a;配置MySQL数据库连接 1.首先点击侧边的数据库&#xff0c;再点击上面的加号 2…

OpenCV官方教程中文版 —— Hough 圆环变换

OpenCV官方教程中文版 —— Hough 圆环变换 前言Hough 圆环变换 前言 目标 • 学习使用霍夫变换在图像中找圆形&#xff08;环&#xff09; • 学习函数&#xff1a;cv2.HoughCircles() Hough 圆环变换 opencv_logo.png&#xff1a; # -*- coding: utf-8 -*- import cv2 …