readd sneak

This commit is contained in:
jshipsey 2020-08-02 01:09:11 -04:00
parent 691607f398
commit 9ff5c23cf0
23 changed files with 482 additions and 20 deletions

View File

@ -594,6 +594,21 @@ impl Client {
}
}
pub fn toggle_sneak(&mut self) {
let is_sneaking = self
.state
.ecs()
.read_storage::<comp::CharacterState>()
.get(self.entity)
.map(|cs| matches!(cs, comp::CharacterState::Sneak));
match is_sneaking {
Some(true) => self.control_action(ControlAction::Stand),
Some(false) => self.control_action(ControlAction::Sneak),
None => warn!("Can't toggle sneak, client entity doesn't have a `CharacterState`"),
}
}
pub fn toggle_glide(&mut self) {
let is_gliding = self
.state

View File

@ -41,6 +41,7 @@ pub enum CharacterState {
Climb,
Sit,
Dance,
Sneak,
Glide,
GlideWield,
/// A basic blocking state

View File

@ -46,6 +46,7 @@ pub enum ControlAction {
Unwield,
Sit,
Dance,
Sneak,
Stand,
}
@ -170,7 +171,8 @@ pub struct ControllerInputs {
pub wall_leap: Input,
pub charge: Input,
pub climb: Option<Climb>,
pub swim: Input,
pub swimup: Input,
pub swimdown: Input,
pub move_dir: Vec2<f32>,
pub look_dir: Dir,
}
@ -194,7 +196,8 @@ impl ControllerInputs {
self.glide.tick(dt);
self.wall_leap.tick(dt);
self.charge.tick(dt);
self.swim.tick(dt);
self.swimup.tick(dt);
self.swimdown.tick(dt);
}
pub fn tick_freshness(&mut self) {
@ -206,7 +209,8 @@ impl ControllerInputs {
self.glide.tick_freshness();
self.wall_leap.tick_freshness();
self.charge.tick_freshness();
self.swim.tick_freshness();
self.swimup.tick_freshness();
self.swimdown.tick_freshness();
}
/// Updates Controller inputs with new version received from the client
@ -220,7 +224,8 @@ impl ControllerInputs {
self.wall_leap.update_with_new(new.wall_leap);
self.charge.update_with_new(new.charge);
self.climb = new.climb;
self.swim.update_with_new(new.swim);
self.swimup.update_with_new(new.swimup);
self.swimdown.update_with_new(new.swimdown);
self.move_dir = new.move_dir;
self.look_dir = new.look_dir;
}

View File

@ -52,7 +52,8 @@ impl CharacterBehavior for Data {
// Expend energy if climbing
let energy_use = match climb {
Climb::Up | Climb::Down => 8,
Climb::Up => 5,
Climb::Down => 1,
Climb::Hold => 1,
};
@ -79,14 +80,14 @@ impl CharacterBehavior for Data {
match climb {
Climb::Down => {
update.vel.0 -=
data.dt.0 * update.vel.0.map(|e| e.abs().powf(1.5) * e.signum() * 6.0);
data.dt.0 * update.vel.0.map(|e| e.abs().powf(1.5) * e.signum() * 1.0);
},
Climb::Up => {
update.vel.0.z = (update.vel.0.z + data.dt.0 * GRAVITY * 1.25).min(CLIMB_SPEED);
},
Climb::Hold => {
// Antigrav
update.vel.0.z = (update.vel.0.z + data.dt.0 * GRAVITY * 1.5).min(CLIMB_SPEED);
update.vel.0.z = (update.vel.0.z + data.dt.0 * GRAVITY * 1.1).min(CLIMB_SPEED);
update.vel.0 = Lerp::lerp(
update.vel.0,
Vec3::zero(),

View File

@ -16,9 +16,12 @@ impl CharacterBehavior for Data {
handle_wield(data, &mut update);
// If not on the ground while wielding glider enter gliding state
if !data.physics.on_ground && !data.physics.in_fluid {
if !data.physics.on_ground {
update.character = CharacterState::Glide;
}
if data.physics.in_fluid {
update.character = CharacterState::Idle;
}
update
}
@ -35,6 +38,12 @@ impl CharacterBehavior for Data {
update
}
fn sneak(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_sneak(data, &mut update);
update
}
fn unwield(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
update.character = CharacterState::Idle;

View File

@ -37,6 +37,12 @@ impl CharacterBehavior for Data {
update
}
fn sneak(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_sneak(data, &mut update);
update
}
fn glide_wield(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_glide_wield(data, &mut update);

View File

@ -13,6 +13,7 @@ pub mod idle;
pub mod leap_melee;
pub mod roll;
pub mod sit;
pub mod sneak;
pub mod spin_melee;
pub mod triple_strike;
pub mod utils;

View File

@ -0,0 +1,56 @@
use super::utils::*;
use crate::{
comp::{CharacterState, StateUpdate},
sys::character_behavior::{CharacterBehavior, JoinData},
};
pub struct Data;
impl CharacterBehavior for Data {
fn behavior(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
handle_move(data, &mut update, 0.4);
handle_jump(data, &mut update);
handle_wield(data, &mut update);
handle_climb(data, &mut update);
handle_dodge_input(data, &mut update);
// Try to Fall/Stand up/Move
if !data.physics.on_ground {
update.character = CharacterState::Idle;
}
update
}
fn wield(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_wield(data, &mut update);
update
}
fn sit(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_sit(data, &mut update);
update
}
fn dance(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_dance(data, &mut update);
update
}
fn glide_wield(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_glide_wield(data, &mut update);
update
}
fn swap_loadout(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_swap_loadout(data, &mut update);
update
}
}

View File

@ -118,9 +118,14 @@ fn swim_move(data: &JoinData, update: &mut StateUpdate, efficiency: f32) {
handle_orientation(data, update, if data.physics.on_ground { 9.0 } else { 2.0 });
// Swim
if data.inputs.swim.is_pressed() {
if data.inputs.swimup.is_pressed() {
update.vel.0.z =
(update.vel.0.z + data.dt.0 * GRAVITY * 2.25).min(BASE_HUMANOID_WATER_SPEED);
(update.vel.0.z + data.dt.0 * GRAVITY * 4.0).min(BASE_HUMANOID_WATER_SPEED);
}
// Swim
if data.inputs.swimdown.is_pressed() {
update.vel.0.z =
(update.vel.0.z + data.dt.0 * GRAVITY * -3.5).min(BASE_HUMANOID_WATER_SPEED);
}
}
@ -159,6 +164,12 @@ pub fn attempt_dance(data: &JoinData, update: &mut StateUpdate) {
}
}
pub fn attempt_sneak(data: &JoinData, update: &mut StateUpdate) {
if data.physics.on_ground && data.body.is_humanoid() {
update.character = CharacterState::Sneak;
}
}
/// Checks that player can `Climb` and updates `CharacterState` if so
pub fn handle_climb(data: &JoinData, update: &mut StateUpdate) {
if data.inputs.climb.is_some()

View File

@ -33,6 +33,12 @@ impl CharacterBehavior for Data {
update
}
fn sneak(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
attempt_sneak(data, &mut update);
update
}
fn unwield(&self, data: &JoinData) -> StateUpdate {
let mut update = StateUpdate::from(data);
update.character = CharacterState::Idle;

View File

@ -27,6 +27,7 @@ pub trait CharacterBehavior {
fn unwield(&self, data: &JoinData) -> StateUpdate { StateUpdate::from(data) }
fn sit(&self, data: &JoinData) -> StateUpdate { StateUpdate::from(data) }
fn dance(&self, data: &JoinData) -> StateUpdate { StateUpdate::from(data) }
fn sneak(&self, data: &JoinData) -> StateUpdate { StateUpdate::from(data) }
fn stand(&self, data: &JoinData) -> StateUpdate { StateUpdate::from(data) }
fn handle_event(&self, data: &JoinData, event: ControlAction) -> StateUpdate {
match event {
@ -36,6 +37,7 @@ pub trait CharacterBehavior {
ControlAction::Unwield => self.unwield(data),
ControlAction::Sit => self.sit(data),
ControlAction::Dance => self.dance(data),
ControlAction::Sneak => self.sneak(data),
ControlAction::Stand => self.stand(data),
}
}
@ -232,6 +234,9 @@ impl<'a> System<'a> for Sys {
CharacterState::Dance => {
states::dance::Data::handle_event(&states::dance::Data, &j, action)
},
CharacterState::Sneak => {
states::sneak::Data::handle_event(&states::sneak::Data, &j, action)
},
CharacterState::BasicBlock => {
states::basic_block::Data.handle_event(&j, action)
},
@ -261,6 +266,7 @@ impl<'a> System<'a> for Sys {
CharacterState::GlideWield => states::glide_wield::Data.behavior(&j),
CharacterState::Sit => states::sit::Data::behavior(&states::sit::Data, &j),
CharacterState::Dance => states::dance::Data::behavior(&states::dance::Data, &j),
CharacterState::Sneak => states::sneak::Data::behavior(&states::sneak::Data, &j),
CharacterState::BasicBlock => states::basic_block::Data.behavior(&j),
CharacterState::Roll(data) => data.behavior(&j),
CharacterState::Wielding => states::wielding::Data.behavior(&j),

View File

@ -15,7 +15,7 @@ use specs::{
use vek::*;
pub const GRAVITY: f32 = 9.81 * 5.0;
const BOUYANCY: f32 = 0.0;
const BOUYANCY: f32 = 1.0;
// Friction values used for linear damping. They are unitless quantities. The
// value of these quantities must be between zero and one. They represent the
// amount an object will slow down within 1/60th of a second. Eg. if the frction

View File

@ -77,6 +77,7 @@ impl<'a> System<'a> for Sys {
CharacterState::Idle { .. }
| CharacterState::Sit { .. }
| CharacterState::Dance { .. }
| CharacterState::Sneak { .. }
| CharacterState::Glide { .. }
| CharacterState::GlideWield { .. }
| CharacterState::Wielding { .. }

View File

@ -16,6 +16,7 @@ pub mod roll;
pub mod run;
pub mod shoot;
pub mod sit;
pub mod sneak;
pub mod spin;
pub mod spinmelee;
pub mod stand;
@ -29,8 +30,9 @@ pub use self::{
dance::DanceAnimation, dash::DashAnimation, equip::EquipAnimation,
glidewield::GlideWieldAnimation, gliding::GlidingAnimation, idle::IdleAnimation,
jump::JumpAnimation, leapmelee::LeapAnimation, roll::RollAnimation, run::RunAnimation,
shoot::ShootAnimation, sit::SitAnimation, spin::SpinAnimation, spinmelee::SpinMeleeAnimation,
stand::StandAnimation, swim::SwimAnimation, wield::WieldAnimation,
shoot::ShootAnimation, sit::SitAnimation, sneak::SneakAnimation, spin::SpinAnimation,
spinmelee::SpinMeleeAnimation, stand::StandAnimation, swim::SwimAnimation,
wield::WieldAnimation,
};
use super::{Bone, FigureBoneData, Skeleton};

View File

@ -0,0 +1,319 @@
use super::{super::Animation, CharacterSkeleton, SkeletonAttr};
use common::comp::item::ToolKind;
use std::{f32::consts::PI, ops::Mul};
use vek::*;
pub struct SneakAnimation;
impl Animation for SneakAnimation {
type Dependency = (Option<ToolKind>, Vec3<f32>, Vec3<f32>, Vec3<f32>, f64);
type Skeleton = CharacterSkeleton;
#[cfg(feature = "use-dyn-lib")]
const UPDATE_FN: &'static [u8] = b"character_sneak\0";
#[cfg_attr(feature = "be-dyn-lib", export_name = "character_sneak")]
#[allow(clippy::identity_conversion)] // TODO: Pending review in #587
fn update_skeleton_inner(
skeleton: &Self::Skeleton,
(_active_tool_kind, velocity, orientation, last_ori, global_time): Self::Dependency,
anim_time: f64,
rate: &mut f32,
skeleton_attr: &SkeletonAttr,
) -> Self::Skeleton {
let mut next = (*skeleton).clone();
let speed = Vec2::<f32>::from(velocity).magnitude();
*rate = 1.0;
let slow = (anim_time as f32 * 3.0).sin();
let breathe = ((anim_time as f32 * 0.5).sin()).abs();
let walkintensity = if speed > 5.0 { 1.0 } else { 0.45 };
let lower = if speed > 5.0 { 0.0 } else { 1.0 };
let _snapfoot = if speed > 5.0 { 1.1 } else { 2.0 };
let lab = 1.0;
let foothoril = (anim_time as f32 * 7.0 * lab as f32 + PI * 1.45).sin();
let foothorir = (anim_time as f32 * 7.0 * lab as f32 + PI * (0.45)).sin();
let footvertl = (anim_time as f32 * 7.0 * lab as f32).sin();
let footvertr = (anim_time as f32 * 7.0 * lab as f32 + PI).sin();
let footrotl = (((5.0)
/ (2.5
+ (2.5)
* ((anim_time as f32 * 7.0 * lab as f32 + PI * 1.4).sin()).powf(2.0 as f32)))
.sqrt())
* ((anim_time as f32 * 7.0 * lab as f32 + PI * 1.4).sin());
let footrotr = (((5.0)
/ (1.0
+ (4.0)
* ((anim_time as f32 * 7.0 * lab as f32 + PI * 0.4).sin()).powf(2.0 as f32)))
.sqrt())
* ((anim_time as f32 * 7.0 * lab as f32 + PI * 0.4).sin());
let short = (anim_time as f32 * lab as f32 * 7.0).sin();
let noisea = (anim_time as f32 * 11.0 + PI / 6.0).sin();
let noiseb = (anim_time as f32 * 19.0 + PI / 4.0).sin();
let shorte = (((5.0)
/ (4.0 + 1.0 * ((anim_time as f32 * lab as f32 * 7.0).sin()).powf(2.0 as f32)))
.sqrt())
* ((anim_time as f32 * lab as f32 * 7.0).sin());
let shortalt = (anim_time as f32 * lab as f32 * 7.0 + PI / 2.0).sin();
let head_look = Vec2::new(
((global_time + anim_time) as f32 / 18.0)
.floor()
.mul(7331.0)
.sin()
* 0.2,
((global_time + anim_time) as f32 / 18.0)
.floor()
.mul(1337.0)
.sin()
* 0.1,
);
let ori = Vec2::from(orientation);
let last_ori = Vec2::from(last_ori);
let tilt = if Vec2::new(ori, last_ori)
.map(|o| Vec2::<f32>::from(o).magnitude_squared())
.map(|m| m > 0.001 && m.is_finite())
.reduce_and()
&& ori.angle_between(last_ori).is_finite()
{
ori.angle_between(last_ori).min(0.2)
* last_ori.determine_side(Vec2::zero(), ori).signum()
} else {
0.0
} * 1.3;
if speed > 0.5 {
next.l_hand.offset = Vec3::new(
1.0 - skeleton_attr.hand.0,
4.0 + skeleton_attr.hand.1,
1.0 + skeleton_attr.hand.2,
);
next.l_hand.ori = Quaternion::rotation_x(1.0);
next.l_hand.scale = Vec3::one();
next.r_hand.offset = Vec3::new(
-1.0 + skeleton_attr.hand.0,
-1.0 + skeleton_attr.hand.1,
skeleton_attr.hand.2,
);
next.r_hand.ori = Quaternion::rotation_x(0.4);
next.r_hand.scale = Vec3::one();
next.head.offset = Vec3::new(
0.0,
-4.0 + skeleton_attr.head.0,
-1.0 + skeleton_attr.head.1 + short * 0.06,
);
next.head.ori = Quaternion::rotation_z(tilt * -2.5 + head_look.x * 0.2 - short * 0.06)
* Quaternion::rotation_x(head_look.y + 0.45);
next.head.scale = Vec3::one() * skeleton_attr.head_scale;
next.chest.offset = Vec3::new(
0.0,
skeleton_attr.chest.0,
-1.0 + skeleton_attr.chest.1 + shortalt * -0.5,
);
next.chest.ori = Quaternion::rotation_z(0.3 + short * 0.08 + tilt * -0.2)
* Quaternion::rotation_y(tilt * 0.8)
* Quaternion::rotation_x(-0.5);
next.chest.scale = Vec3::one();
next.belt.offset =
Vec3::new(0.0, 0.5 + skeleton_attr.belt.0, 0.7 + skeleton_attr.belt.1);
next.belt.ori = Quaternion::rotation_z(short * 0.1 + tilt * -1.1)
* Quaternion::rotation_y(tilt * 0.5)
* Quaternion::rotation_x(0.2);
next.belt.scale = Vec3::one();
next.glider.ori = Quaternion::rotation_x(0.0);
next.glider.offset = Vec3::new(0.0, 0.0, 10.0);
next.glider.scale = Vec3::one() * 0.0;
next.back.offset = Vec3::new(0.0, skeleton_attr.back.0, skeleton_attr.back.1);
next.back.ori =
Quaternion::rotation_x(-0.25 + short * 0.1 + noisea * 0.1 + noiseb * 0.1);
next.back.scale = Vec3::one() * 1.02;
next.shorts.offset = Vec3::new(
0.0,
1.0 + skeleton_attr.shorts.0,
1.0 + skeleton_attr.shorts.1,
);
next.shorts.ori = Quaternion::rotation_z(short * 0.16 + tilt * -1.5)
* Quaternion::rotation_y(tilt * 0.7)
* Quaternion::rotation_x(0.3);
next.shorts.scale = Vec3::one();
next.l_foot.offset = Vec3::new(
-skeleton_attr.foot.0,
skeleton_attr.foot.1 + foothoril * -10.5 * walkintensity - lower * 1.0,
1.0 + skeleton_attr.foot.2 + ((footvertl * -1.7).max(-1.0)) * walkintensity,
);
next.l_foot.ori = Quaternion::rotation_x(-0.2 + footrotl * -0.8 * walkintensity)
* Quaternion::rotation_y(tilt * 1.8);
next.l_foot.scale = Vec3::one();
next.r_foot.offset = Vec3::new(
skeleton_attr.foot.0,
skeleton_attr.foot.1 + foothorir * -10.5 * walkintensity - lower * 1.0,
1.0 + skeleton_attr.foot.2 + ((footvertr * -1.7).max(-1.0)) * walkintensity,
);
next.r_foot.ori = Quaternion::rotation_x(-0.2 + footrotr * -0.8 * walkintensity)
* Quaternion::rotation_y(tilt * 1.8);
next.r_foot.scale = Vec3::one();
next.l_shoulder.offset = Vec3::new(
-skeleton_attr.shoulder.0,
skeleton_attr.shoulder.1,
skeleton_attr.shoulder.2,
);
next.l_shoulder.ori = Quaternion::rotation_x(short * 0.15 * walkintensity);
next.l_shoulder.scale = Vec3::one() * 1.1;
next.r_shoulder.offset = Vec3::new(
skeleton_attr.shoulder.0,
skeleton_attr.shoulder.1,
skeleton_attr.shoulder.2,
);
next.r_shoulder.ori = Quaternion::rotation_x(short * -0.15 * walkintensity);
next.r_shoulder.scale = Vec3::one() * 1.1;
next.main.offset = Vec3::new(-7.0, -6.5, 15.0);
next.main.ori = Quaternion::rotation_y(2.5) * Quaternion::rotation_z(1.57);
next.main.scale = Vec3::one();
next.second.scale = Vec3::one() * 0.0;
next.lantern.offset = Vec3::new(
skeleton_attr.lantern.0,
skeleton_attr.lantern.1,
skeleton_attr.lantern.2,
);
next.lantern.ori =
Quaternion::rotation_x(shorte * 0.2 + 0.4) * Quaternion::rotation_y(shorte * 0.1);
next.lantern.scale = Vec3::one() * 0.65;
next.torso.offset = Vec3::new(0.0, 0.0, 0.0) * skeleton_attr.scaler;
next.torso.ori = Quaternion::rotation_y(0.0);
next.torso.scale = Vec3::one() / 11.0 * skeleton_attr.scaler;
next.control.offset = Vec3::new(0.0, 0.0, 0.0);
next.control.ori = Quaternion::rotation_x(0.0);
next.control.scale = Vec3::one();
next.l_control.scale = Vec3::one();
next.r_control.scale = Vec3::one();
} else {
next.head.offset = Vec3::new(
0.0,
-4.0 + skeleton_attr.head.0,
-2.0 + skeleton_attr.head.1 + slow * 0.1 + breathe * -0.05,
);
next.head.ori = Quaternion::rotation_z(head_look.x)
* Quaternion::rotation_x(0.6 + head_look.y.abs());
next.head.scale = Vec3::one() * skeleton_attr.head_scale + breathe * -0.05;
next.chest.offset = Vec3::new(
0.0,
skeleton_attr.chest.0,
-3.0 + skeleton_attr.chest.1 + slow * 0.1,
);
next.chest.ori = Quaternion::rotation_x(-0.7);
next.chest.scale = Vec3::one() * 1.01 + breathe * 0.03;
next.belt.offset = Vec3::new(0.0, skeleton_attr.belt.0, skeleton_attr.belt.1);
next.belt.ori = Quaternion::rotation_z(0.3 + head_look.x * -0.1);
next.belt.scale = Vec3::one() + breathe * -0.03;
next.l_hand.offset = Vec3::new(
1.0 - skeleton_attr.hand.0,
5.0 + skeleton_attr.hand.1,
0.0 + skeleton_attr.hand.2,
);
next.l_hand.ori = Quaternion::rotation_x(1.35);
next.l_hand.scale = Vec3::one();
next.r_hand.offset = Vec3::new(
-1.0 + skeleton_attr.hand.0,
skeleton_attr.hand.1,
skeleton_attr.hand.2,
);
next.r_hand.ori = Quaternion::rotation_x(0.4);
next.r_hand.scale = Vec3::one();
next.glider.ori = Quaternion::rotation_x(0.35);
next.glider.offset = Vec3::new(0.0, 0.0, 10.0);
next.glider.scale = Vec3::one() * 0.0;
next.back.offset = Vec3::new(0.0, skeleton_attr.back.0, skeleton_attr.back.1);
next.back.scale = Vec3::one() * 1.02;
next.shorts.offset = Vec3::new(0.0, skeleton_attr.shorts.0, skeleton_attr.shorts.1);
next.shorts.ori = Quaternion::rotation_z(0.6 + head_look.x * -0.2);
next.shorts.scale = Vec3::one() + breathe * -0.03;
next.l_foot.offset = Vec3::new(
-skeleton_attr.foot.0,
-6.0 + skeleton_attr.foot.1,
1.0 + skeleton_attr.foot.2,
);
next.l_foot.ori = Quaternion::rotation_x(-0.5);
next.l_foot.scale = Vec3::one();
next.r_foot.offset = Vec3::new(
skeleton_attr.foot.0,
4.0 + skeleton_attr.foot.1,
skeleton_attr.foot.2,
);
next.r_foot.ori = Quaternion::rotation_x(0.0);
next.r_foot.scale = Vec3::one();
next.l_shoulder.offset = Vec3::new(
-skeleton_attr.shoulder.0,
skeleton_attr.shoulder.1,
skeleton_attr.shoulder.2,
);
next.l_shoulder.scale = (Vec3::one() + breathe * -0.05) * 1.15;
next.r_shoulder.offset = Vec3::new(
skeleton_attr.shoulder.0,
skeleton_attr.shoulder.1,
skeleton_attr.shoulder.2,
);
next.r_shoulder.scale = (Vec3::one() + breathe * -0.05) * 1.15;
next.main.offset = Vec3::new(-7.0, -5.0, 15.0);
next.main.ori = Quaternion::rotation_y(2.5) * Quaternion::rotation_z(1.57);
next.main.scale = Vec3::one();
next.second.offset = Vec3::new(0.0, 0.0, 0.0);
next.second.scale = Vec3::one() * 0.0;
next.lantern.offset = Vec3::new(
skeleton_attr.lantern.0,
skeleton_attr.lantern.1,
skeleton_attr.lantern.2,
);
next.lantern.ori = Quaternion::rotation_x(0.1) * Quaternion::rotation_y(0.1);
next.lantern.scale = Vec3::one() * 0.65;
next.torso.offset = Vec3::new(0.0, 0.0, 0.0) * skeleton_attr.scaler;
next.torso.ori = Quaternion::rotation_x(0.0);
next.torso.scale = Vec3::one() / 11.0 * skeleton_attr.scaler;
next.control.scale = Vec3::one();
next.l_control.scale = Vec3::one();
next.r_control.scale = Vec3::one();
}
next
}
}

View File

@ -42,12 +42,8 @@ impl Animation for SwimAnimation {
let short = (anim_time as f32 * lab as f32 * 6.0).sin();
let shortalt = (anim_time as f32 * lab as f32 * 6.0 + PI / 2.0).sin();
let foot = (anim_time as f32 * lab as f32 * 6.0).sin();
let wave_stop = (anim_time as f32 * 9.0).min(PI / 2.0 / 2.0).sin();
let footrotl = (((1.0)
/ (0.2
+ (0.8)
@ -146,7 +142,7 @@ impl Animation for SwimAnimation {
next.l_foot.offset = Vec3::new(
-skeleton_attr.foot.0,
skeleton_attr.foot.1 + foothorir * 1.5 * intensity,
skeleton_attr.foot.1 + foothoril * 1.5 * intensity,
-15.0 + skeleton_attr.foot.2 + footrotl * 3.0 * intensity,
);
next.l_foot.ori = Quaternion::rotation_x(-0.8 + footrotl * 0.4 * intensity);

View File

@ -142,7 +142,7 @@ impl<'a> From<&'a comp::quadruped_low::Body> for SkeletonAttr {
(Tortoise, _) => (5.0, 1.0),
(Rocksnapper, _) => (6.0, 0.5),
(Pangolin, _) => (-0.5, 8.0),
(Maneater, _) => (6.0, 9.5),
(Maneater, _) => (7.0, 11.5),
},
head_lower: match (body.species, body.body_type) {
(Crocodile, _) => (8.0, 0.0),

View File

@ -209,7 +209,7 @@ impl<'a> From<&'a comp::quadruped_medium::Body> for SkeletonAttr {
(Wolf, _) => (5.0, -3.0),
(Frostfang, _) => (4.0, -3.0),
(Mouflon, _) => (10.5, -4.0),
(Catoblepas, _) => (1.0, -6.0),
(Catoblepas, _) => (1.0, -4.0),
(Bonerattler, _) => (3.0, -3.0),
},
tail: match (body.species, body.body_type) {

View File

@ -10,6 +10,7 @@ pub struct KeyState {
pub toggle_wield: bool,
pub toggle_glide: bool,
pub toggle_sit: bool,
pub toggle_sneak: bool,
pub toggle_dance: bool,
pub auto_walk: bool,
pub swap_loadout: bool,
@ -30,6 +31,7 @@ impl Default for KeyState {
toggle_wield: false,
toggle_glide: false,
toggle_sit: false,
toggle_sneak: false,
toggle_dance: false,
auto_walk: false,
swap_loadout: false,

View File

@ -720,6 +720,15 @@ impl FigureMgr {
)
}
},
CharacterState::Sneak { .. } => {
anim::character::SneakAnimation::update_skeleton(
&CharacterSkeleton::new(),
(active_tool_kind, vel.0, ori, state.last_ori, time),
state.state_time,
&mut state_animation_rate,
skeleton_attr,
)
},
CharacterState::Boost(_) => {
anim::character::AlphaAnimation::update_skeleton(
&target_base,

View File

@ -347,6 +347,15 @@ impl PlayState for SessionState {
self.client.borrow_mut().toggle_dance();
}
}
Event::InputUpdate(GameInput::Sneak, state)
if state != self.key_state.toggle_sneak =>
{
self.key_state.toggle_sneak = state;
if state {
self.stop_auto_walk();
self.client.borrow_mut().toggle_sneak();
}
}
Event::InputUpdate(GameInput::MoveForward, state) => {
if state && global_state.settings.gameplay.stop_auto_walk_on_input {
self.stop_auto_walk();

View File

@ -136,6 +136,7 @@ impl ControlSettings {
GameInput::ClimbDown => KeyMouse::Key(VirtualKeyCode::LControl),
GameInput::SwimUp => KeyMouse::Key(VirtualKeyCode::Space),
GameInput::SwimDown => KeyMouse::Key(VirtualKeyCode::LShift),
GameInput::Sneak => KeyMouse::Key(VirtualKeyCode::LControl),
//GameInput::WallLeap => MIDDLE_CLICK_KEY,
GameInput::ToggleLantern => KeyMouse::Key(VirtualKeyCode::G),
GameInput::Mount => KeyMouse::Key(VirtualKeyCode::F),
@ -202,6 +203,7 @@ impl Default for ControlSettings {
GameInput::ClimbDown,
GameInput::SwimUp,
GameInput::SwimDown,
GameInput::Sneak,
//GameInput::WallLeap,
GameInput::ToggleLantern,
GameInput::Mount,
@ -312,6 +314,7 @@ pub mod con_settings {
pub climb_down: Button,
pub swimup: Button,
pub swimdown: Button,
pub sneak: Button,
//pub wall_leap: Button,
pub toggle_lantern: Button,
pub mount: Button,
@ -403,6 +406,7 @@ pub mod con_settings {
climb_down: Button::Simple(GilButton::Unknown),
swimup: Button::Simple(GilButton::South),
swimdown: Button::Simple(GilButton::Unknown),
sneak: Button::Simple(GilButton::Unknown),
//wall_leap: Button::Simple(GilButton::Unknown),
toggle_lantern: Button::Simple(GilButton::East),
mount: Button::Simple(GilButton::North),

View File

@ -41,6 +41,7 @@ pub enum GameInput {
ClimbDown,
SwimUp,
SwimDown,
Sneak,
//WallLeap,
ToggleLantern,
Mount,
@ -91,6 +92,7 @@ impl GameInput {
GameInput::ClimbDown => "gameinput.climbdown",
GameInput::SwimUp => "gameinput.swimup",
GameInput::SwimDown => "gameinput.swimdown",
GameInput::Sneak => "gameinput.sneak",
//GameInput::WallLeap => "gameinput.wallleap",
GameInput::ToggleLantern => "gameinput.togglelantern",
GameInput::Mount => "gameinput.mount",
@ -151,6 +153,7 @@ impl GameInput {
GameInput::ClimbDown,
GameInput::SwimUp,
GameInput::SwimDown,
GameInput::Sneak,
GameInput::ToggleLantern,
GameInput::Mount,
GameInput::Enter,