Qt/C++控件实例 QWidget联合动画实现卷轴效果

embedded/2024/10/20 5:45:45/

显示特点

  1. 动态翻页效果:数字在更新时,会有一个从前一数字向下一数字过渡的翻页效果。这种过渡动画使得数字变化过程更加平滑和自然,避免了突然的跳变。

  2. 高对比度显示:每个数字的背景框颜色为红色,数字颜色为白色,这种高对比度设计确保了数字在不同环境下的可读性。

  3. 多位数字同步翻转:控件支持同时翻转多位数字,适用于五位数的显示。每位数字都在相同的时间段内平滑地过渡到新的数值,营造整体的翻页效果。

这种翻页效果不仅美观,而且实用,适合需要频繁更新的数值显示场合,通过视觉动画增强用户体验。

#include "flipcounter.h"
#include <QPainter>// 构造函数,初始化 FlipCounter 对象
FlipCounter::FlipCounter(QWidget *parent): QWidget(parent), previousValue(0), currentValue(0), m_progress(0.0) {setFixedSize(260, 100); // 设置控件的固定大小为 260x100 像素// 初始化动画animation = new QPropertyAnimation(this, "progress"); // 创建动画对象,目标属性为 "progress"animation->setDuration(500); // 设置动画持续时间为 500 毫秒animation->setStartValue(0.0); // 动画开始值为 0.0animation->setEndValue(1.0); // 动画结束值为 1.0connect(animation, &QPropertyAnimation::valueChanged, this, QOverload<>::of(&FlipCounter::update)); // 连接动画的值变化信号到 update 槽函数,用于触发重绘
}// 设置数字并开始动画
void FlipCounter::setNumbers(int previous, int current) {previousValue = previous; // 设置前一个数值currentValue = current; // 设置当前数值m_progress = 0.0; // 重置进度为 0.0// 开始翻页动画animation->start(); // 启动动画
}// 获取当前进度
double FlipCounter::progress() const {return m_progress; // 返回当前进度
}// 设置进度并更新绘制
void FlipCounter::setProgress(double value) {m_progress = value; // 设置新的进度值update(); // 触发重新绘制
}// 绘制事件
void FlipCounter::paintEvent(QPaintEvent *event) {QPainter painter(this); // 创建 QPainter 对象painter.setRenderHint(QPainter::Antialiasing); // 开启抗锯齿painter.setRenderHint(QPainter::TextAntialiasing); // 开启文字抗锯齿// 绘制整体背景painter.setBrush(QColor(22, 53, 81)); // 设置背景颜色为深蓝色painter.drawRect(0, 0, width(), height()); // 绘制整个控件的背景矩形// 设置字体QFont font = painter.font();font.setPointSize(32); // 设置字体大小为 32font.setBold(true); // 设置字体加粗painter.setFont(font); // 应用字体设置// 设置绘制参数int digitSpacing = 10; // 数字之间的水平间隔int charPadding = 4;   // 缩小背景框与数字的间隔int charWidth = (width() - (5 - 1) * digitSpacing) / 5; // 计算每个字符的宽度int charHeight = height() - 2 * charPadding; // 计算每个字符的高度// 将前一个数值和当前数值转换为 5 位的字符串,不足位用 0 填充QString prevText = QString("%1").arg(previousValue, 5, 10, QChar('0'));QString currText = QString("%1").arg(currentValue, 5, 10, QChar('0'));// 循环绘制每一位数字for (int i = 0; i < 5; ++i) {int prevDigit = prevText.mid(i, 1).toInt(); // 获取前一个数值的第 i 位数字int currDigit = currText.mid(i, 1).toInt(); // 获取当前数值的第 i 位数字QRect baseRect(i * (charWidth + digitSpacing), charPadding, charWidth, charHeight); // 计算当前位数字的基础矩形区域int offset = m_progress * charHeight; // 根据进度计算垂直偏移量QRect prevRect = baseRect.translated(0, -offset); // 计算前一个数字的位置,向上偏移QRect currRect = baseRect.translated(0, charHeight - offset); // 计算当前数字的位置,向下偏移// 绘制前一个数字及其背景框QRect prevBackgroundRect = prevRect.adjusted(-charPadding, -charPadding, charPadding, charPadding); // 计算前一个数字背景框的矩形区域painter.setBrush(QColor(200, 42, 65)); // 设置背景颜色为红色painter.setPen(Qt::NoPen); // 不绘制边框painter.drawRect(prevBackgroundRect); // 绘制前一个数字的背景框painter.setPen(Qt::white); // 设置画笔颜色为白色,用于绘制数字painter.drawText(prevRect, Qt::AlignCenter, QString::number(prevDigit)); // 在前一个数字的位置绘制数字// 绘制当前数字及其背景框QRect currBackgroundRect = currRect.adjusted(-charPadding, -charPadding, charPadding, charPadding); // 计算当前数字背景框的矩形区域painter.setBrush(QColor(200, 42, 65)); // 设置背景颜色为红色painter.setPen(Qt::NoPen); // 不绘制边框painter.drawRect(currBackgroundRect); // 绘制当前数字的背景框painter.setPen(Qt::white); // 设置画笔颜色为白色,用于绘制数字painter.drawText(currRect, Qt::AlignCenter, QString::number(currDigit)); // 在当前数字的位置绘制数字}
}


