青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

posts - 311, comments - 0, trackbacks - 0, articles - 0
  C++博客 :: 首頁 :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

英文原文: http://test.ogitor.org/tiki/AnimationBlender

動畫混合 -- 實現(xiàn)兩個動畫的切換, 一個動畫逐漸消逝, 另一個動畫逐漸顯示來實現(xiàn). 主要通過動畫狀態(tài)的權(quán)重來實現(xiàn)
通過三種方式來實現(xiàn)兩個動畫的混合:
    - BlendSwitch - 直接切換至目標動畫
    - BlendWhileAnimating - 混合的過程中目標動畫也更新幀, 實現(xiàn)動畫
    - BlendThenAnimate - 用源動畫的當前幀混合目標動畫的第一個幀

源碼理解, 主要代碼位于下面兩個函數(shù)
AnimationBlender::blend函數(shù) 根據(jù)傳入的參數(shù)設(shè)置新轉(zhuǎn)換的源動畫和目標動畫
AnimationBlender::add函數(shù)則更新源動畫和目標動畫(如存在)的狀態(tài)和權(quán)重

AnimationBlender::blend函數(shù)
1. 如果動畫轉(zhuǎn)換類型為 AnimationBlender::BlendSwitch
    直接將源動畫轉(zhuǎn)換成目標動畫
2. 如果不是這個轉(zhuǎn)換類型 AnimationBlender::BlendSwitch
    如果上次的動畫轉(zhuǎn)換還未完成
        如果新的目標動畫等于上次轉(zhuǎn)換的源動畫
            則反向轉(zhuǎn)換
        如果新的目標動畫不等于上次轉(zhuǎn)換的源動畫和目標動畫
            根據(jù)上次轉(zhuǎn)換的剩余時間設(shè)置是顯示上次轉(zhuǎn)換的源動畫還是目標動畫, 并將其設(shè)置為新轉(zhuǎn)換的源動畫
            顯示新轉(zhuǎn)換的目標動畫, 并設(shè)置其權(quán)重
    假設(shè)上次的動畫轉(zhuǎn)換已經(jīng)完成了轉(zhuǎn)換
        設(shè)置轉(zhuǎn)換時間, 轉(zhuǎn)換類型, 目標動畫和其權(quán)重

AnimationBlender::addTime 函數(shù)
1. 如有動畫在運行
    如果存在轉(zhuǎn)換
        更新剩余時間
            如剩余時間小于0
                禁止源動畫
                將目標動畫設(shè)置為源動畫, 繼續(xù)運行
            如剩余時間不小于0
                更新源動畫和目標動畫的權(quán)重
                如轉(zhuǎn)換類型為AnimationBlender::BlendWhileAnimating
                    更新目標動畫
    判斷動畫是否完成
        更新源動畫

完整代碼和Demo代碼

AnimationBlender.h

 

#ifndef __ANIMATION_BLENDER_H__   
#define __ANIMATION_BLENDER_H__   
#include 
<Ogre.h>   
using namespace Ogre;   
class AnimationBlender   
{   
public:   
    
enum BlendingTransition   
    {   
        BlendSwitch,         
// stop source and start dest   
        BlendWhileAnimating,   // cross fade, blend source animation out while blending destination animation in   
        BlendThenAnimate      // blend source to first frame of dest, when done, start dest anim   
    };   
private:   
    Entity 
*mEntity;   
    AnimationState 
*mSource;   
    AnimationState 
*mTarget;   
    BlendingTransition mTransition;   
    
bool loop;   
    
~AnimationBlender() {}   
public:    
    Real mTimeleft, mDuration;   
    
bool complete;   
    
void blend( const String &animation, BlendingTransition transition, Real duration, bool l=true );   
    
void addTime( Real );   
    Real getProgress() { 
return mTimeleft/ mDuration; }   
    AnimationState 
*getSource() { return mSource; }   
    AnimationState 
*getTarget() { return mTarget; }   
    AnimationBlender( Entity 
*);   
    
void init( const String &animation, bool l=true );   
};   
#endif 

AnimationBlender.cpp

