Qt 帧动画 (QWidget)
来源:互联网 发布:nginx 线程模型 编辑:程序博客网 时间:2024/06/06 14:14
引言
动画很让人烦恼,在Qt中,已经给出了很多简单的动画,例如 QPropertyAnimation 类实现的动画,但是还不够智能,不是我想要的,相信你也有同感,今天我们就来实现自定义动画类
来方便我们日后的开发。
版权所有:瓯裔,转载请注明出处:http://blog.csdn.net/csnd_ayo
简介
操作系统:window7 x64
编程IDE:Qt Creator 4.2.1
Qt版本: 5.0.3 · 5.3.0 · 5.8.0
最后更新:2017年4月14日
- 引言
- 简介
- 示例
- 效果
- 下载
- 原理
- 实现
- 逻辑函数
示例
效果
效果展示
为了减小文件,我对gif动画做了一些删减,所以看起来好像有跳帧的现象,其实并没有。所需资源
封装后引用
封装后我只需要五行代码即可显示自定义的动画了。
#include "widget.h"#include "ui_widget.h"#include "customdynamicwidget.h"Widget::Widget(QWidget *parent) : QWidget(parent), ui(new Ui::Widget){ ui->setupUi(this); dynamicAnima_ = new CustomDynamicWidget(this); dynamicAnima_->setAnimation(QPixmap(":/q/level_num.png"),10,100); dynamicAnima_->setGeometry(41,41,41,41); dynamicAnima_->show(); // 顺时针播放每帧 dynamicAnima_->startClockwise();}Widget::~Widget(){ delete ui;}
下载
拥有了这个类,你就拥有了所有动画!
代码:下载
图片:下载
原理
- 实现关联
#include <QTimer> #include <QPainter> #include <QWidget>
逻辑流程
等比例切割传入的图片元素
- 创建定时器,并关联更新槽
- 等比例对图片进行切割
利用了
定时器(QTimer)
定时更新界面- 定时器被触发
- 辨别当前帧
- 若是尾帧辨别是否启用了动画无限循环
- 修改帧
- 更新界面
重写paintEvent函数,利用
画家类(QPainter)
完成自绘。- 获取当前帧的对应图片
- 更新当前窗口
实现
逻辑函数
- 1、等比例切割传入的图片元素
/** 设置动画* setAnimation* _pix:图片* _count:图片帧数* _msec:切换速度 (毫秒 1秒 = 1000毫秒)*/void CustomDynamicWidget::setAnimation(const QPixmap &_pix, const short _count, const int _msec) { count_ = _count; currentIndex_ = 0; if (!pixList_.empty()) { pixList_.clear(); } else { /* 顺时针动画关联 */ clockTimer_ = new QTimer(this); clockTimer_->setInterval(_msec); connect(clockTimer_, SIGNAL(timeout()), this, SLOT(updateClockwise())); /* 逆时针动画关联 */ counterclockTimer_ = new QTimer(this); counterclockTimer_->setInterval(_msec); connect(counterclockTimer_, SIGNAL(timeout()), this, SLOT(updateCounterclockwise())); } /* 链式动画图标分离 */ for(short i=0; i != _count; ++i) { pixList_.append(_pix.copy(i * (_pix.width() / _count), 0, _pix.width() / _count, _pix.height())); } currentPix_ = pixList_.at(0); this->setGeometry(0,0,currentPix_.width(),currentPix_.height()); update();}
- 2、利用了
定时器(QTimer)
定时更新界面
void CustomDynamicWidget::updateClockwise(void) { do { if (currentIndex_ < count_ && currentIndex_ >= 0) { /* 更新帧 */ currentPix_ = pixList_.at(currentIndex_); update(); /* 判断帧数 */ if (currentIndex_ >= (count_ - 1)) { if(isLoop_) { currentIndex_ = 0; return; } break; } /* 跳帧 */ ++currentIndex_; return; } #ifndef QT_NO_DEBUG else { qDebug() << __FUNCTION__ << "waring: 错误的下标" << currentIndex_; } #endif } while(false); clockTimer_->stop(); currentIndex_ = 0; emit clockwiseFinished();}
- 3、重写paintEvent函数,利用
画家类(QPainter)
完成自绘。
void CustomDynamicWidget::paintEvent(QPaintEvent *) { QPainter painter(this); painter.drawPixmap(rect(), currentPix_);}
- 头文件
#ifndef CUSTOMDYNAMICWIDGET_H#define CUSTOMDYNAMICWIDGET_H/** 自定义动画类* 作者:瓯裔* 邮箱:727057301@qq.com* CSDN:http://blog.csdn.net/csnd_ayo* 创建时间:2017年1月9日 19:34:13* QT版本:5.0.2 ~ 5.8.0*/#include <QWidget>/** 说明:* 当前类是针对一张链式图片* 链式图片默认为8帧,默认0.1秒播放一帧* 可以根据自己需要进行设置与更改* 进行自动切割,循环播放每一帧** 示例:* 类内声明 CustomDynamicWidget* dynamicAnima_* ui->setupUi(this);* dynamicAnima_ = new CustomDynamicWidget(this);* dynamicAnima_->setAnimation(QPixmap(":/res/loading.png"),8,100);* dynamicAnima_->setGeometry(100,100,300,300);* dynamicAnima_->show();* // 顺时针播放每帧* dynamicAnima_->startClockwise();*/class QTimer;class CustomDynamicWidget : public QWidget{ Q_OBJECTpublic: explicit CustomDynamicWidget(QWidget *parent = 0); /* * 设置动画图标 * 函数名:setAnimation * 参数 _pix:图标实例 * 参数 _count:图标实例动画帧数 * 参数 _msec:动画切帧速度 (毫秒级) */ void setAnimation(const QPixmap& _pix, const short _count = 8, const int _msec = 100); /* 开始动画(顺时针) */ void startClockwise(void); /* 开始动画(逆时针) */ void startCounterclockwise(void); /* 停止动画 */ void stop(void); /* 设置动画无限循环 */ void setLoop(const bool _isLoop = false) { isLoop_ = _isLoop; }signals: /* 顺时针动画结束 */ void clockwiseFinished(void); /* 逆时针动画结束 */ void counterclockwiseFinished(void);private slots: /* 顺时针动画槽 */ void updateClockwise(void); /* 逆时针动画槽 */ void updateCounterclockwise(void);protected: void paintEvent(QPaintEvent *);private: /* 动画(是否无限循环) */ bool isLoop_; /* 图标列表数量 */ short count_; /* 当前展示的图标下标 */ short currentIndex_; /* 控制顺时针槽定时器 */ QTimer *clockTimer_; /* 控制逆时针槽定时器 */ QTimer *counterclockTimer_; /* 当前展示的图标 */ QPixmap currentPix_; /* 图标列表 */ QList<QPixmap> pixList_;};#endif // CUSTOMDYNAMICWIDGET_H
5 0
- Qt 帧动画 (QWidget)
- Qt QWidget控件透明动画实现
- QT主要类QWidget
- QT主要类QWidget
- QT主要类QWidget
- QT主要类QWidget
- Qt QWidget 类简介
- Qt类之--Qwidget
- Qt 汽车仪表 QWidget
- Qt常用类QWidget
- Qt之设置QWidget背景色(4种方法,推荐QWidget::setAutoFillBackground)
- QT学习(四)如何正确继承QWidget
- Qt 常用类 (9)—— QWidget
- Qt类简介之QWidget类(1)
- QT学习(二)之QWidget,QDialog,QMainWindow
- Qt 常用类 (9)—— QWidget
- Qt 常用类 (9)—— QWidget
- Qt 常用类 (10)—— QWidget
- NC编译器结题以及软件重用性的思索
- SpringMVC原理图
- 图像分割(二)——阈值分割/区域生长/区域分裂合并法
- C# 数组最大值与最小值
- (转)ImageView 设置图片
- Qt 帧动画 (QWidget)
- 优先队列(3道优先队列问题)
- mac上找java的地址
- toast
- 二叉树实现计算器
- 计算平方
- 观察者模式
- ScheduledFuture
- 紫书章六例题六 小球下落 (UVA 679) (直接模拟超时,找规律)