Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Animation API #91

Closed
cart opened this issue Aug 5, 2020 · 14 comments
Closed

Animation API #91

cart opened this issue Aug 5, 2020 · 14 comments
Labels
A-Assets Load files from disk to use for things like images, models, and sounds A-Rendering Drawing game state to the screen C-Feature A new feature, making something new possible

Comments

@cart
Copy link
Member

cart commented Aug 5, 2020

Animation permeates almost everything in gamedev. First, we should add a general purpose code-first animation system. Then later we can add a property-based timeline system that can be saved to a config file and visualized / edited in the Bevy Editor.

@cart cart mentioned this issue Aug 5, 2020
@karroffel karroffel added A-Assets Load files from disk to use for things like images, models, and sounds C-Feature A new feature, making something new possible A-Rendering Drawing game state to the screen labels Aug 12, 2020
@JonahPlusPlus
Copy link
Contributor

I think a good place to start would be interpolation. The minterpolate crate provides a nice set of functions for interpolation. It shouldn't be hard to add an interface for it, and could be later expanded to the timeline system you have in mind.

@JonahPlusPlus
Copy link
Contributor

Looking at minterpolate and interpolation, minterpolate provides more interpolation functions and a common interface between them, which is nice when swapping out functions on the fly.

However, it adds the mint crate, which is unnecessary unless using multiple math crates. It is possible to make a fork and remove the mint sections, or ask the author to make it a crate feature, however the last update was 2 years ago, so it might not be maintained.

But the benefit of using it would be that animations sets can easily be added. The only drawbacks I could think of is that it might be a hassle when working in an animation set where the interpolation function differs between values.

Fortunately, both issues could be fixed by implementing all the features and more into the bevy_animation crate. The mint types could be removed, and a new MixedFunction variant could be added to the IterpolationFunction enum. TheMixedFunction could be constructed to take any number of interpolation functions and ranges, including more MixedFunctions, allowing the interpolation function to change over the entire set.

Hope this wasn't too long, it's just great to see such a great project.

@JonahPlusPlus
Copy link
Contributor

Looking into glam-rs, it also uses the mint crate. It probably doesn't need to be removed.

@kirawi
Copy link

kirawi commented Nov 11, 2020

Relatively, how far down on the roadmap is this?

@razaamir
Copy link

razaamir commented Nov 11, 2020 via email

@DrewRidley
Copy link

I am quite new to Bevy but perhaps this might be useful.

https://github.com/openrr/k

Inverse and Forward kinematics library for rust that seems stable, well documented, and pretty fast from my initial benchmarking. Let me know what you think.

@alice-i-cecile
Copy link
Member

We have a solid start on this in #1429 and another starting point to look at in #482.

@EvoTeamDevelop
Copy link

Maybe it would be easier to integration already existing solutions like https://rive.app/
I know that Defold game engine also is in the middle of its integration.

@Type1J
Copy link

Type1J commented Oct 8, 2021

The crates mentioned, so far, seem to lack sequences, easing, or keeps the easing functions built-in, while user defined functions are second class.

I haven't seen a mention of keyframe, yet. As animation foundations go, keyframe is pretty complete. I could see a UI in an editor being built using it as a foundation with seperate tracks, etc. functioning pretty well.

It also brings in mint, but given mint's purpose (being a common set of types for 3D linear algebra for interop with various crates and engines), I don't believe that to be a problem.

I'm not familiar with Rive, but I believe keyframe would ease the import of Rive assets, as well, given its capabilities.

Please take a look at keyframe. I invite persuasion to use another crate, if you find it superior.

@parasyte
Copy link
Contributor

I think one of the troubles with keyframe is that it owns its easing functions. Working with easings/interpolation on their own means one of two things will happen:

  • Add a dependency on keyframe to use only its interpolation functions. Strange, but fine if other parts of your app also make direct use of keyframe. No interoperability issues.
  • Depend on something else for interpolations. More purpose-driven, but duplicates code and possibly produces different results (or results of varying quality) compared to other parts of the app that use keyframe. Interoperability would be bad at best or non-existent at worst.

Honestly this is a small concern, because it's a tiny crate. But I'm calling it out because I would personally never search for an interpolation crate with keywords like keyframe or sequence, so I would land in the latter case.

@Type1J
Copy link

Type1J commented Nov 28, 2021

Actually, it doesn't own them. That was a major concern of mine, and one of the reasons that I landed on this library for a few projects. It has a trait defined as:

pub trait EasingFunction {
	/// For an X position on the curve, calculate the Y position.
	/// 0.0-1.0 is start and end on both axes but values can go out of bounds.
	///
	/// # Note
	///
	/// Because this method has a `&self` argument this trait can be used to both implement a "static" curve function (e.g. a linear interpolation)
	/// or a "dynamic" curve function (e.g. a bezier curve with user defined inputs).
	///
	/// Since a static curve function will have zero size the size of a `dyn EasingFunction` will be the same size as a vtable.
	/// This also means you can specify a static curve function with only the name of the type (e.g. `ease(EaseInOut, 0.0, 1.0, 0.5)`).
	fn y(&self, x: f64) -> f64;
}

You can pass it any type that implements this trait.

@parasyte
Copy link
Contributor

I was talking about the actual implementations. I understand that one can implement any conceivable interpolation function and use it with the trait. That wasn't the concern I raised.

@lygamac
Copy link

lygamac commented Dec 4, 2021

Just curious about how is going to be the final design of the animation system in code. I really like the code-first concept, as editor-based animations are less flexible.

Will the design be similar to Godot's animation API (deprecated, now it seems to be an editor resource)? Such design is based on functions, and it's really difficult to manipulate and understand through the code in a big project. Rather, it's meant to be used in an editor.

Is it possible to achieve a nested function list feature like in Lua? I made up this example:

animation_list = {
	{ "anim1", "path_to_animation"},
	{ "anim2", "path_to_animation"},
	-- ... etc
}

animation_player(function(s)
	node = animation.states {
		fade_time = 0.3,
		states = {
			state1 = "path_to_animation",
			state2 = animation.blend {
				blend1 = "path_to_animation",
				blend2 = animation.states {states = animation_list}
				-- etc
			},
		},
	}
	end)

Which is literary a code-based node tree to a Godot equivalent:
image

@cart
Copy link
Member Author

cart commented Feb 23, 2022

Closing in favor of #4026

@cart cart closed this as completed Feb 23, 2022
hymm referenced this issue in hymm/bevy Jan 26, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-Assets Load files from disk to use for things like images, models, and sounds A-Rendering Drawing game state to the screen C-Feature A new feature, making something new possible
Projects
None yet
Development

No branches or pull requests