#include "AnimationBlender.h"   
void AnimationBlender::init(const String &animation, bool l)   
{   
    
// 初始化, 將所有的動畫禁止, 只允許參數(shù)中的動畫運行.   
    AnimationStateSet *set = mEntity->getAllAnimationStates();   
    AnimationStateIterator it 
= set->getAnimationStateIterator();   
    
while(it.hasMoreElements())   
    {   
        AnimationState 
*anim = it.getNext();   
        anim
->setEnabled(false);   
        anim
->setWeight(0);   
        anim
->setTimePosition(0);   
    }   
    mSource 
= mEntity->getAnimationState( animation );   
    mSource
->setEnabled(true);   
    mSource
->setWeight(1);   
    mTimeleft 
= 0;   
    mDuration 
= 1;   
    mTarget 
= 0;   
    complete 
= false;   
    loop 
= l;   
}    
void AnimationBlender::blend( const String &animation, BlendingTransition transition, Real duration, bool l )   
{   
    loop 
= l;   
    
if( transition == AnimationBlender::BlendSwitch )   
    {   
        
if( mSource != 0 )   
            mSource
->setEnabled(false);   
        mSource 
= mEntity->getAnimationState( animation );   
        mSource
->setEnabled(true);   
        mSource
->setWeight(1);   
        mSource
->setTimePosition(0);   
        mTimeleft 
= 0;   
    }    
    
else    
    {    
        AnimationState 
*newTarget = mEntity->getAnimationState( animation );   
        
if( mTimeleft > 0 )   
        {   
            
// oops, weren't finished yet   
            if( newTarget == mTarget )   
            {   
                
// nothing to do! (ignoring duration here)   
            }   
            
else if( newTarget == mSource )   
            {   
                
// going back to the source state, so let's switch   
                mSource = mTarget;   
                mTarget 
= newTarget;   
                mTimeleft 
= mDuration - mTimeleft; // i'm ignoring the new duration here   
            }   
            
else  
            {   
                
// ok, newTarget is really new, so either we simply replace the target with this one, or   
                
// we make the target the new source   
                if( mTimeleft < mDuration * 0.5 )   
                {   
                    
// simply replace the target with this one   
                    mTarget->setEnabled(false);   
                    mTarget
->setWeight(0);   
                }   
                
else  
                {   
                    
// old target becomes new source   
                    mSource->setEnabled(false);   
                    mSource
->setWeight(0);   
                    mSource 
= mTarget;   
                }    
                mTarget 
= newTarget;   
                mTarget
->setEnabled(true);   
                mTarget
->setWeight( 1.0 - mTimeleft / mDuration );   
                mTarget
->setTimePosition(0);   
            }   
        }   
        
else  
        {   
            
// assert( target == 0, "target should be 0 when not blending" )   
            
// mSource->setEnabled(true);   
            
// mSource->setWeight(1);   
            mTransition = transition;   
            mTimeleft 
= mDuration = duration;   
            mTarget 
= newTarget;   
            mTarget
->setEnabled(true);   
            mTarget
->setWeight(0);   
            mTarget
->setTimePosition(0);   
        }   
    }   
}   
void AnimationBlender::addTime( Real time )   
{   
    
if( mSource != 0 )   
    {   
        
if( mTimeleft > 0 )   
        {   
            mTimeleft 
-= time;   
            
if( mTimeleft < 0 )   
            {   
                
// finish blending   
                mSource->setEnabled(false);   
                mSource
->setWeight(0);   
                mSource 
= mTarget;   
                mSource
->setEnabled(true);   
                mSource
->setWeight(1);   
                mTarget 
= 0;   
            }   
            
else  
            {   
                
// still blending, advance weights   
                mSource->setWeight(mTimeleft / mDuration);   
                mTarget
->setWeight(1.0 - mTimeleft / mDuration);   
                
if(mTransition == AnimationBlender::BlendWhileAnimating)   
                    mTarget
->addTime(time);   
            }   
        }   
        
if (mSource->getTimePosition() >= mSource->getLength())   
        {   
            complete 
= true;   
        }   
        
else  
        {   
            complete 
= false;   
        }   
        mSource
->addTime(time);   
        mSource
->setLoop(loop);   
    }   
}   
AnimationBlender::AnimationBlender( Entity 
*entity ) : mEntity(entity)    
{   

AnimationBlenderDemo.h

#ifndef __ANIMATIONBLENDER_DEMO_H__   
#define __ANIMATIONBLENDER_DEMO_H__   
#include 
"ExampleApplication.h"   
#include 
"AnimationBlender.h"   
class AnimationBlenderDemoFrameListener : public ExampleFrameListener   
{   
protected:   
    Entity
* mNinjaEnt;   
    AnimationBlender
* mAnimationBlender;   
    
bool walking, jumping;   
public:   
    AnimationBlenderDemoFrameListener(RenderWindow
* mWin, Camera* mCam, Entity* ent)   
        : ExampleFrameListener(mWin, mCam, 
falsefalse), mNinjaEnt(ent)   
    {   
        mAnimationBlender 
= new AnimationBlender(mNinjaEnt);   
        mAnimationBlender
->init("Walk"true);   
        walking 
= false;   
        jumping 
= false;   
    }   
    
virtual ~AnimationBlenderDemoFrameListener()   
    {   
        
if(mAnimationBlender)   
        {   
//          delete mAnimationBlender;   
        }   
    }   
    
bool frameRenderingQueued(const FrameEvent& evt)   
    {   
        
if (!ExampleFrameListener::frameRenderingQueued(evt))   
        {   
            
return false;   
        }   
        
if (!walking)   
        {   
            mAnimationBlender
->blend( "Walk",AnimationBlender::BlendWhileAnimating, 0.2true );   
            walking
=true;   
        }   
        
if (mKeyboard->isKeyDown( OIS::KC_SPACE ) && !jumping)   
        {   
            jumping
=true;   
            mAnimationBlender
->blend("Jump",AnimationBlender::BlendWhileAnimating, 0.2false );   
        }   
        
if (jumping)   
        {   
            
if (mAnimationBlender->complete)   
            {   
                mAnimationBlender
->blend( "Idle1",AnimationBlender::BlendWhileAnimating, 0.02true );   
                jumping
=false;   
            }   
        }   
        mAnimationBlender
->addTime(evt.timeSinceLastFrame);   
        
return true;   
    }   
};   
class AnimationBlenderDemoApp : public ExampleApplication   
{   
public:   
    AnimationBlenderDemoApp() {}   
protected:   
    Entity
* mNinjaEnt;   
    
void createScene();   
    
void createFrameListener()   
    {   
        mFrameListener 
= new AnimationBlenderDemoFrameListener(mWindow, mCamera, mNinjaEnt);   
        mRoot
->addFrameListener(mFrameListener);   
    }   
};   
#endif  


AnimationBlenderDemo.cpp

#include "AnimationBlenderDemo.h"   
#include <OgreStringConverter.h>   
void AnimationBlenderDemoApp::createScene()   
{   
    mSceneMgr->setAmbientLight(ColourValue(1.0, 1.0, 1.0));   
    mNinjaEnt = mSceneMgr->createEntity("Ninja", "ninja.mesh");   
    SceneNode* node = mSceneMgr->getRootSceneNode()->createChildSceneNode();   
    node->attachObject(mNinjaEnt);   
}   
#ifdef __cplusplus   
extern "C" {   
#endif   
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32   
#define WIN32_LEAN_AND_MEAN   
#include "windows.h"   
    INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR strCmdLine, INT )   
#else   
    int main(int argc, char **argv)   
#endif   
    {   
        AnimationBlenderDemoApp app;   
        try {   
            app.go();   
        } catch( Ogre::Exception& e ) {   
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32   
            MessageBox( NULL, e.getFullDescription().c_str(), "An exception has occured!", MB_OK | MB_ICONERROR | MB_TASKMODAL );   
#else   
            std::cerr << "An exception has occured: " << e.getFullDescription();   
#endif   
        }   
        return 0;   
    }   
#ifdef __cplusplus   
}   
#endif  
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            久久久久久噜噜噜久久久精品| 欧美一区二区视频免费观看| 国产专区精品视频| 亚洲黄色小视频| 国产亚洲精品一区二区| 日韩一级欧洲| 亚洲第一精品夜夜躁人人躁 | 久久综合激情| 国产精品免费视频xxxx| 亚洲美女淫视频| 亚洲人成人77777线观看| 久久电影一区| 久久久久91| 好男人免费精品视频| 亚洲欧美日韩中文在线制服| 亚洲在线中文字幕| 欧美午夜在线观看| 一二三区精品福利视频| 亚洲午夜精品久久久久久app| 欧美国产视频在线| 美女黄色成人网| 久久尤物视频| 激情小说另类小说亚洲欧美| 欧美亚洲综合另类| 久久色中文字幕| 伊人久久亚洲热| 另类天堂av| 亚洲激情影院| 亚洲午夜久久久久久久久电影网| 欧美日韩亚洲91| 亚洲视频导航| 久久久.com| 在线成人免费观看| 欧美电影免费观看高清完整版| 亚洲国产精品日韩| 亚洲少妇一区| 国产精一区二区三区| 欧美一区二区三区免费观看| 久久综合狠狠综合久久综合88| 伊大人香蕉综合8在线视| 久久综合久久综合久久综合| 亚洲国产精品一区制服丝袜| 亚洲无限乱码一二三四麻| 国产精品久久久久久福利一牛影视| 亚洲尤物在线视频观看| 久久视频在线视频| 亚洲理论在线观看| 国产精品久久久久免费a∨大胸| 午夜性色一区二区三区免费视频| 免费视频一区| 亚洲图片欧美午夜| 国产一区二区主播在线| 老牛国产精品一区的观看方式| 亚洲精品视频免费观看| 久久国产黑丝| 亚洲三级毛片| 国产欧美日韩综合一区在线观看| 久久亚洲综合网| 一本到12不卡视频在线dvd| 久久www成人_看片免费不卡| 亚洲激情成人在线| 国产精品有限公司| 欧美成人小视频| 欧美亚洲一级| 日韩视频在线你懂得| 久久亚洲风情| 午夜精品视频一区| 亚洲激情综合| 午夜在线电影亚洲一区| 亚洲国产清纯| 国产噜噜噜噜噜久久久久久久久| 欧美成人第一页| 欧美一级大片在线免费观看| 日韩亚洲欧美高清| 欧美sm视频| 久久国内精品自在自线400部| 99视频一区二区三区| 狠狠色丁香久久婷婷综合丁香| 欧美日韩亚洲视频| 欧美1区免费| 久久国产精品99国产精| 一本色道久久综合狠狠躁篇的优点| 毛片精品免费在线观看| 欧美一区二区大片| 亚洲综合第一| 亚洲素人一区二区| 亚洲精品综合精品自拍| 亚洲第一搞黄网站| 国产一区激情| 国产欧美日韩在线观看| 欧美视频四区| 欧美日韩精品福利| 欧美成人综合网站| 欧美aⅴ99久久黑人专区| 久久国产主播| 欧美一区激情| 亚洲欧美一区二区精品久久久| 亚洲最新在线| 日韩一区二区福利| 亚洲人体影院| 亚洲精品在线免费观看视频| 亚洲第一黄色| 亚洲电影免费观看高清完整版在线| 美女网站久久| 欧美**人妖| 欧美福利电影在线观看| 欧美激情视频在线播放 | 久久久福利视频| 欧美怡红院视频一区二区三区| 亚洲欧美日韩人成在线播放| 亚洲欧美不卡| 久久不射电影网| 久久久亚洲高清| 老色批av在线精品| 欧美成人午夜激情| 欧美剧在线免费观看网站| 欧美连裤袜在线视频| 欧美日韩国产页| 国产精品v日韩精品| 国产精品视频福利| 国产午夜亚洲精品不卡| 极品日韩久久| 日韩网站在线观看| 一区二区三区四区精品| 销魂美女一区二区三区视频在线| 欧美在线一二三| 牛牛国产精品| 亚洲美女性视频| 午夜精品免费| 噜噜噜91成人网| 欧美午夜宅男影院在线观看| 国产欧美精品xxxx另类| 在线日韩日本国产亚洲| 一本色道久久综合亚洲精品小说| 亚洲在线视频观看| 乱码第一页成人| 日韩一二三区视频| 欧美一区二区三区在线看| 免费亚洲一区| 国产精品永久免费在线| 亚洲国产精品成人| 亚洲欧美精品在线| 欧美 日韩 国产在线| 99视频一区二区三区| 久久成人久久爱| 欧美日韩国产专区| 国内精品久久久久久久果冻传媒 | 一区二区成人精品 | 国产网站欧美日韩免费精品在线观看| 国产一区二区中文| 一区二区精品国产| 久久久久久亚洲精品杨幂换脸 | 亚洲少妇在线| 另类综合日韩欧美亚洲| 一区二区三区四区五区视频 | 亚洲第一在线综合网站| 亚洲在线播放电影| 欧美多人爱爱视频网站| 亚洲欧美一区二区视频| 欧美区在线播放| 尹人成人综合网| 午夜天堂精品久久久久| 91久久久国产精品| 久久国内精品自在自线400部| 欧美日韩在线一区| 亚洲人成网在线播放| 久久久亚洲高清| 亚洲制服av| 欧美视频在线观看免费| 亚洲精品日韩综合观看成人91| 久久精品夜色噜噜亚洲aⅴ| 中文在线资源观看网站视频免费不卡 | 国产精品久久久久久久浪潮网站| 亚洲三级免费观看| 免费日韩精品中文字幕视频在线| 午夜久久久久久| 国产精品日韩精品| 亚洲一区免费在线观看| 亚洲日本成人在线观看| 欧美国产成人精品| 亚洲动漫精品| 米奇777在线欧美播放| 欧美制服第一页| 国产日韩精品在线播放| 欧美呦呦网站| 欧美亚洲综合另类| 国产精品影院在线观看| 性高湖久久久久久久久| 亚洲在线播放电影| 国产精品免费观看视频| 香蕉亚洲视频| 午夜精品久久一牛影视| 国产性做久久久久久| 欧美专区在线观看| 久久国产精品高清| 好看的av在线不卡观看| 老色鬼久久亚洲一区二区| 久久久久久久综合色一本| 亚洲电影在线免费观看| 亚洲第一在线视频|