Crate bevy_easings

Source
Expand description

§Bevy Easings

MIT/Apache 2.0 Doc Crate Bevy Tracking CI

Easings on Bevy components using interpolation.

menu example

§Usage

§System setup

Add the plugin to your app:

use bevy::prelude::*;
use bevy_easings::EasingsPlugin;

fn main() {
    App::new()
        .add_plugins(EasingsPlugin::default());
}

§Easing a component to a new value

And then just ease your components to their new state!

use bevy::prelude::*;
use bevy_easings::Ease;

fn my_system(mut commands: Commands){
    commands
        .spawn((
            Sprite {
                ..Default::default()
            },
            Sprite {
                custom_size: Some(Vec2::new(10., 10.)),
                ..Default::default()
            }
            .ease_to(
                Sprite {
                    custom_size: Some(Vec2::new(100., 100.)),
                    ..Default::default()
                },
                bevy_easings::EaseFunction::QuadraticIn,
                bevy_easings::EasingType::PingPong {
                    duration: std::time::Duration::from_secs(1),
                    pause: Some(std::time::Duration::from_millis(500)),
                },
            ),
        ));
}

If the component being eased is not already a component of the entity, the component should first be inserted for the target entity.

§Easing to a function-generated target

You can also ease to a target that is generated dynamically from the previous value using a function:

use bevy::prelude::*;
use bevy_easings::Ease;

fn my_system(mut commands: Commands){
    commands
        .spawn((
            Transform::from_scale(Vec3::new(0.1, 0.1, 1.0))
            .ease_to_fn(
                |start| Transform {
                    scale: start.scale * 10.0,
                    ..*start
                },
                bevy_easings::EaseFunction::QuadraticIn,
                bevy_easings::EasingType::PingPong {
                    duration: std::time::Duration::from_secs(1),
                    pause: Some(std::time::Duration::from_millis(500)),
                },
            )
            .ease_to_fn(
                |prev| Transform {
                    scale: prev.scale * 0.5,
                    ..*prev
                },
                bevy_easings::EaseFunction::CubicInOut,
                bevy_easings::EasingType::Once {
                    duration: std::time::Duration::from_secs(2),
                },
            ).with_original_value(),
        ));
}

This is particularly useful to rescue you from repeatly writing initialize code for start status, or chaining animation without worrying about maintaining interior status.

§Easing using EaseMethod

The EaseMethod enum can be used to provide easing methods that are not avaliable in EaseFunction.

pub enum EaseMethod {
    /// Follow `EaseFunction`
    EaseFunction(EaseFunction),
    /// Linear interpolation, with no function
    Linear,
    /// Discrete interpolation, eased value will jump from start to end
    Discrete,
    /// Use a custom function to interpolate the value
    CustomFunction(fn(f32) -> f32),
}

This is shown below

use bevy::prelude::*;
use bevy_easings::Ease;

fn my_system(mut commands: Commands){
    commands
        .spawn((
            Sprite {
                ..Default::default()
            },
            Sprite {
                custom_size: Some(Vec2::new(10., 10.)),
                ..Default::default()
            }
            .ease_to(
                Sprite {
                    custom_size: Some(Vec2::new(100., 100.)),
                    ..Default::default()
                },
                bevy_easings::EaseMethod::Linear,
                bevy_easings::EasingType::PingPong {
                    duration: std::time::Duration::from_secs(1),
                    pause: Some(std::time::Duration::from_millis(500)),
                },
            ),
        ));
}

§Chaining easing

You can chain easings, if they are not set to repeat they will happen in sequence.

use bevy::prelude::*;
use bevy_easings::Ease;

fn my_system(mut commands: Commands){
    commands
        .spawn((
            Sprite {
                ..Default::default()
            },
            Sprite {
                custom_size: Some(Vec2::new(10., 10.)),
                ..Default::default()
            }
            .ease_to(
                Sprite {
                    custom_size: Some(Vec2::new(300., 300.)),
                    ..Default::default()
                },
                bevy_easings::EaseFunction::QuadraticIn,
                bevy_easings::EasingType::Once {
                    duration: std::time::Duration::from_secs(1),
                },
            )
            .ease_to(
                Sprite {
                    custom_size: Some(Vec2::new(350., 350.)),
                    ..Default::default()
                },
                bevy_easings::EaseFunction::QuadraticIn,
                bevy_easings::EasingType::PingPong {
                    duration: std::time::Duration::from_millis(500),
                    pause: Some(std::time::Duration::from_millis(200)),
                },
            ),
        ));
}

§Custom component support

To be able to ease a component, it needs to implement the traits Default and Lerp. This trait is re-exported by beavy_easings.

use bevy::prelude::*;
use bevy_easings::*;

#[derive(Default, Component)]
struct CustomComponent(f32);
impl Lerp for CustomComponent {
    type Scalar = f32;

    fn lerp(&self, other: &Self, scalar: &Self::Scalar) -> Self {
        CustomComponent(interpolation::lerp(&self.0, &other.0, scalar))
    }
}

The basic formula for lerp (linear interpolation) is self + (other - self) * scalar.

Then, the system custom_ease_system::<CustomComponent> needs to be added to the application.

§Examples

See examples

§Choosing the ease function

easing on size

easing on color

When easing colors, pay attention on the color space you are using

color spaces

§Ease Functions

Many ease functions are available:

  • QuadraticIn
  • QuadraticOut
  • QuadraticInOut
  • CubicIn
  • CubicOut
  • CubicInOut
  • QuarticIn
  • QuarticOut
  • QuarticInOut
  • QuinticIn
  • QuinticOut
  • QuinticInOut
  • SineIn
  • SineOut
  • SineInOut
  • CircularIn
  • CircularOut
  • CircularInOut
  • ExponentialIn
  • ExponentialOut
  • ExponentialInOut
  • ElasticIn
  • ElasticOut
  • ElasticInOut
  • BackIn
  • BackOut
  • BackInOut
  • BounceIn
  • BounceOut
  • BounceInOut

§Bevy supported version

Bevybevy_easings
mainmain
0.160.16
0.150.15
0.140.14
0.130.14
0.120.12
0.110.11
0.100.10
0.90.9
0.80.8
0.70.7
0.60.6
0.50.4

Structs§

EaseValue
Wrapper around a type that can be eased.
EasingChainComponent
Component to control a chain of easing
EasingComponent
Component to control an easing
EasingsLabel
Label to coordinate new easing spawns
EasingsPlugin
Plugin to add systems related to easing

Enums§

EaseFunction
EaseMethod
Describe how eased value should be computed
EasingDirection
Direction of an easing. It can be backward with an EasingType::PingPong
EasingState
Control if an easing is played
EasingType
How should this easing loop repeat

Traits§

CustomComponentEase
Trait to mark custom component that can be eased. It will be automatically implemented if the custom component implement Lerp
Ease
Trait marking components that can be eased
Lerp
Describes a type that can linearly interpolate between two points.

Functions§

custom_ease_system
Ease system for custom component. Add this system to your application with your component as a type parameter.