diff --git a/src/lib.rs b/src/lib.rs index 2a31bd9..54d458b 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,6 +1,9 @@ use argh::FromArgs; use bevy::prelude::*; +const SPEED: f32 = 20.0; +const SPEED_DIFF_RANGE: f32 = 0.08; // +/- 8% + #[derive(Debug, FromArgs, Resource)] /// Toid Watching pub struct Config { @@ -26,6 +29,9 @@ impl Pointable for Vec3 { #[derive(Resource, Deref, DerefMut)] pub struct Index(pub rstar::RTree<Toint>); +#[derive(Resource, Deref, DerefMut)] +pub struct Positions(pub std::collections::HashMap<Entity, Vec3>); + #[derive(Component, Debug, Clone, Deref, DerefMut, Default)] pub struct Buddies(Vec<Entity>); @@ -33,12 +39,21 @@ pub struct Buddies(Vec<Entity>); pub struct Velocity(Vec3); #[derive(Component)] -pub struct Toid; +pub struct Toid { + pub speed: f32, +} -pub fn turkey_time(commands: &mut Commands, scene: &Handle<Scene>) -> Entity { +pub fn turkey_time( + commands: &mut Commands, + scene: &Handle<Scene>, + r: &mut impl rand::prelude::Rng, +) -> Entity { + let speed_diff = r.gen_range(-SPEED_DIFF_RANGE..=SPEED_DIFF_RANGE); + let speed = SPEED + (SPEED * speed_diff); + let vel = unit_vec(r) * speed; commands .spawn(SpatialBundle::default()) - .insert((Velocity::default(), Buddies::default(), Toid)) + .insert((Velocity(vel), Buddies::default(), Toid { speed })) .with_children(|t| { t.spawn(SceneBundle { scene: scene.to_owned(), @@ -60,3 +75,54 @@ pub fn add_gizmos(mut gizmos: Gizmos, toids: Query<(&Transform, Entity), With<To gizmos.ray(rpos, pos.forward(), Color::RED); } } + +pub fn update_pos( + mut toids: Query<(&mut Transform, &Velocity, Entity)>, + time: Res<Time>, + mut index: Res<Index>, +) { + let dt = time.delta_seconds(); + for (mut xform, vel, _entity) in toids.iter_mut() { + let vel = vel.0; + xform.translation += vel * dt; + } +} + +pub fn update_vel( + mut toids: Query<(&Transform, &mut Velocity, &Toid), With<Toid>>, + time: Res<Time>, +) { + let dt = time.delta_seconds(); + for (xform, mut vel, toid) in toids.iter_mut() { + let speed = toid.speed; + let mut dir = xform.forward(); + + // nudge up if too low + + // nudge toward origin if too far + + // find buddies and orient: point more towards further-away buddies + } +} + +pub fn update_buddies(mut toids: Query<(&Transform, Entity, &mut Buddies)>, index: Res<Index>) {} + +//-************************************************************************ +// util +//-************************************************************************ + +pub fn unit_vec(r: &mut impl rand::prelude::Rng) -> Vec3 { + let mut x1: f32 = 0.0; + let mut x2: f32 = 0.0; + let mut ssum = std::f32::MAX; + while ssum >= 1.0 { + x1 = r.gen_range(-1.0..=1.0); + x2 = r.gen_range(-1.0..=1.0); + ssum = x1.powi(2) + x2.powi(2); + } + let sqrt = (1.0 - ssum).sqrt(); + let x = 2.0 * x1 * sqrt; + let y = 2.0 * x2 * sqrt; + let z = 1.0 - 2.0 * ssum; + Vec3::new(x, y, z).normalize() +} diff --git a/src/main.rs b/src/main.rs index 550d0ad..8740fcd 100644 --- a/src/main.rs +++ b/src/main.rs @@ -29,13 +29,15 @@ fn setup( config: Res<Config>, models: Res<AssetServer>, ) { + let rand = &mut rand::thread_rng(); + commands.spawn(Camera3dBundle { transform: Transform::from_xyz(0., 1.5, 6.).looking_at(Vec3::ZERO, Vec3::Y), ..default() }); // plane commands.spawn(PbrBundle { - mesh: meshes.add(Mesh::from(shape::Plane::from_size(5.0))), + mesh: meshes.add(Mesh::from(shape::Plane::from_size(50.0))), material: materials.add(Color::rgb(0.3, 0.5, 0.3).into()), ..default() }); @@ -43,7 +45,7 @@ fn setup( let toid_model = models.load("models/boid.glb#Scene0"); for _ in 0..config.toids { - let _ = turkey_time(&mut commands, &toid_model); + let _ = turkey_time(&mut commands, &toid_model, rand); } // light