diff --git a/common/src/comp/inventory/item/tool.rs b/common/src/comp/inventory/item/tool.rs index 78d0d40e96..3b4ab95573 100644 --- a/common/src/comp/inventory/item/tool.rs +++ b/common/src/comp/inventory/item/tool.rs @@ -337,7 +337,7 @@ impl Tool { buildup_duration: Duration::from_millis(200), shoot_duration: Duration::from_millis(200), recover_duration: Duration::from_millis(800), - leap: Some(10.0), + leap: Some(5.0), projectile: Projectile { hit_solid: vec![projectile::Effect::Stick], hit_entity: vec![ diff --git a/common/src/states/combo_melee.rs b/common/src/states/combo_melee.rs index 4ae0d24efd..ca66efae6e 100644 --- a/common/src/states/combo_melee.rs +++ b/common/src/states/combo_melee.rs @@ -146,11 +146,13 @@ impl CharacterBehavior for Data { StageSection::Swing => { if self.timer < self.static_data.stage_data[stage_index].base_swing_duration { // Forward movement - forward_move( + handle_forced_movement( data, &mut update, + ForcedMovement::Forward { + strength: self.static_data.stage_data[stage_index].forward_movement, + }, 0.3, - self.static_data.stage_data[stage_index].forward_movement, ); // Swings diff --git a/common/src/states/dash_melee.rs b/common/src/states/dash_melee.rs index fbd83a2652..820117704e 100644 --- a/common/src/states/dash_melee.rs +++ b/common/src/states/dash_melee.rs @@ -111,7 +111,14 @@ impl CharacterBehavior for Data { && update.energy.current() > 0 { // Forward movement - forward_move(data, &mut update, 0.1, self.static_data.forward_speed); + handle_forced_movement( + data, + &mut update, + ForcedMovement::Forward { + strength: self.static_data.forward_speed, + }, + 0.1, + ); // This logic basically just decides if a charge should end, and prevents the // character state spamming attacks while checking if it has hit something diff --git a/common/src/states/leap_melee.rs b/common/src/states/leap_melee.rs index d6b6f297af..0739761281 100644 --- a/common/src/states/leap_melee.rs +++ b/common/src/states/leap_melee.rs @@ -6,7 +6,6 @@ use crate::{ }; use serde::{Deserialize, Serialize}; use std::time::Duration; -use vek::Vec3; /// Separated out to condense update portions of character state #[derive(Copy, Clone, Debug, PartialEq, Serialize, Deserialize)] @@ -76,28 +75,20 @@ impl CharacterBehavior for Data { }, StageSection::Movement => { if self.timer < self.static_data.movement_duration { - // Apply jumping force while in Movement portion of state - update.vel.0 = Vec3::new( - data.inputs.look_dir.x, - data.inputs.look_dir.y, - self.static_data.vertical_leap_strength, - ) * 2.0 - // Multiply decreasing amount linearly over time of - // movement duration - * (1.0 - - self.timer.as_secs_f32() - / self.static_data.movement_duration.as_secs_f32()) - // Apply inputted movement directions at 0.25 strength - + (update.vel.0 * Vec3::new(2.0, 2.0, 0.0) - + 0.25 * data.inputs.move_dir.try_normalized().unwrap_or_default()) - .try_normalized() - .unwrap_or_default() - // Multiply by forward leap strength - * self.static_data.forward_leap_strength - // Control forward movement based on look direction. - // This allows players to stop moving forward when they - // look downward at target - * (1.0 - data.inputs.look_dir.z.abs()); + // Apply jumping force + let progress = 1.0 + - self.timer.as_secs_f32() + / self.static_data.movement_duration.as_secs_f32(); + handle_forced_movement( + data, + &mut update, + ForcedMovement::Leap { + vertical: self.static_data.vertical_leap_strength, + forward: self.static_data.forward_leap_strength, + progress, + }, + 0.15, + ); // Increment duration // If we were to set a timeout for state, this would be diff --git a/common/src/states/repeater_ranged.rs b/common/src/states/repeater_ranged.rs index c2c4e5d81b..5adfdde10a 100644 --- a/common/src/states/repeater_ranged.rs +++ b/common/src/states/repeater_ranged.rs @@ -54,13 +54,18 @@ impl CharacterBehavior for Data { StageSection::Movement => { // Jumping if let Some(leap_strength) = self.static_data.leap { - update.vel.0 = Vec3::new( - data.vel.0.x, - data.vel.0.y, - leap_strength - * (1.0 - - self.timer.as_secs_f32() - / self.static_data.movement_duration.as_secs_f32()), + let progress = 1.0 + - self.timer.as_secs_f32() + / self.static_data.movement_duration.as_secs_f32(); + handle_forced_movement( + data, + &mut update, + ForcedMovement::Leap { + vertical: leap_strength, + forward: 10.0, + progress, + }, + 1.0, ); } if self.timer < self.static_data.movement_duration { @@ -87,7 +92,12 @@ impl CharacterBehavior for Data { StageSection::Buildup => { // Aim gliding if self.static_data.leap.is_some() { - update.vel.0 = Vec3::new(data.vel.0.x, data.vel.0.y, 0.0); + handle_forced_movement( + data, + &mut update, + ForcedMovement::Hover { move_input: 0.1 }, + 1.0, + ); } if self.timer < self.static_data.buildup_duration { // Buildup to attack diff --git a/common/src/states/spin_melee.rs b/common/src/states/spin_melee.rs index 73765d1607..d685d5dbb4 100644 --- a/common/src/states/spin_melee.rs +++ b/common/src/states/spin_melee.rs @@ -123,7 +123,14 @@ impl CharacterBehavior for Data { }); } else if self.timer < self.static_data.swing_duration { if !self.static_data.is_helicopter { - forward_move(data, &mut update, 0.1, self.static_data.forward_speed); + handle_forced_movement( + data, + &mut update, + ForcedMovement::Forward { + strength: self.static_data.forward_speed, + }, + 0.1, + ); handle_orientation(data, &mut update, 1.0); } diff --git a/common/src/states/utils.rs b/common/src/states/utils.rs index 13e0f50269..b2dd5ecb9e 100644 --- a/common/src/states/utils.rs +++ b/common/src/states/utils.rs @@ -91,18 +91,54 @@ fn basic_move(data: &JoinData, update: &mut StateUpdate, efficiency: f32) { handle_orientation(data, update, data.body.base_ori_rate()); } -/// Similar to basic_move function, but with forced forward movement -pub fn forward_move(data: &JoinData, update: &mut StateUpdate, efficiency: f32, forward: f32) { - let accel = if data.physics.on_ground { - data.body.base_accel() - } else { - BASE_HUMANOID_AIR_ACCEL - }; - - update.vel.0 += Vec2::broadcast(data.dt.0) - * accel - * (data.inputs.move_dir * efficiency + (*update.ori.0).xy() * forward); +/// Handles forced movement +pub fn handle_forced_movement( + data: &JoinData, + update: &mut StateUpdate, + movement: ForcedMovement, + efficiency: f32, +) { + match movement { + ForcedMovement::Forward { strength } => { + let accel = if data.physics.on_ground { + data.body.base_accel() + } else { + BASE_HUMANOID_AIR_ACCEL + }; + update.vel.0 += Vec2::broadcast(data.dt.0) + * accel + * (data.inputs.move_dir * efficiency + (*update.ori.0).xy() * strength); + }, + ForcedMovement::Leap { + vertical, + forward, + progress, + } => { + // Apply jumping force + update.vel.0 = Vec3::new( + data.inputs.look_dir.x, + data.inputs.look_dir.y, + vertical, + ) + // Multiply decreasing amount linearly over time (with average of 1) + * 2.0 * progress + // Apply inputted movement directions with some efficiency + + (data.inputs.move_dir.try_normalized().unwrap_or_default() + update.vel.0.xy()) + .try_normalized() + .unwrap_or_default() + // Multiply by forward leap strength + * forward + // Control forward movement based on look direction. + // This allows players to stop moving forward when they + // look downward at target + * (1.0 - data.inputs.look_dir.z.abs()); + }, + ForcedMovement::Hover { move_input } => { + update.vel.0 = Vec3::new(data.vel.0.x, data.vel.0.y, 0.0) + + move_input * data.inputs.move_dir.try_normalized().unwrap_or_default(); + }, + } handle_orientation(data, update, data.body.base_ori_rate() * efficiency); } @@ -389,3 +425,18 @@ pub enum AbilityKey { Skill1, Dodge, } + +#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)] +pub enum ForcedMovement { + Forward { + strength: f32, + }, + Leap { + vertical: f32, + forward: f32, + progress: f32, + }, + Hover { + move_input: f32, + }, +}