mirror of
https://github.com/kaosat-dev/Blender_bevy_components_workflow.git
synced 2024-11-22 20:00:53 +00:00
chore(): cargo fmt
This commit is contained in:
parent
2523691513
commit
49dd0bc536
@ -37,7 +37,7 @@ pub struct AnimationInfo {
|
|||||||
pub frame_end: f32,
|
pub frame_end: f32,
|
||||||
pub frames_length: f32,
|
pub frames_length: f32,
|
||||||
pub frame_start_override: f32,
|
pub frame_start_override: f32,
|
||||||
pub frame_end_override:f32
|
pub frame_end_override: f32,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Stores information about animations, to make things a bit easier api wise:
|
/// Stores information about animations, to make things a bit easier api wise:
|
||||||
@ -45,7 +45,7 @@ pub struct AnimationInfo {
|
|||||||
#[derive(Component, Reflect, Default, Debug)]
|
#[derive(Component, Reflect, Default, Debug)]
|
||||||
#[reflect(Component)]
|
#[reflect(Component)]
|
||||||
pub struct AnimationInfos {
|
pub struct AnimationInfos {
|
||||||
pub animations: Vec<AnimationInfo>
|
pub animations: Vec<AnimationInfo>,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct AnimationMarker {
|
pub struct AnimationMarker {
|
||||||
@ -59,7 +59,6 @@ pub struct AnimationMarker{
|
|||||||
#[reflect(Component)]
|
#[reflect(Component)]
|
||||||
pub struct AnimationMarkers(pub HashMap<String, HashMap<u32, Vec<String>>>);
|
pub struct AnimationMarkers(pub HashMap<String, HashMap<u32, Vec<String>>>);
|
||||||
|
|
||||||
|
|
||||||
// FIXME: ugh, ugly, there has to be a better way to do this ?
|
// FIXME: ugh, ugly, there has to be a better way to do this ?
|
||||||
#[derive(Component, Default, Debug)]
|
#[derive(Component, Default, Debug)]
|
||||||
pub struct AnimationMarkerTrackers(pub HashMap<String, HashMap<u32, Vec<AnimationMarkerTracker>>>);
|
pub struct AnimationMarkerTrackers(pub HashMap<String, HashMap<u32, Vec<AnimationMarkerTracker>>>);
|
||||||
@ -69,7 +68,7 @@ pub struct AnimationMarkerTracker{
|
|||||||
// pub frame:u32,
|
// pub frame:u32,
|
||||||
// pub name: String,
|
// pub name: String,
|
||||||
// pub processed_for_cycle: bool,
|
// pub processed_for_cycle: bool,
|
||||||
pub prev_frame: u32
|
pub prev_frame: u32,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Event that gets triggered once a specific marker inside an animation has been reached (frame based)
|
/// Event that gets triggered once a specific marker inside an animation has been reached (frame based)
|
||||||
|
@ -119,18 +119,15 @@ impl Plugin for BlueprintsPlugin {
|
|||||||
.register_type::<BlueprintName>()
|
.register_type::<BlueprintName>()
|
||||||
.register_type::<MaterialInfo>()
|
.register_type::<MaterialInfo>()
|
||||||
.register_type::<SpawnHere>()
|
.register_type::<SpawnHere>()
|
||||||
|
|
||||||
.register_type::<BlueprintAnimations>()
|
.register_type::<BlueprintAnimations>()
|
||||||
.register_type::<InstanceAnimations>()
|
.register_type::<InstanceAnimations>()
|
||||||
.register_type::<AnimationInfo>()
|
.register_type::<AnimationInfo>()
|
||||||
.register_type::<AnimationInfos>()
|
.register_type::<AnimationInfos>()
|
||||||
.register_type::<Vec<AnimationInfo>>()
|
.register_type::<Vec<AnimationInfo>>()
|
||||||
|
|
||||||
.register_type::<AnimationMarkers>()
|
.register_type::<AnimationMarkers>()
|
||||||
.register_type::<HashMap<u32, Vec<String>>>()
|
.register_type::<HashMap<u32, Vec<String>>>()
|
||||||
.register_type::<HashMap<String, HashMap<u32, Vec<String>>>>()
|
.register_type::<HashMap<String, HashMap<u32, Vec<String>>>>()
|
||||||
.add_event::<AnimationMarkerReached>()
|
.add_event::<AnimationMarkerReached>()
|
||||||
|
|
||||||
.register_type::<BlueprintsList>()
|
.register_type::<BlueprintsList>()
|
||||||
.register_type::<HashMap<String, Vec<String>>>()
|
.register_type::<HashMap<String, Vec<String>>>()
|
||||||
.insert_resource(BluePrintsConfig {
|
.insert_resource(BluePrintsConfig {
|
||||||
|
@ -2,7 +2,7 @@ use std::path::{Path, PathBuf};
|
|||||||
|
|
||||||
use bevy::{gltf::Gltf, prelude::*, utils::HashMap};
|
use bevy::{gltf::Gltf, prelude::*, utils::HashMap};
|
||||||
|
|
||||||
use crate::{BlueprintAnimations, BluePrintsConfig};
|
use crate::{BluePrintsConfig, BlueprintAnimations};
|
||||||
|
|
||||||
/// this is a flag component for our levels/game world
|
/// this is a flag component for our levels/game world
|
||||||
#[derive(Component)]
|
#[derive(Component)]
|
||||||
@ -281,9 +281,10 @@ pub(crate) fn spawn_from_blueprints(
|
|||||||
},
|
},
|
||||||
Spawned,
|
Spawned,
|
||||||
OriginalChildren(original_children),
|
OriginalChildren(original_children),
|
||||||
BlueprintAnimations { // these are animations specific to the inside of the blueprint
|
BlueprintAnimations {
|
||||||
|
// these are animations specific to the inside of the blueprint
|
||||||
named_animations: gltf.named_animations.clone(),
|
named_animations: gltf.named_animations.clone(),
|
||||||
}
|
},
|
||||||
));
|
));
|
||||||
|
|
||||||
if add_to_world.is_some() {
|
if add_to_world.is_some() {
|
||||||
|
@ -85,7 +85,9 @@ pub(crate) fn spawned_blueprint_post_process(
|
|||||||
// FIXME: stopgap solution: since we cannot use an AnimationPlayer at the root entity level
|
// FIXME: stopgap solution: since we cannot use an AnimationPlayer at the root entity level
|
||||||
// and we cannot update animation clips so that the EntityPaths point to one level deeper,
|
// and we cannot update animation clips so that the EntityPaths point to one level deeper,
|
||||||
// BUT we still want to have some marker/control at the root entity level, we add this
|
// BUT we still want to have some marker/control at the root entity level, we add this
|
||||||
commands.entity(original).insert(BlueprintAnimationPlayerLink(added));
|
commands
|
||||||
|
.entity(original)
|
||||||
|
.insert(BlueprintAnimationPlayerLink(added));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,12 +1,13 @@
|
|||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use bevy_gltf_blueprints::{AnimationInfos, AnimationMarkerReached, AnimationMarkerTrackers, AnimationMarkers, BlueprintAnimationPlayerLink, BlueprintAnimations, BlueprintName, BlueprintsList, GltfBlueprintsSet, InstanceAnimationPlayerLink, InstanceAnimations};
|
use bevy_gltf_blueprints::{
|
||||||
|
AnimationInfos, AnimationMarkerReached, AnimationMarkerTrackers, AnimationMarkers,
|
||||||
use bevy::{
|
BlueprintAnimationPlayerLink, BlueprintAnimations, BlueprintName, BlueprintsList,
|
||||||
gltf::Gltf, prelude::*
|
GltfBlueprintsSet, InstanceAnimationPlayerLink, InstanceAnimations,
|
||||||
};
|
};
|
||||||
use bevy_gltf_worlflow_examples_common_rapier::{AppState, GameState};
|
|
||||||
|
|
||||||
|
use bevy::{gltf::Gltf, prelude::*};
|
||||||
|
use bevy_gltf_worlflow_examples_common_rapier::{AppState, GameState};
|
||||||
|
|
||||||
#[derive(Component, Reflect, Default, Debug)]
|
#[derive(Component, Reflect, Default, Debug)]
|
||||||
#[reflect(Component)]
|
#[reflect(Component)]
|
||||||
@ -26,11 +27,7 @@ pub struct Marker3;
|
|||||||
#[derive(Resource)]
|
#[derive(Resource)]
|
||||||
pub struct AnimTest(Handle<Gltf>);
|
pub struct AnimTest(Handle<Gltf>);
|
||||||
|
|
||||||
|
pub fn setup_main_scene_animations(asset_server: Res<AssetServer>, mut commands: Commands) {
|
||||||
pub fn setup_main_scene_animations(
|
|
||||||
asset_server: Res<AssetServer>,
|
|
||||||
mut commands: Commands,
|
|
||||||
) {
|
|
||||||
commands.insert_resource(AnimTest(asset_server.load("models/World.glb")));
|
commands.insert_resource(AnimTest(asset_server.load("models/World.glb")));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -53,17 +50,20 @@ pub fn animations(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if matching_data {
|
if matching_data {
|
||||||
println!("inserting Animations components into {} ({:?})", name, entity);
|
println!(
|
||||||
println!("Found match {:?}", gltf.named_animations);
|
"inserting Animations components into {} ({:?})",
|
||||||
commands.entity(entity).insert(
|
name, entity
|
||||||
InstanceAnimations {
|
|
||||||
named_animations: gltf.named_animations.clone(),
|
|
||||||
},
|
|
||||||
);
|
);
|
||||||
|
println!("Found match {:?}", gltf.named_animations);
|
||||||
|
commands.entity(entity).insert(InstanceAnimations {
|
||||||
|
named_animations: gltf.named_animations.clone(),
|
||||||
|
});
|
||||||
for ancestor in parents.iter_ancestors(entity) {
|
for ancestor in parents.iter_ancestors(entity) {
|
||||||
if added_animation_players.contains(ancestor) {
|
if added_animation_players.contains(ancestor) {
|
||||||
// println!("found match with animationPlayer !! {:?}",names.get(ancestor));
|
// println!("found match with animationPlayer !! {:?}",names.get(ancestor));
|
||||||
commands.entity(entity).insert(InstanceAnimationPlayerLink(ancestor));
|
commands
|
||||||
|
.entity(entity)
|
||||||
|
.insert(InstanceAnimationPlayerLink(ancestor));
|
||||||
}
|
}
|
||||||
// info!("{:?} is an ancestor of {:?}", ancestor, player);
|
// info!("{:?} is an ancestor of {:?}", ancestor, player);
|
||||||
}
|
}
|
||||||
@ -73,13 +73,26 @@ pub fn animations(
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn play_animations(
|
pub fn play_animations(
|
||||||
animated_marker1: Query<(&InstanceAnimationPlayerLink, &InstanceAnimations), (With<AnimationInfos>, With<Marker1>)>,
|
animated_marker1: Query<
|
||||||
animated_marker2: Query<(&InstanceAnimationPlayerLink, &InstanceAnimations), (With<AnimationInfos>, With<Marker2>)>,
|
(&InstanceAnimationPlayerLink, &InstanceAnimations),
|
||||||
animated_marker3: Query<(&InstanceAnimationPlayerLink, &InstanceAnimations, &BlueprintAnimationPlayerLink, &BlueprintAnimations), (With<AnimationInfos>, With<Marker3>)>,
|
(With<AnimationInfos>, With<Marker1>),
|
||||||
|
>,
|
||||||
|
animated_marker2: Query<
|
||||||
|
(&InstanceAnimationPlayerLink, &InstanceAnimations),
|
||||||
|
(With<AnimationInfos>, With<Marker2>),
|
||||||
|
>,
|
||||||
|
animated_marker3: Query<
|
||||||
|
(
|
||||||
|
&InstanceAnimationPlayerLink,
|
||||||
|
&InstanceAnimations,
|
||||||
|
&BlueprintAnimationPlayerLink,
|
||||||
|
&BlueprintAnimations,
|
||||||
|
),
|
||||||
|
(With<AnimationInfos>, With<Marker3>),
|
||||||
|
>,
|
||||||
|
|
||||||
mut animation_players: Query<&mut AnimationPlayer>,
|
mut animation_players: Query<&mut AnimationPlayer>,
|
||||||
keycode: Res<ButtonInput<KeyCode>>,
|
keycode: Res<ButtonInput<KeyCode>>,
|
||||||
|
|
||||||
) {
|
) {
|
||||||
if keycode.just_pressed(KeyCode::KeyM) {
|
if keycode.just_pressed(KeyCode::KeyM) {
|
||||||
for (link, animations) in animated_marker1.iter() {
|
for (link, animations) in animated_marker1.iter() {
|
||||||
@ -190,10 +203,16 @@ pub fn play_animations(
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn trigger_event_based_on_animation_marker(
|
pub fn trigger_event_based_on_animation_marker(
|
||||||
animation_infos: Query<(Entity, &AnimationMarkers, &InstanceAnimationPlayerLink, &InstanceAnimations, &AnimationInfos)>,
|
animation_infos: Query<(
|
||||||
|
Entity,
|
||||||
|
&AnimationMarkers,
|
||||||
|
&InstanceAnimationPlayerLink,
|
||||||
|
&InstanceAnimations,
|
||||||
|
&AnimationInfos,
|
||||||
|
)>,
|
||||||
animation_players: Query<&AnimationPlayer>,
|
animation_players: Query<&AnimationPlayer>,
|
||||||
animation_clips: Res<Assets<AnimationClip>>,
|
animation_clips: Res<Assets<AnimationClip>>,
|
||||||
mut animation_marker_events: EventWriter<AnimationMarkerReached>
|
mut animation_marker_events: EventWriter<AnimationMarkerReached>,
|
||||||
) {
|
) {
|
||||||
for (entity, markers, link, animations, animation_infos) in animation_infos.iter() {
|
for (entity, markers, link, animations, animation_infos) in animation_infos.iter() {
|
||||||
let animation_player = animation_players.get(link.0).unwrap();
|
let animation_player = animation_players.get(link.0).unwrap();
|
||||||
@ -206,18 +225,30 @@ pub fn trigger_event_based_on_animation_marker(
|
|||||||
// println!("Player {:?} {}", animation_player.elapsed(), animation_player.completions());
|
// println!("Player {:?} {}", animation_player.elapsed(), animation_player.completions());
|
||||||
|
|
||||||
// FIMXE: yikes ! very inneficient ! perhaps add boilerplate to the "start playing animation" code so we know what is playing
|
// FIMXE: yikes ! very inneficient ! perhaps add boilerplate to the "start playing animation" code so we know what is playing
|
||||||
let animation_name = animations.named_animations.iter().find_map(|(key, value)| if value == animation_player.animation_clip(){ Some(key) }else { None});
|
let animation_name = animations.named_animations.iter().find_map(|(key, value)| {
|
||||||
|
if value == animation_player.animation_clip() {
|
||||||
|
Some(key)
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
}
|
||||||
|
});
|
||||||
if animation_name.is_some() {
|
if animation_name.is_some() {
|
||||||
let animation_name = animation_name.unwrap();
|
let animation_name = animation_name.unwrap();
|
||||||
|
|
||||||
let animation_length_seconds = animation_clip.unwrap().duration();
|
let animation_length_seconds = animation_clip.unwrap().duration();
|
||||||
let animation_length_frames = animation_infos.animations.iter().find(|anim| &anim.name == animation_name).unwrap().frames_length;
|
let animation_length_frames = animation_infos
|
||||||
|
.animations
|
||||||
|
.iter()
|
||||||
|
.find(|anim| &anim.name == animation_name)
|
||||||
|
.unwrap()
|
||||||
|
.frames_length;
|
||||||
// TODO: we also need to take playback speed into account
|
// TODO: we also need to take playback speed into account
|
||||||
let time_in_animation = animation_player.elapsed() - (animation_player.completions() as f32) * animation_length_seconds;
|
let time_in_animation = animation_player.elapsed()
|
||||||
let frame_seconds = (animation_length_frames as f32 / animation_length_seconds) * time_in_animation ;
|
- (animation_player.completions() as f32) * animation_length_seconds;
|
||||||
|
let frame_seconds =
|
||||||
|
(animation_length_frames as f32 / animation_length_seconds) * time_in_animation;
|
||||||
let frame = frame_seconds as u32;
|
let frame = frame_seconds as u32;
|
||||||
|
|
||||||
|
|
||||||
let matching_animation_marker = &markers.0[animation_name];
|
let matching_animation_marker = &markers.0[animation_name];
|
||||||
if matching_animation_marker.contains_key(&frame) {
|
if matching_animation_marker.contains_key(&frame) {
|
||||||
let matching_markers_per_frame = matching_animation_marker.get(&frame).unwrap();
|
let matching_markers_per_frame = matching_animation_marker.get(&frame).unwrap();
|
||||||
@ -229,20 +260,18 @@ pub fn trigger_event_based_on_animation_marker(
|
|||||||
entity: entity,
|
entity: entity,
|
||||||
animation_name: animation_name.clone(),
|
animation_name: animation_name.clone(),
|
||||||
frame: frame,
|
frame: frame,
|
||||||
marker_name: marker_name.clone()
|
marker_name: marker_name.clone(),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn react_to_animation_markers(
|
pub fn react_to_animation_markers(
|
||||||
mut animation_marker_events: EventReader<AnimationMarkerReached>
|
mut animation_marker_events: EventReader<AnimationMarkerReached>,
|
||||||
)
|
) {
|
||||||
{
|
|
||||||
for event in animation_marker_events.read() {
|
for event in animation_marker_events.read() {
|
||||||
println!("animation marker event {:?}", event)
|
println!("animation marker event {:?}", event)
|
||||||
}
|
}
|
||||||
|
@ -1,16 +1,19 @@
|
|||||||
pub mod in_game;
|
|
||||||
pub mod animation;
|
pub mod animation;
|
||||||
pub use in_game::*;
|
pub mod in_game;
|
||||||
pub use animation::*;
|
pub use animation::*;
|
||||||
|
pub use in_game::*;
|
||||||
|
|
||||||
use std::{
|
use std::{collections::HashMap, fs, time::Duration};
|
||||||
collections::HashMap, fs, time::Duration
|
|
||||||
|
use bevy_gltf_blueprints::{
|
||||||
|
AnimationInfos, AnimationMarkerReached, AnimationMarkerTrackers, AnimationMarkers,
|
||||||
|
BlueprintAnimationPlayerLink, BlueprintAnimations, BlueprintName, BlueprintsList,
|
||||||
|
GltfBlueprintsSet, InstanceAnimationPlayerLink, InstanceAnimations,
|
||||||
};
|
};
|
||||||
|
|
||||||
use bevy_gltf_blueprints::{AnimationInfos, AnimationMarkerReached, AnimationMarkerTrackers, AnimationMarkers, BlueprintAnimationPlayerLink, BlueprintAnimations, BlueprintName, BlueprintsList, GltfBlueprintsSet, InstanceAnimationPlayerLink, InstanceAnimations};
|
|
||||||
|
|
||||||
use bevy::{
|
use bevy::{
|
||||||
ecs::query, gltf::Gltf, prelude::*, render::view::screenshot::ScreenshotManager, time::common_conditions::on_timer, window::PrimaryWindow
|
ecs::query, gltf::Gltf, prelude::*, render::view::screenshot::ScreenshotManager,
|
||||||
|
time::common_conditions::on_timer, window::PrimaryWindow,
|
||||||
};
|
};
|
||||||
use bevy_gltf_worlflow_examples_common_rapier::{AppState, GameState};
|
use bevy_gltf_worlflow_examples_common_rapier::{AppState, GameState};
|
||||||
|
|
||||||
@ -21,7 +24,6 @@ fn start_game(mut next_app_state: ResMut<NextState<AppState>>) {
|
|||||||
next_app_state.set(AppState::AppLoading);
|
next_app_state.set(AppState::AppLoading);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// if the export from Blender worked correctly, we should have animations (simplified here by using AnimationPlayerLink)
|
// if the export from Blender worked correctly, we should have animations (simplified here by using AnimationPlayerLink)
|
||||||
// if the export from Blender worked correctly, we should have an Entity called "Blueprint4_nested" that has a child called "Blueprint3" that has a "BlueprintName" component with value Blueprint3
|
// if the export from Blender worked correctly, we should have an Entity called "Blueprint4_nested" that has a child called "Blueprint3" that has a "BlueprintName" component with value Blueprint3
|
||||||
// if the export from Blender worked correctly, we should have a blueprints_list
|
// if the export from Blender worked correctly, we should have a blueprints_list
|
||||||
@ -36,7 +38,7 @@ fn validate_export(
|
|||||||
empties_candidates: Query<(Entity, &Name, &GlobalTransform)>,
|
empties_candidates: Query<(Entity, &Name, &GlobalTransform)>,
|
||||||
|
|
||||||
blueprints_list: Query<(Entity, &BlueprintsList)>,
|
blueprints_list: Query<(Entity, &BlueprintsList)>,
|
||||||
root: Query<(Entity, &Name, &Children), (Without<Parent>, With<Children>)>
|
root: Query<(Entity, &Name, &Children), (Without<Parent>, With<Children>)>,
|
||||||
) {
|
) {
|
||||||
let animations_found = !animation_player_links.is_empty();
|
let animations_found = !animation_player_links.is_empty();
|
||||||
|
|
||||||
@ -82,22 +84,23 @@ fn validate_export(
|
|||||||
let mut tree: HashMap<String, Vec<String>> = HashMap::new();
|
let mut tree: HashMap<String, Vec<String>> = HashMap::new();
|
||||||
|
|
||||||
for child in children.iter_descendants(root.0) {
|
for child in children.iter_descendants(root.0) {
|
||||||
let child_name:String = names.get(child).map_or(String::from("no_name"), |e| e.to_string() ); //|e| e.to_string(), || "no_name".to_string());
|
let child_name: String = names
|
||||||
|
.get(child)
|
||||||
|
.map_or(String::from("no_name"), |e| e.to_string()); //|e| e.to_string(), || "no_name".to_string());
|
||||||
//println!(" child {}", child_name);
|
//println!(" child {}", child_name);
|
||||||
let parent = parents.get(child).unwrap();
|
let parent = parents.get(child).unwrap();
|
||||||
let parent_name:String = names.get(parent.get()).map_or(String::from("no_name"), |e| e.to_string() ); //|e| e.to_string(), || "no_name".to_string());
|
let parent_name: String = names
|
||||||
tree.entry(parent_name).or_default().push(child_name.clone());
|
.get(parent.get())
|
||||||
|
.map_or(String::from("no_name"), |e| e.to_string()); //|e| e.to_string(), || "no_name".to_string());
|
||||||
|
tree.entry(parent_name)
|
||||||
|
.or_default()
|
||||||
|
.push(child_name.clone());
|
||||||
}
|
}
|
||||||
|
|
||||||
let hierarchy = to_json_string(&tree);
|
let hierarchy = to_json_string(&tree);
|
||||||
fs::write(
|
fs::write("bevy_hierarchy.json", hierarchy).expect("unable to write hierarchy file")
|
||||||
"bevy_hierarchy.json",
|
|
||||||
hierarchy
|
|
||||||
)
|
|
||||||
.expect("unable to write hierarchy file")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
fs::write(
|
fs::write(
|
||||||
"bevy_diagnostics.json",
|
"bevy_diagnostics.json",
|
||||||
format!(
|
format!(
|
||||||
|
Loading…
Reference in New Issue
Block a user