Qt 幀動畫 (QWidget)
引言
動畫很讓人煩惱,在Qt中,已經給出了很多簡單的動畫,例如 QPropertyAnimation 類實現的動畫,但是還不夠智慧,不是我想要的,相信你也有同感,今天我們就來實現自定義動畫類
來方便我們日後的開發。
簡介
作業系統: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
/*
* 自定義動畫類
* 作者:甌裔
* 郵箱:[email protected]
* 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_OBJECT
public:
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
相關推薦
Qt 幀動畫 (QWidget)
引言 動畫很讓人煩惱,在Qt中,已經給出了很多簡單的動畫,例如 QPropertyAnimation 類實現的動畫,但是還不夠智慧,不是我想要的,相信你也有同感,今天我們就來實現自定義動畫類來方便我們日後的開發。 簡介 作業系統:windo
Android 學習之逐幀動畫(Frame)
http sta ram override start pub fill creat 代碼 幀動畫就是將一些列圖片。依次播放。利用肉眼的“視覺暫留”的原理,給用戶的感覺是動畫的錯覺,逐幀動畫的原理和早期的電影原理是一樣的。 a:須要定義逐幀動畫,能夠通過代碼定義。也能夠
Cocos2d-JS中使用CocosStudio資源——幀動畫(1)
在本篇部落格中,我們將通過一個在Cocos2d-JS中使用從CocosStudio匯出的幀動畫資源的例子,來簡要介紹以下內容:利用ActionTimeLine進行動畫切割,如何使用匯出的幀動畫資源。關於幀動畫,由於內容繁雜。我們將分為兩篇進行介紹。本篇將主
自己定義View時,用到Paint Canvas的一些溫故,簡單的幀動畫(動畫一 ,"掏糞男孩Gif"順便再提提onWindowFocusChanged)
eat android 內容 rri generated 簡單的 fadein spl onclick 轉載請註明出處:王亟亟的大牛之路 之前在繪畫的過程中提到了靜態的旋轉啊,縮放啊,平移等一些效果。那麽自己定義的View當然也有動態的效果也就是我們的
Qt開場動畫(gif效果)的實現
Qt自己提供了一個開場動畫的類QSplashScreen,可以實現簡單的圖片開場的效果,但是是靜態的圖片。 Qt播放gif格式圖片是利用的QMovie實現的。因此利用QMoviee和QTimer,每隔一段時間將QSplashScreen重繪一次,來實現gi
筆記八 :EgretH5通用MVC框架的入門操作:製作並播放幀動畫(UI部分)
前言:幀動畫是遊戲中最常用的的兩種動畫播放形式之一,其中一種是骨骼動畫,一種就是幀動畫了,在H5遊戲中,幀動畫一般用於UI介面的操作動畫,人物技能,特效什麼的。本筆記基於通用MVC框架,以及“筆記一”中的scene搭建的範例,基於原始碼我的資源中的《筆記一到筆記七原始碼》,最
Android三種動畫View Animation(補間動畫) 、Drawable Animation(幀動畫) 、Property Animation(屬性動畫)(下)
轉載:http://blog.csdn.net/lmj623565791/article/details/38092093 三種動畫的優缺點: (1)Frame Animation(幀動畫)主要用於播放一幀幀準備好的圖片,類似GIF圖片,優點是使用簡單
Android 動畫(一)幀動畫、補間動畫
1.Frame Animation(幀動畫) 幀動畫就是把多張圖片在定義的短時間內完成順序播放,最終呈現在視覺上的動態效果;幀動畫首先得具有圖片資源。 下面是幀動畫在Android開發中的具體實現: (1)activity_main.xml檔案: <
Android 幀動畫(Frame Animation) 動畫停止在第一幀
專案中遇到的問題: 需求: 做一個聊天頁面,要求播放語音時,有一個類似於喇叭的動畫,從小到大不停迴圈,語音播放完,動畫停止在第一幀。當點選正在播放的語音時,語音停止,動畫回覆到第一幀(回覆到第一幀是難點) 實現:用Frame Animation 可以在Java程式碼中新
Qt 旋轉動畫(純程式碼)
簡述 初嘗QT不甚歡喜,CSDN上有非常多的朋友在為QT做出貢獻,我也願意以主觀角度來分享QT,讓QT變得更好。 該原始碼系作者個人撰寫,使用時請尊重作者,不要隨意篡改關於作者的資訊。 獲取方式 為了讓你我都能得到提升,請您在評論區留下對我的建議,並附上您可愛的郵箱,
核心動畫(三)-關鍵幀動畫
一、簡單介紹 CAKeyframeAnimation是CApropertyAnimation的子類,跟CABasicAnimation的區別是:CABasicAnimation只能從一個數值(fromValue)變到另一個數值(toValue),而CAKeyf
Android Studio之Activity切換動畫(三)
文章 oid out size ref intel tar studio anim 1、上一篇文章“Android Studio之多個Activity的滑動切換(二)”中實現了多個activity之間的滑動切換,可是新切換出的activity大多是從右側進入 2、我們能
js動畫(速度)
fun esc move keywords nload desc func cache scale <!DOCTYPE html><html><head><meta charset="utf-8" /><meta htt
CSS3動畫(二):波浪效果
col -1 loading ack css代碼 code load width ase 實現效果 如圖所示: 首先得準備三張圖,一張是淺黃色的背景圖loading_bg.png,一張是深紅色的圖loading.png,最後一張為bolang.png。 css代碼
Qt 3D教程(二)初步顯示3D的內容
初始 應用 frame 通過 net settings mod rgba bsp Qt3D教程(二)初步顯示3D的內容 前一篇很easy,全然就沒有牽涉到3D的內容,它僅僅是我們搭建3D應用的基本框架而已,而這一篇。我們將要利用它來初步地顯示3D
CSS3-loading動畫(五)
sla 橢圓 clas gif 同時 沒有 .cn idt das CSS3-loading加載動畫 在線示例demo:http://liyunpei.xyz/loading.html 之前發了四篇,二十二個效果,今天再分享六個效果,總計二十八個效果。 二十三、效果二
QT學習筆記(3) 我的第一個程序
9.png har 中文 gets 有一個 setw 通過 坐標 關系 今天,學習搭建一個空項目,了解程序是如何運行的。 (1)新建一個空項目 1、在創建完空項目之後,項目中只有一個空的項目文件( .pro) 2、然後需要在項目文件(.pro)中添加:
QT學習筆記(5) 菜單欄、工具欄、窗口、對話框
let qlabel rman 運行 內存空間 介紹 edi left setw 本程序主要介紹了以下幾種常用控件的使用方法: (1)菜單欄、工具欄 (2)核心控件、狀態欄、浮動窗口 (3)模態窗口、非模態窗口 (4)標準對話框、文件對話框 代碼如下: mainwindow
QT學習筆記(14) 定時器類DTimer的使用
fin isa play htm number conn stat alt .cn 一、 在前面的學習筆記中,我們已經學習定時器事件http://www.cnblogs.com/blog-ccs/p/7445323.html 現在,我們學習QTimer定時器類,比較
QT學習筆記(13) QT下的UDP通信
組播 create pan int cor 通過 width widget window 一、UDP通信 UDP通信沒有明確的服務器端和客戶端之分 TCP通信像是打電話(必須要接通才能通信),UDP通信像是寫信(不管能不能收到都發送出去) 首先需要QUdpSOc