1
0
mirror of https://github.com/rwengine/openrw.git synced 2024-09-20 09:21:44 +02:00
openrw/rwengine/include/engine/Animator.hpp

153 lines
3.6 KiB
C++
Raw Normal View History

2013-09-11 01:26:13 +02:00
#pragma once
#ifndef _ANIMATOR_HPP_
#define _ANIMATOR_HPP_
#include <glm/glm.hpp>
#include <glm/gtx/quaternion.hpp>
#include <queue>
#include <map>
#include <loaders/LoaderIFP.hpp>
2013-09-11 01:26:13 +02:00
#include <cstdint>
class Model;
2014-03-01 12:19:33 +01:00
class ModelFrame;
2013-09-11 01:26:13 +02:00
/**
* @brief calculates animation frame matrices, as well as procedural frame
* animation.
2013-09-11 01:26:13 +02:00
*/
class Animator
{
/**
* @brief _animations Queue of animations to play.
*/
std::queue<Animation*> _animations;
2013-09-11 01:26:13 +02:00
/**
* @brief model The model being animated.
*/
2013-09-11 01:26:13 +02:00
Model* model;
/**
* @brief Stores data required to animate a model frame
*/
struct FrameInstanceData {
bool visible;
AnimationBone* bone;
// Used if bone is non-null.
AnimationKeyframe first;
AnimationKeyframe second;
// Used if bone is null and entry exists.
glm::quat orientation;
/// Construct from animation data
FrameInstanceData(AnimationBone* bone, const AnimationKeyframe& a, const AnimationKeyframe& b)
: visible(true), bone(bone), first(a), second(b) {}
/// Construct from procedural data
FrameInstanceData(bool visible, const glm::quat& orientation = {})
: visible(visible), bone(nullptr), orientation(orientation) {}
};
std::map<ModelFrame*, FrameInstanceData> _frameInstances;
// Used in determining how far the skeleton being animated has moved
// From it's local origin.
2013-09-11 01:26:13 +02:00
glm::vec3 lastRootPosition;
glm::quat lastRootRotation;
float time;
float serverTime;
float lastServerTime;
bool playing;
2013-09-30 20:32:14 +02:00
bool repeat;
2013-09-11 01:26:13 +02:00
void reset();
public:
Animator();
/**
* @brief setAnimation Sets the currently active animation.
* @param animation
2013-09-30 20:32:14 +02:00
* @param repeat If true animation will restart after ending.
2013-09-11 01:26:13 +02:00
* @todo Interpolate between the new and old frames.
*/
2013-09-30 20:32:14 +02:00
void setAnimation(Animation* animation, bool repeat = true);
2013-09-11 01:26:13 +02:00
void queueAnimation(Animation* animation);
void next();
const std::queue<Animation*> getAnimationQueue() const
{ return _animations; }
const Animation* getAnimation() const
{ return _animations.empty() ? nullptr : _animations.front(); }
2013-09-11 01:26:13 +02:00
void setModel(Model* model);
void setFrameVisibility(ModelFrame* frame, bool visible);
bool getFrameVisibility(ModelFrame* frame) const;
2014-06-19 20:18:34 +02:00
void setFrameOrientation(ModelFrame* frame, const glm::quat& orientation);
glm::quat getFrameOrientation(ModelFrame* frame) const;
FrameInstanceData* getFrameInstance(ModelFrame* frame);
2014-03-01 12:19:33 +01:00
/**
* @brief getFrameMatrix returns the matrix for frame at the given time
2014-03-01 12:19:33 +01:00
* @param t
* @param frame
* @return
*/
glm::mat4 getFrameMatrixAt(ModelFrame* frame, float time, bool disableRoot = true) const;
AnimationKeyframe getKeyframeAt(ModelFrame* frame, float time) const;
glm::mat4 getFrameMatrix(ModelFrame* frame, float alpha = 0.f, bool ignoreRoot = true) const;
2014-03-01 12:19:33 +01:00
2013-09-11 01:26:13 +02:00
/**
* @brief tick Update animation paramters for server-side data.
* @param dt
*/
void tick(float dt);
/**
* @brief render Update frame matricies for client-side animation.
* @param dt
*/
void render(float dt);
/**
* @brief getRootTranslation Returns the translation of the root bone from the last server-side frame.
* @return
*/
glm::vec3 getRootTranslation() const;
2014-08-05 16:09:42 +02:00
/**
* @brief getDurationTransform returns the translation of the root bone over the duration of the animation.
* @return
*/
glm::vec3 getDurationTransform() const;
2013-09-11 01:26:13 +02:00
/**
* @brief getRootRotation see getRootTranslation
* @return
*/
glm::quat getRootRotation() const;
2013-10-02 02:27:48 +02:00
/**
* Returns true if the animation has finished playing.
*/
bool isCompleted() const;
2014-03-01 12:19:33 +01:00
float getAnimationTime(float alpha = 0.f) const;
void setAnimationTime(float time);
void setPlaying( bool play ) { playing = play; }
2013-09-11 01:26:13 +02:00
};
#endif