http://www.ppmy.cn/embedded/100385.html

相关文章

从匿名内部类到Lambda表达式:Java编程的优雅进化

匿名内部类 首先我们先来介绍一下什么是匿名内部类 匿名内部类&#xff1a;java中一种特殊的类定义方式&#xff0c;它允许你在需要实现一个接口或继承一个类的地方直接定义一个该接口或类的匿名子类。若想创建一个派生类的对象&#xff0c;并且对象只创建一次&#xff0c;可…

【C#】【EXCEL】Bumblebee/Classes/ExEnums.cs

文章目录 Bumblebee/Classes/ExEnums.csFlow diagramDescriptionCode Bumblebee/Classes/ExEnums.cs Flow diagram #mermaid-svg-FB98N7ZCCccQ4Z38 {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg-FB98N7ZCCccQ4Z38…

【论文阅读】Retargeting and Respecializing GPU Workloads for Performance Portability

摘要 为了接近峰值性能&#xff0c;像gpu这样的加速设备需要大量的特定于架构的调优&#xff0c;以了解共享内存、并行性、tensor core等的可用性。不幸的是&#xff0c;对更高性能和更低成本的追求导致了架构设计的显著多样化&#xff0c;甚至是产自同一供应商的产品也是如此。…

【Linux多线程】线程安全的单例模式

文章目录 1. 单例模式 与 设计模式1.1 单例模式1.2 设计模式1.3 饿汉实现模式 与 懒汉实现模式1.4 饿汉模式① 饿汉模式的特点② 饿汉式单例模式的实现③ 饿汉式单例模式的优缺点④ 适用场景 1.5 懒汉模式① 懒汉式单例模式的特点② 懒汉式单例模式的实现③ 懒汉式单例模式的优…

记录一次搭建uniapp-vue3的基础项目

1.使用 HBuilder X 创建uniapp vue3的基础项目 2.安装 自动导包插件 unplugin-auto-import npm install unplugin-auto-import或者 pnpm install unplugin-auto-import2.1 根目录下创建 vite.config.js 复制粘贴以下内容 import { defineConfig } from vite import uni fro…

【HarmonyOS 4.0】全局UI方法

1. 弹窗 1.1 Toast - 消息提示 常用于显示一些简短的消息或提示&#xff0c;一般会在短暂停留后自动消失。 import promptAction from ohos.promptActionpromptAction.showToast(options: {message: string | Resource, duration: number, bottom: string | number}): void1.2…

第2章-05-接口API与安全签名算法

🏆作者简介,黑夜开发者,CSDN领军人物,全栈领域优质创作者✌,CSDN博客专家,阿里云社区专家博主,2023年CSDN全站百大博主。 🏆数年电商行业从业经验,历任核心研发工程师,项目技术负责人。 🏆本文已收录于专栏:Web爬虫入门与实战精讲,后续完整更新内容如下。 文章…

查找------折半查找(二分查找)

目录 折半查找算法原理 折半查找的步骤 折半查找的时间复杂度 折半查找的空间复杂度 例题演示&#xff1a; 题目描述 具体代码&#xff1a; 折半查找算法原理 折半查找&#xff08;也称为二分查找&#xff09;是一种在有序数组中查找特定元素的搜索算法。它的基本思想是将…