Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion examples3d/src/glb_to_point_cloud_color.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ pub fn elastic_color_model_demo(
device: RenderDevice,
app_state: &mut AppState,
_callbacks: &mut Callbacks,
_assets: &Dependencies,
assets: &Dependencies,
) -> PhysicsContext {
let buffer = &assets.get_data("shiba.glb").unwrap().data;
let pc_grid = load_model_with_colors(
Expand Down
23 changes: 22 additions & 1 deletion src_testbed/load_scene.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use bevy::asset::LoadState;
use bevy::ecs::system::SystemId;
use bevy::prelude::*;
use bevy::render::renderer::RenderDevice;
Expand All @@ -18,12 +19,13 @@ pub fn load_scene_plugin(app: &mut App) {
#[derive(Resource, Default)]
pub struct CurrentSceneId(pub usize);

#[derive(Copy, Clone, States, Hash, PartialEq, Eq, Debug, Default)]
#[derive(Clone, States, Hash, PartialEq, Eq, Debug, Default)]
pub enum SceneState {
#[default]
Waiting,
Loading,
Loaded,
LoadingError(Vec<(String, String)>),
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

type error ?

}

#[derive(Resource)]
Expand Down Expand Up @@ -64,13 +66,32 @@ pub fn check_scene_loaded(
loading_assets: Res<LoadingAssets>,
asset_server: Res<AssetServer>,
) {
let errors = loading_assets
.assets
.iter()
.filter_map(|a| {
if let Some(load_state) = asset_server.get_load_state(a.1) {
Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

unse ?

return match load_state {
LoadState::Failed(error) => Some((a.0.clone(), error.to_string())),
_ => None,
};
}
None
})
.collect::<Vec<_>>();
if !errors.is_empty() {
next_scene_state.set(SceneState::LoadingError(errors));
return;
}

if loading_assets
.assets
.iter()
.any(|a| !asset_server.is_loaded_with_dependencies(a.1))
{
return;
}

next_scene_state.set(SceneState::Loaded);
}
pub fn call_init_state(
Expand Down
243 changes: 133 additions & 110 deletions src_testbed/ui.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,131 +38,154 @@ pub fn update_ui(
app_state.restarting = false;
}

if scene_state.get() == &SceneState::Loading {
ui.label("Loading...");
} else if let Some(physics) = physics {
let mut changed = false;
egui::ComboBox::from_label("render mode")
.selected_text(RenderMode::from_u32(app_state.render_config.mode).text())
.show_ui(ui, |ui| {
for i in 0..6 {
changed = ui
.selectable_value(
&mut app_state.render_config.mode,
i,
RenderMode::from_u32(i).text(),
)
.changed()
|| changed;
}
});

if changed {
queue.write_buffer(
app_state.gpu_render_config.buffer.buffer(),
0,
bytemuck::bytes_of(&app_state.render_config.mode),
);
queue.submit([]);
match scene_state.get() {
SceneState::Waiting => {
ui.label("Waiting...");
}

let mut sim_params_changed = false;
sim_params_changed = ui
.add(Slider::new(&mut app_state.num_substeps, 1..=200).text("substeps"))
.changed()
|| sim_params_changed;
sim_params_changed = ui
.add(Slider::new(&mut app_state.gravity_factor, 0.0..=10.0).text("gravity factor"))
.changed()
|| sim_params_changed;

if ui
.checkbox(&mut app_state.show_rigid_particles, "show rigid_particles")
.changed()
{
for mut visibility in rigid_particles.iter_mut() {
if app_state.show_rigid_particles {
*visibility = Visibility::Inherited;
} else {
*visibility = Visibility::Hidden;
}
SceneState::Loading => {
ui.label("Loading...");
}
SceneState::LoadingError(errors) => {
ui.label("Error loading scene!");
ui.label("Locally, run `cargo run` from the same directory where your `assets/` directory is located.");
ui.label("Typically in `examples2d/` or `example3d/`.");
ui.label("Errors:");
for error in errors {
ui.label(format!(
"asset \"{}\" failed with errors: {:?}",
error.0, error.1
));
}
}
SceneState::Loaded => {
if let Some(physics) = physics {
let mut changed = false;
egui::ComboBox::from_label("render mode")
.selected_text(RenderMode::from_u32(app_state.render_config.mode).text())
.show_ui(ui, |ui| {
for i in 0..6 {
changed = ui
.selectable_value(
&mut app_state.render_config.mode,
i,
RenderMode::from_u32(i).text(),
)
.changed()
|| changed;
}
});

#[cfg(feature = "dim2")]
let gravity = vector![0.0, -9.81];
#[cfg(feature = "dim3")]
let gravity = vector![0.0, -9.81, 0.0];
if changed {
queue.write_buffer(
app_state.gpu_render_config.buffer.buffer(),
0,
bytemuck::bytes_of(&app_state.render_config.mode),
);
queue.submit([]);
}

let mut sim_params_changed = false;
sim_params_changed = ui
.add(Slider::new(&mut app_state.num_substeps, 1..=200).text("substeps"))
.changed()
|| sim_params_changed;
sim_params_changed = ui
.add(
Slider::new(&mut app_state.gravity_factor, 0.0..=10.0)
.text("gravity factor"),
)
.changed()
|| sim_params_changed;

if ui
.checkbox(&mut app_state.show_rigid_particles, "show rigid_particles")
.changed()
{
for mut visibility in rigid_particles.iter_mut() {
if app_state.show_rigid_particles {
*visibility = Visibility::Inherited;
} else {
*visibility = Visibility::Hidden;
}
}
}

if sim_params_changed {
let new_params = SimulationParams {
gravity: gravity * app_state.gravity_factor,
dt: (1.0 / 60.0) / (app_state.num_substeps as f32),
#[cfg(feature = "dim2")]
padding: 0.0,
};
queue.write_buffer(
physics.data.sim_params.params.buffer(),
0,
bytemuck::bytes_of(&new_params),
);
queue.submit([]);
}
let gravity = vector![0.0, -9.81];
#[cfg(feature = "dim3")]
let gravity = vector![0.0, -9.81, 0.0];

ui.label(format!("Particle count: {}", physics.particles.len()));
ui.label(format!(
"Rigid particle count: {}",
physics.data.rigid_particles.len()
));
if sim_params_changed {
let new_params = SimulationParams {
gravity: gravity * app_state.gravity_factor,
dt: (1.0 / 60.0) / (app_state.num_substeps as f32),
#[cfg(feature = "dim2")]
padding: 0.0,
};
queue.write_buffer(
physics.data.sim_params.params.buffer(),
0,
bytemuck::bytes_of(&new_params),
);
queue.submit([]);
}

CollapsingHeader::new(format!("GPU runtime: {:.3}ms", timings.total_time()))
.id_salt("GPU runtimes")
.show(ui, |ui| {
ui.label(format!(
"Rigid update: {:.3}ms",
timings.update_rigid_particles
));
ui.label(format!("Grid sort: {:.3}ms", timings.grid_sort));
ui.label(format!("CDF Grid update: {:.3}ms", timings.grid_update_cdf));
ui.label(format!("CDF P2G: {:.3}ms", timings.p2g_cdf));
ui.label(format!("CDF G2P: {:.3}ms", timings.g2p_cdf));
ui.label(format!("P2G: {:.3}ms", timings.p2g));
ui.label(format!("Grid update: {:.3}ms", timings.grid_update));
ui.label(format!("G2P: {:.3}ms", timings.g2p));
ui.label(format!(
"Particles update: {:.3}ms",
timings.particles_update
));
ui.label(format!("Particle count: {}", physics.particles.len()));
ui.label(format!(
"Integrate bodies: {:.3}ms",
timings.integrate_bodies
"Rigid particle count: {}",
physics.data.rigid_particles.len()
));
});

ui.horizontal(|ui| {
let label = if app_state.run_state == RunState::Paused {
"Run"
} else {
"Pause"
};
CollapsingHeader::new(format!("GPU runtime: {:.3}ms", timings.total_time()))
.id_salt("GPU runtimes")
.show(ui, |ui| {
ui.label(format!(
"Rigid update: {:.3}ms",
timings.update_rigid_particles
));
ui.label(format!("Grid sort: {:.3}ms", timings.grid_sort));
ui.label(format!("CDF Grid update: {:.3}ms", timings.grid_update_cdf));
ui.label(format!("CDF P2G: {:.3}ms", timings.p2g_cdf));
ui.label(format!("CDF G2P: {:.3}ms", timings.g2p_cdf));
ui.label(format!("P2G: {:.3}ms", timings.p2g));
ui.label(format!("Grid update: {:.3}ms", timings.grid_update));
ui.label(format!("G2P: {:.3}ms", timings.g2p));
ui.label(format!(
"Particles update: {:.3}ms",
timings.particles_update
));
ui.label(format!(
"Integrate bodies: {:.3}ms",
timings.integrate_bodies
));
});

if ui.button(label).clicked() {
if app_state.run_state == RunState::Paused {
app_state.run_state = RunState::Running
} else {
app_state.run_state = RunState::Paused
}
}
ui.horizontal(|ui| {
let label = if app_state.run_state == RunState::Paused {
"Run"
} else {
"Pause"
};

if ui.button("Step").clicked() {
app_state.run_state = RunState::Step;
}
if ui.button(label).clicked() {
if app_state.run_state == RunState::Paused {
app_state.run_state = RunState::Running
} else {
app_state.run_state = RunState::Paused
}
}

if ui.button("Restart").clicked() {
scenes.init_scene(&mut commands, app_state.selected_scene);
app_state.restarting = true;
if ui.button("Step").clicked() {
app_state.run_state = RunState::Step;
}

if ui.button("Restart").clicked() {
scenes.init_scene(&mut commands, app_state.selected_scene);
app_state.restarting = true;
}
});
}
});
}
}
});
}