From 0ce3d03e1f12f1b490b64be0b4fdeec76ebbc397 Mon Sep 17 00:00:00 2001 From: yuni <hut@hut.pm> Date: Sat, 30 Nov 2024 03:23:25 +0100 Subject: [PATCH] rewrite handle_wants_acceleration() using MatchVelocityTarget --- src/actor.rs | 95 +++++++++++----------------------------------------- 1 file changed, 19 insertions(+), 76 deletions(-) diff --git a/src/actor.rs b/src/actor.rs index 685eafb..a6c1692 100644 --- a/src/actor.rs +++ b/src/actor.rs @@ -791,17 +791,15 @@ fn handle_wants_rotation_change(mut q_actor: Query<(&mut Rotation, &mut WantsRot fn handle_wants_acceleration( time: Res<Time>, settings: Res<var::Settings>, - jupiter_pos: Res<game::JupiterPos>, q_audiosinks: Query<(&audio::Sfx, &AudioSink)>, mut q_actor: Query< ( - Entity, &Transform, &Position, &mut LinearVelocity, + &MatchingVelocityTarget, Option<&mut Engine>, Option<&WantsAcceleration>, - Option<&hud::IsTargeted>, Option<&PlayerCamera>, ), (Without<visual::IsEffect>, Without<HiddenInsideVehicle>), @@ -809,78 +807,25 @@ fn handle_wants_acceleration( mut ew_effect: EventWriter<visual::SpawnEffectEvent>, ) { let dt = time.delta_seconds(); - - // Vector elements: (Entity, is_player, pos) - let mut request_closest: Vec<(Entity, bool, DVec3)> = vec![]; - let mut closest_map: HashMap<Entity, DVec3> = HashMap::new(); - - // First, determine whether any actor wants to brake (=match velocity) - for (entity, _, pos, _, _, accel, _, is_player) in &mut q_actor { - if accel.is_some() && accel.unwrap().brake { - request_closest.push((entity, is_player.is_some(), pos.0.clone())); - } - } - - // If an actor is braking, find out relative to what it wants to brake - for (entity, is_player, pos) in &request_closest { - let mut target_v: Option<DVec3> = None; - - // First, if this is the player, check whether they targeted anything - // so we can match velocity to the target. - if *is_player { - for (_, _, _, v, _, _, is_target, _) in &q_actor { - if is_target.is_some() { - target_v = Some(v.0); - break; - } - } - } - - // If not, simply look for the closest object and match velocity to that. - if target_v.is_none() { - let mut closest_distance = camera::MAX_DIST_FOR_MATCH_VELOCITY; - for (testentity, _, testpos, v, _, _, _, _) in &q_actor { - if *entity != testentity { - let distance = (*pos - testpos.0).length(); - if distance < closest_distance { - target_v = Some(v.0); - closest_distance = distance; - } - } - } - } - - // Last resort: Match velocity to the orbital velocity around Jupiter - if target_v.is_none() { - let relative_pos = *pos - jupiter_pos.0; - target_v = Some(nature::orbital_velocity(relative_pos, nature::JUPITER_MASS)); - } - - if let Some(target_v) = target_v { - closest_map.insert(*entity, target_v); - } - } - - // Finally, apply the requested acceleration to the actor's velocity let mut play_thruster_sound = false; let mut players_engine: Option<Engine> = None; - for (entity, trans, pos, mut v, engine, accel, _, is_player) in &mut q_actor { - let mut thruster_on = false; + + for (trans, pos, mut v, matching, engine, accel, is_player) in &mut q_actor { + // Apply the requested acceleration to the actor's velocity if let (Some(mut engine), Some(accel)) = (engine, accel) { + let mut thruster_on = false; let mut delta_v = DVec3::ZERO; let mut allow_fullstop = false; let boost = engine.current_boost_factor; engine.currently_matching_velocity = false; if accel.brake { - if let Some(target_v) = closest_map.get(&entity) { - let stop_direction = (*target_v - v.0).as_vec3(); - if stop_direction.length_squared() > 0.003 { - delta_v = - (trans.rotation.inverse() * stop_direction.normalize()).as_dvec3(); - engine.currently_matching_velocity = true; - thruster_on = true; // is this redundant? - } + let stop_direction = (matching.v - v.0).as_vec3(); + if stop_direction.length_squared() > 0.003 { + delta_v = + (trans.rotation.inverse() * stop_direction.normalize()).as_dvec3(); + engine.currently_matching_velocity = true; + thruster_on = true; // is this redundant? } } @@ -922,16 +867,14 @@ fn handle_wants_acceleration( // Apply acceleration to velocity if allow_fullstop { - if let Some(target_v) = closest_map.get(&entity) { - // Prevent overshooting when matching velocity, which - // would result in oscillating acceleration back and forth - for axis in 0..3 { - let original = v[axis]; - let target = target_v[axis]; - v[axis] += final_accel[axis]; - if (original - target).signum() != (v[axis] - target).signum() { - v[axis] = target; - } + // Prevent overshooting when matching velocity, which + // would result in oscillating acceleration back and forth + for axis in 0..3 { + let original = v[axis]; + let target = matching.v[axis]; + v[axis] += final_accel[axis]; + if (original - target).signum() != (v[axis] - target).signum() { + v[axis] = target; } } } else {