fyrox_animation/machine/node/
play.rsuse crate::{
core::{
pool::{Handle, Pool},
reflect::prelude::*,
visitor::prelude::*,
},
machine::{
node::AnimationEventCollectionStrategy,
node::{AnimationPoseSource, BasePoseNode},
ParameterContainer, PoseNode,
},
Animation, AnimationContainer, AnimationEvent, AnimationPose, EntityId,
};
use std::{
cell::{Ref, RefCell},
ops::{Deref, DerefMut},
};
#[derive(Default, Debug, Visit, Clone, Reflect, PartialEq)]
pub struct PlayAnimation<T: EntityId> {
pub base: BasePoseNode<T>,
pub animation: Handle<Animation<T>>,
#[visit(skip)]
#[reflect(hidden)]
pub output_pose: RefCell<AnimationPose<T>>,
}
impl<T: EntityId> Deref for PlayAnimation<T> {
type Target = BasePoseNode<T>;
fn deref(&self) -> &Self::Target {
&self.base
}
}
impl<T: EntityId> DerefMut for PlayAnimation<T> {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.base
}
}
impl<T: EntityId> PlayAnimation<T> {
pub fn new(animation: Handle<Animation<T>>) -> Self {
Self {
base: Default::default(),
animation,
output_pose: Default::default(),
}
}
}
impl<T: EntityId> AnimationPoseSource<T> for PlayAnimation<T> {
fn eval_pose(
&self,
_nodes: &Pool<PoseNode<T>>,
_params: &ParameterContainer,
animations: &AnimationContainer<T>,
_dt: f32,
) -> Ref<AnimationPose<T>> {
if let Some(animation) = animations.try_get(self.animation) {
let mut output_pose = self.output_pose.borrow_mut();
animation.pose().clone_into(&mut output_pose);
output_pose.set_root_motion(animation.root_motion().cloned());
}
self.output_pose.borrow()
}
fn pose(&self) -> Ref<AnimationPose<T>> {
self.output_pose.borrow()
}
fn collect_animation_events(
&self,
_nodes: &Pool<PoseNode<T>>,
_params: &ParameterContainer,
animations: &AnimationContainer<T>,
_strategy: AnimationEventCollectionStrategy,
) -> Vec<(Handle<Animation<T>>, AnimationEvent)> {
animations
.try_get(self.animation)
.map(|a| {
a.events_ref()
.iter()
.map(|e| (self.animation, e.clone()))
.collect()
})
.unwrap_or_default()
}
}