use bevy::prelude::*;
use big_space::prelude::*;
fn main() {
App::new()
.add_plugins((
DefaultPlugins.build().disable::<TransformPlugin>(),
BigSpaceDefaultPlugins,
))
.add_systems(Startup, (setup_scene, setup_ui))
.add_systems(Update, (rotator_system, toggle_plugin))
.run();
}
const DISTANCE: GridPrecision = 2_000_000;
fn toggle_plugin(
input: Res<ButtonInput<KeyCode>>,
grids: Grids,
mut text: Query<&mut Text>,
mut disabled: Local<bool>,
mut floating_origin: Query<(Entity, &mut CellCoord), With<FloatingOrigin>>,
) -> Result {
if input.just_pressed(KeyCode::Space) {
*disabled = !*disabled;
}
let this_grid = grids
.parent_grid(floating_origin.single().unwrap().0)
.unwrap();
let mut origin_cell = floating_origin.single_mut()?.1;
let index_max = DISTANCE / this_grid.cell_edge_length() as GridPrecision;
let increment = index_max / 100;
let msg = if *disabled {
if origin_cell.x > 0 {
origin_cell.x = 0.max(origin_cell.x - increment);
origin_cell.y = 0.max(origin_cell.y - increment);
origin_cell.z = 0.max(origin_cell.z - increment);
"Disabling..."
} else {
"Floating Origin Disabled"
}
} else if origin_cell.x < index_max {
origin_cell.x = index_max.min(origin_cell.x.saturating_add(increment));
origin_cell.y = index_max.min(origin_cell.y.saturating_add(increment));
origin_cell.z = index_max.min(origin_cell.z.saturating_add(increment));
"Enabling..."
} else {
"Floating Origin Enabled"
};
let dist =
index_max.saturating_sub(origin_cell.x) * this_grid.cell_edge_length() as GridPrecision;
let thousands = |num: GridPrecision| {
num.to_string()
.as_bytes()
.rchunks(3)
.rev()
.map(core::str::from_utf8)
.collect::<Result<Vec<&str>, _>>()
.unwrap()
.join(",") };
text.single_mut()?.0 =
format!("Press Spacebar to toggle: {msg}\nCamera distance to floating origin: {}\nMesh distance from origin: {}", thousands(dist), thousands(DISTANCE));
Ok(())
}
#[derive(Component)]
struct Rotator;
fn rotator_system(time: Res<Time>, mut query: Query<&mut Transform, With<Rotator>>) {
for mut transform in &mut query {
transform.rotate_y(time.delta_secs());
}
}
fn setup_ui(mut commands: Commands) {
commands.spawn((
Text::default(),
TextFont {
font_size: 30.0,
..default()
},
Node {
position_type: PositionType::Absolute,
top: Val::Px(12.0),
left: Val::Px(12.0),
..default()
},
));
}
fn setup_scene(mut commands: Commands, asset_server: Res<AssetServer>) {
commands.spawn_big_space_default(|root| {
let d = DISTANCE / root.grid().cell_edge_length() as GridPrecision;
let distant_grid_cell = CellCoord::new(d, d, d);
root.spawn_spatial((distant_grid_cell, FloatingOrigin));
root.spawn_spatial((
SceneRoot(asset_server.load("models/low_poly_spaceship/scene.gltf#Scene0")),
Transform::from_scale(Vec3::splat(0.2)),
distant_grid_cell,
Rotator,
))
.with_child((
SceneRoot(asset_server.load("models/low_poly_spaceship/scene.gltf#Scene0")),
Transform::from_xyz(0.0, 0.0, 20.0),
));
root.spawn_spatial((
DirectionalLight::default(),
Transform::from_xyz(4.0, -10.0, -4.0),
distant_grid_cell,
));
root.spawn_spatial((
Camera3d::default(),
Transform::from_xyz(8.0, 8.0, 0.0).looking_at(Vec3::ZERO, Vec3::Y),
distant_grid_cell,
));
});
}