Qt动画框架的学习
近一年,学习游戏开发遇到了瓶颈,主要是因为游戏中有很多复杂的状态要维护,以前使用的switch–if方法现在看来已经穷途末路了,因此,我开始学习游戏开发更加高级的内容。我觉得还是学习游戏人工智能部分是最迫切的。其实游戏的人工智能不仅仅是人工智能,还包含了游戏的架构方面的知识,尤其是当你面对一个非常复杂的系统时,该如何应对。
Qt作为一个优秀的跨平台开源框架,已经有了相关的研究成果。Qt4.6开始就引进了动画框架和状态机框架。这段时间觉得不得不学习Qt的动画框架了,因此写下这篇日志,希望能够帮得上对渴望学习游戏动画方面但是困惑的同学。(原创博客,原文地址:http://blog.csdn.net/jiangcaiyang123/article/details/8680816)
源代码下载地址:这里
最为入门,我想制作一个可以动的按钮。下面是这个程序的截图:
名为”请帮助我”的按钮将从窗口的左上角移动到右下角,耗时5秒。下面是这个程序源代码:
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QPushButton>
class Widget: public QWidget
{
Q_OBJECT
public:
explicit Widget( void );
private:
QPushButton* m_pButton;
};
#endif // WIDGET_H
Widget类定义了一个QPushButton对象的指针,用来显示一个按钮。下面是实现文件:
#include <QtGui>
#include "Widget.h"
/*---------------------------------------------------------------------------*/
Widget::Widget( void ): QWidget( 0 )
{
// 初始化类的成员
resize( 640, 360 );
setWindowTitle( tr( "Qt_EasyAnimation" ) );
m_pButton = new QPushButton( tr( "Please Help" ), this );
// 设置动画
QPropertyAnimation* pAnimation =
new QPropertyAnimation( m_pButton, "geometry" );
pAnimation->setDuration( 5000 );
int textWidth = fontMetrics( ).width( m_pButton->text( ) );
int textHeight = fontMetrics( ).height( );
pAnimation->setStartValue( QRect( 0, 0, textWidth, textHeight ) );
pAnimation->setEndValue( QRect( width( ) - textWidth,
height( ) - textHeight,
textWidth, textHeight ) );
pAnimation->start( );
}
实现文件中使用 QpropertyAnimation类来实现一个属性动画,即通过线性插值(lerp)来对按钮的属性进行设置。注意上面的”geometry”名字是按钮的属性之一,Qt内置类的各种属性可以在Qt Creator的帮助中每一个类的Property中可以看到。随后通过 QpropertyAnimation::setStartValue和QpropertyAnimation:: setEndValue来设置起始和终止状态的值。最后通过QpropertyAnimation::start( )来开始动画。
最后简简单单地完成main.cpp就完工了。
#include <QApplication>
#include <QTranslator>
#include "Widget.h"
int main( int argc, char** argv )
{
QApplication app( argc, argv );
QTranslator trans;
trans.load( ":/zh_CN.qm" );
app.installTranslator( &trans );
Widget w;
w.show( );
return app.exec( );
}
下面我来展示一下Qt如何将状态机框架和动画框架结合起来制作出一个简单的有限状态机动画。
“请帮助我“这个按钮并不自主地移动,它从按下它,将从左上角移动到右下角,在右下角的时候,再按下它,将重新地移动到左上角,耗时2秒。它只是在前一个程序的基础上添加了少部分功能。下面是类Widget的头文件。
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QPushButton>
#include <QPropertyAnimation>
#include <QStateMachine>
class Widget: public QWidget
{
Q_OBJECT
public:
explicit Widget( void );
private:
QStateMachine* m_pMachine;
QPushButton* m_pButton;
};
#endif // WIDGET_H
在第一个例子的基础上,添加了QStateMachine类,用来表示一个有限状态机。下面是Widget.cpp的代码:
#include <QState>
#include <QSignalTransition>
#include "Widget.h"
/*---------------------------------------------------------------------------*/
Widget::Widget( void ): QWidget( 0 )
{
// 设置窗口的成员
resize( 640, 360 );
setWindowTitle( tr( "Qt_EasyAnimation2" ) );
m_pButton = new QPushButton( tr( "Please Help" ), this );
int textWidth = fontMetrics( ).width( m_pButton->text( ) );
int textHeight = fontMetrics( ).height( );
// 设置动画和有限状态机
m_pMachine = new QStateMachine( this );
QState* pState1 = new QState( m_pMachine );
QState* pState2 = new QState( m_pMachine );
pState1->assignProperty( m_pButton, "geometry",
QRect( 0, 0, textWidth, textHeight ) );
pState2->assignProperty( m_pButton, "geometry",
QRect( width( ) - textWidth,
height( ) - textHeight,
textWidth, textHeight ) );
QSignalTransition* transition1 = pState1->addTransition(
m_pButton, SIGNAL( clicked( ) ), pState2 );
QSignalTransition* transition2 = pState2->addTransition(
m_pButton, SIGNAL( clicked( ) ), pState1 );
QPropertyAnimation* pAnimation =
new QPropertyAnimation( m_pButton, "geometry" );
pAnimation->setDuration( 2000 );
transition1->addAnimation( pAnimation );
transition2->addAnimation( pAnimation );
m_pMachine->setInitialState( pState1 );// 设置初始的状态
m_pMachine->start( );
}
这一段代码首先创建状态机,然后在逐个地创建状态,这样可以保证传入的状态机指针是一个有效的指针。通过QState::assignProperty()函数来指定对哪种Qt类的那一个属性进行动画化。随后通过创建一个QSignalTransition来设置从state1到state2的动画转换。这里要保证QPropertyAnimation所指定的属性和QState::assignProperty()中的一致。最后设置一下初始的状态和启动有限状态机就行了。main.cpp和原来的一致,就不赘述了。
分享到:
相关推荐
近一年,学习游戏开发遇到了瓶颈,主要是因为游戏中有很多复杂的状态要维护,以前使用的switch – ...这段时间觉得不得不学习Qt的动画框架了,因此写下这篇日志,希望能够帮得上对渴望学习游戏动画方面但是困惑的同学。
学习QT图形视图、动画框架的小游戏demo,有源码和可执行程序
Qt 5事件处理及实例 第12章 Qt 5多线程 第13章 Qt 5数据库 第14章 Qt 5多国语言国际化 第15章 Qt 5单元测试框架 第19章 QML编程基础 第20章 QML动画特效 第21章 Qt Quick Controls开发基础 第22章 Qt Quick Controls...
本书内容全面、实用,讲解通俗易懂,适合没有Qt编程基础、有Qt编程基础但是没有形成知识框架以及想学习Qt某一方面应用的读者,也适合想从Qt4跨入Qt5编程的读者。对于想学习QML及QtQuick编程的读者,可以学习《Qt5 编程...
二十、Qt 2D绘图(十)图形视图框架简介 二十一、Qt数据库(一)简介 二十二、Qt数据库(二)添加MySQL数据库驱动插件 二十三、Qt数据库(三)利用QSqlQuery类执行SQL语句(一) 二十四、Qt数据库(四)利用...
Qt技术是一套强大的跨平台应用程序开发框架,专注于使用C++语言来构建高性能、高可维护... Qt拥有活跃的开发者社区、丰富的文档资源、示例代码库以及商业支持选项,为开发者的学习、问题解决和项目实施提供了坚实后盾。
本书内容全面、实用,讲解通俗易懂,适合没有Qt编程基础、有Qt编程基础但是没有形成知识框架以及想学习Qt某一方面应用的读者,也适合想从Qt4跨入Qt5编程的读者。对于想学习QML及QtQuick编程的读者,可以学习《Qt5 编程...
本书的内容全面、实用,讲解通俗易懂,适合没有Qt编程基础、有Qt编程基础但是没有形成知识框架以及想学习Qt某一方面应用的读者。对于想进一步学习Qt开发实例或者Qt Quick的读者,可以学习《Qt及Qt Quick开发实战精解...
对于Qt Quick中的关键主题,如动画、Model-View、Component、网络、多媒体,做了详尽入微的讲解,让读者一册在手,别无他求;QML与C++混合编程、Canvas、定制及自定义控件等高级主题,《Qt Quick核心编程》也做了...
Graphics View Framework ...Graphics View Framework 还提供了方便的方法来处理事件、选择图形项、执行动画、导出图形为图片等功能。你可以根据需要继承 QGraphicsItem 或 QGraphicsWidget 类来创建自定义的图形项。
采用Qt框架编写,以嵌入式ARM Linux系统作为软件运行平台。 Qt技术是一套强大的跨平台... Qt拥有活跃的开发者社区、丰富的文档资源、示例代码库以及商业支持选项,为开发者的学习、问题解决和项目实施提供了坚实后盾。
Qt技术是一套强大的跨平台应用程序开发框架,专注于使用C++语言来构建高性能、高可维护... Qt拥有活跃的开发者社区、丰富的文档资源、示例代码库以及商业支持选项,为开发者的学习、问题解决和项目实施提供了坚实后盾。
对于Qt Quick中的关键主题,如动画、Model-View、Component、网络、多媒体,做了详尽入微的讲解,让读者一册在手,别无他求;QML与C++混合编程、Canvas、定制及自定义控件等高级主题,《Qt Quick核心编程》也做了...
Qt中可以实现QPropertyAnimation属性动画,动画效果流畅自然,通过对相应的属性参数进行修改,就可以实现诸如大小位置变化的动画。其中内置了多种插值曲线,可以对属性参数进行流畅的变化。对每个场景开始时对每个...
Qt技术是一套强大的跨平台应用程序开发框架,专注于使用C++语言来构建高性能、高可维护... Qt拥有活跃的开发者社区、丰富的文档资源、示例代码库以及商业支持选项,为开发者的学习、问题解决和项目实施提供了坚实后盾。
以及Qt在图形动画、影音媒体、数据处理和网络通信方面的应用内容,Qt Creator快速入门第3版内容全面、实用,讲解通俗易懂,适合没有Qt编程基础、有Qt编程基础但是没有形成知识框架以及想学习Qt某一方面应用的读者。...
Qt技术是一套强大的跨平台应用程序开发框架,专注于使用C++语言来构建高性能、高可维护... Qt拥有活跃的开发者社区、丰富的文档资源、示例代码库以及商业支持选项,为开发者的学习、问题解决和项目实施提供了坚实后盾。