~intarga/the-acorns-must-flow

8c5c337888194bcfa9966bb3b2e94b5b82e26e2d — Ingrid 4 months ago 3ef2ad2
implement flocking behaviour: velocity alignment
1 files changed, 29 insertions(+), 0 deletions(-)

M src/main.rs
M src/main.rs => src/main.rs +29 -0
@@ 29,6 29,7 @@ impl Plugin for TamfPlugin {
                SystemSet::new()
                    .with_run_criteria(FixedTimestep::step(TIME_STEP as f64))
                    .with_system(center_squirrels.system())
                    .with_system(align_squirrels.system())
                    .with_system(move_squirrels.system())
                    .with_system(update_bounds.system()),
            );


@@ 105,6 106,34 @@ fn center_squirrels(mut query: Query<(&mut Squirrel, &Transform)>) {
    }
}

// match velocities with other squirrels in local flock
fn align_squirrels(mut query: Query<(&mut Squirrel, &Transform)>) {
    let mut squirrels: Vec<(Vec3, Vec3)> = Vec::new();
    for (squirrel, transform) in query.iter_mut() {
        squirrels.push((squirrel.velocity, transform.translation))
    }

    for (mut squirrel, transform) in query.iter_mut() {
        let mut avg_velocity = Vec3::ZERO;
        let mut num_neighbours = 0;

        for (sub_velocity, sub_translation) in &squirrels {
            if transform.translation.distance(*sub_translation) < FLOCKING_RANGE {
                avg_velocity += *sub_velocity;
                num_neighbours += 1;
            }
        }

        if num_neighbours >= 2 {
            avg_velocity.x = avg_velocity.x / num_neighbours as f32;
            avg_velocity.y = avg_velocity.y / num_neighbours as f32;

            let sqv = squirrel.velocity.clone();
            squirrel.velocity += (avg_velocity - sqv) * ALIGNMENT_FACTOR;
        }
    }
}

fn move_squirrels(mut query: Query<(&mut Squirrel, &mut Transform)>, bounds: Res<Bounds>) {
    for (mut squirrel, mut transform) in query.iter_mut() {
        // Reverse velocity component if going out of frame