diff --git a/pumpkin/src/client/player_packet.rs b/pumpkin/src/client/player_packet.rs index 64bf0d5f2..dc49458e7 100644 --- a/pumpkin/src/client/player_packet.rs +++ b/pumpkin/src/client/player_packet.rs @@ -183,18 +183,34 @@ impl Player { self.on_ground = ground.on_ground; } - pub fn handle_player_command(&mut self, _server: &mut Server, command: SPlayerCommand) { + pub fn handle_player_command(&mut self, server: &mut Server, command: SPlayerCommand) { if command.entity_id != self.entity.entity_id.into() { return; } if let Some(action) = Action::from_i32(command.action.0) { match action { - pumpkin_protocol::server::play::Action::StartSneaking => self.sneaking = true, - pumpkin_protocol::server::play::Action::StopSneaking => self.sneaking = false, + pumpkin_protocol::server::play::Action::StartSneaking => { + if !self.sneaking { + self.set_sneaking(server, true) + } + } + pumpkin_protocol::server::play::Action::StopSneaking => { + if self.sneaking { + self.set_sneaking(server, false) + } + } pumpkin_protocol::server::play::Action::LeaveBed => todo!(), - pumpkin_protocol::server::play::Action::StartSprinting => self.sprinting = true, - pumpkin_protocol::server::play::Action::StopSprinting => self.sprinting = false, + pumpkin_protocol::server::play::Action::StartSprinting => { + if !self.sprinting { + self.set_sprinting(server, true) + } + } + pumpkin_protocol::server::play::Action::StopSprinting => { + if self.sprinting { + self.set_sprinting(server, false) + } + } pumpkin_protocol::server::play::Action::StartHorseJump => todo!(), pumpkin_protocol::server::play::Action::StopHorseJump => todo!(), pumpkin_protocol::server::play::Action::OpenVehicleInventory => todo!(), @@ -290,6 +306,10 @@ impl Player { } pub fn handle_interact(&mut self, server: &mut Server, interact: SInteract) { + let sneaking = interact.sneaking; + if self.sneaking != sneaking { + self.set_sneaking(server, sneaking); + } match ActionType::from_i32(interact.typ.0) { Some(action) => match action { ActionType::Attack => { @@ -298,7 +318,6 @@ impl Player { let config = &server.advanced_config.pvp; if config.enabled { let attacked_player = server.get_by_entityid(self, entity_id.0 as EntityId); - self.sneaking = interact.sneaking; if let Some(mut player) = attacked_player { let token = player.client.token.clone(); let velo = player.velocity; diff --git a/pumpkin/src/commands/cmd_gamemode.rs b/pumpkin/src/commands/cmd_gamemode.rs index a55743889..767de2254 100644 --- a/pumpkin/src/commands/cmd_gamemode.rs +++ b/pumpkin/src/commands/cmd_gamemode.rs @@ -65,7 +65,6 @@ pub(crate) fn init_command_tree<'a>() -> CommandTree<'a> { let gamemode = parse_arg_gamemode(args)?; return if let Player(target) = sender { - dbg!("1"); if target.gamemode == gamemode { target.send_system_message(TextComponent::text(&format!( "You already in {:?} gamemode", diff --git a/pumpkin/src/entity/player.rs b/pumpkin/src/entity/player.rs index 970c22b0a..c2771a97a 100644 --- a/pumpkin/src/entity/player.rs +++ b/pumpkin/src/entity/player.rs @@ -167,13 +167,54 @@ impl Player { )); } - pub fn set_pose(&mut self, pose: EntityPose) { + pub fn set_sneaking(&mut self, server: &mut Server, sneaking: bool) { + assert!(self.sneaking != sneaking); + self.sneaking = sneaking; + self.set_flag(server, Self::SNEAKING_FLAG_INDEX, sneaking); + if sneaking { + self.set_pose(server, EntityPose::Crouching); + } else { + self.set_pose(server, EntityPose::Standing); + } + } + + pub fn set_sprinting(&mut self, server: &mut Server, sprinting: bool) { + assert!(self.sprinting != sprinting); + self.sprinting = sprinting; + self.set_flag(server, Self::SPRINTING_FLAG_INDEX, sprinting); + } + + pub const ON_FIRE_FLAG_INDEX: u32 = 0; + pub const SNEAKING_FLAG_INDEX: u32 = 1; + pub const SPRINTING_FLAG_INDEX: u32 = 3; + pub const SWIMMING_FLAG_INDEX: u32 = 4; + pub const INVISIBLE_FLAG_INDEX: u32 = 5; + pub const GLOWING_FLAG_INDEX: u32 = 6; + pub const FALL_FLYING_FLAG_INDEX: u32 = 7; + fn set_flag(&mut self, server: &mut Server, index: u32, value: bool) { + let mut b = 0i8; + if value { + b |= 1 << index; + } else { + b &= !(1 << index); + } + server.broadcast_packet( + self, + &CSetEntityMetadata::new(self.entity_id().into(), Metadata::new(0, 0.into(), b)), + ); + } + + pub fn set_pose(&mut self, server: &mut Server, pose: EntityPose) { self.entity.pose = pose; let pose = self.entity.pose as i32; - self.client.send_packet(&CSetEntityMetadata::::new( - self.entity_id().into(), - Metadata::new(6, 10.into(), (pose).into()), - )) + dbg!(pose); + server.broadcast_packet( + self, + &CSetEntityMetadata::::new( + self.entity_id().into(), + Metadata::new(6, 20.into(), (pose).into()), + ), + ) } pub fn teleport(&mut self, x: f64, y: f64, z: f64, yaw: f32, pitch: f32) {