1
2
Fork 0
mirror of https://github.com/mat-1/azalea.git synced 2025-08-02 14:26:04 +00:00

start fixing some packets

This commit is contained in:
Ubuntu 2023-01-07 01:05:27 +00:00
parent cf7b2423d0
commit 590a5ded8d
7 changed files with 70 additions and 67 deletions

1
Cargo.lock generated
View file

@ -280,6 +280,7 @@ dependencies = [
"azalea-world",
"bevy_app",
"bevy_ecs",
"derive_more",
"futures",
"iyes_loopless",
"log",

View file

@ -11,25 +11,26 @@ version = "0.5.0"
[dependencies]
anyhow = "1.0.59"
async-trait = "0.1.58"
azalea-auth = {path = "../azalea-auth", version = "0.5.0"}
azalea-block = {path = "../azalea-block", version = "0.5.0"}
azalea-chat = {path = "../azalea-chat", version = "0.5.0"}
azalea-core = {path = "../azalea-core", version = "0.5.0"}
azalea-crypto = {path = "../azalea-crypto", version = "0.5.0"}
azalea-physics = {path = "../azalea-physics", version = "0.5.0"}
azalea-protocol = {path = "../azalea-protocol", version = "0.5.0"}
azalea-registry = {path = "../azalea-registry", version = "0.5.0"}
azalea-world = {path = "../azalea-world", version = "0.5.0"}
bevy_app = {version = "0.9.1", default-features = false}
bevy_ecs = {version = "0.9.1", default-features = false}
azalea-auth = { path = "../azalea-auth", version = "0.5.0" }
azalea-block = { path = "../azalea-block", version = "0.5.0" }
azalea-chat = { path = "../azalea-chat", version = "0.5.0" }
azalea-core = { path = "../azalea-core", version = "0.5.0" }
azalea-crypto = { path = "../azalea-crypto", version = "0.5.0" }
azalea-physics = { path = "../azalea-physics", version = "0.5.0" }
azalea-protocol = { path = "../azalea-protocol", version = "0.5.0" }
azalea-registry = { path = "../azalea-registry", version = "0.5.0" }
azalea-world = { path = "../azalea-world", version = "0.5.0" }
bevy_app = { version = "0.9.1", default-features = false }
bevy_ecs = { version = "0.9.1", default-features = false }
futures = "0.3.25"
iyes_loopless = "0.9.1"
log = "0.4.17"
nohash-hasher = "0.2.0"
once_cell = "1.16.0"
parking_lot = {version = "^0.12.1", features = ["deadlock_detection"]}
parking_lot = { version = "^0.12.1", features = ["deadlock_detection"] }
regex = "1.7.0"
thiserror = "^1.0.34"
tokio = {version = "^1.21.2", features = ["sync"]}
tokio = { version = "^1.21.2", features = ["sync"] }
typemap_rev = "0.2.0"
uuid = "^1.1.2"
derive_more = { version = "0.99.17", features = ["deref", "deref_mut"] }

View file

@ -1,4 +1,9 @@
use std::{collections::HashMap, io, sync::Arc};
use std::{
collections::HashMap,
io,
ops::{Deref, DerefMut},
sync::Arc,
};
use azalea_auth::game_profile::GameProfile;
use azalea_core::{ChunkPos, ResourceLocation};
@ -8,6 +13,7 @@ use azalea_world::{
EntityInfos, PartialWorld, World,
};
use bevy_ecs::{component::Component, system::Query};
use derive_more::{Deref, DerefMut};
use parking_lot::RwLock;
use thiserror::Error;
use tokio::sync::mpsc;
@ -25,7 +31,6 @@ pub struct LocalPlayer {
// pub world: Arc<RwLock<PartialWorld>>,
pub physics_state: PhysicsState,
pub client_information: ClientInformation,
pub dead: bool,
/// A map of player uuids to their information in the tab list
pub players: HashMap<Uuid, PlayerInfo>,
@ -36,6 +41,10 @@ pub struct LocalPlayer {
pub tx: mpsc::UnboundedSender<Event>,
}
/// Present if the player can be dead.
#[derive(Component, Copy, Clone, Default, Deref, DerefMut)]
pub struct Dead(bool);
#[derive(Default)]
pub struct PhysicsState {
/// Minecraft only sends a movement packet either after 20 ticks or if the

View file

@ -4,11 +4,14 @@ use azalea_protocol::{
connect::{ReadConnection, WriteConnection},
packets::game::{ClientboundGamePacket, ServerboundGamePacket},
};
use azalea_world::{entity::{MinecraftEntityId, Position}, EntityInfos};
use bevy_ecs::{component::Component, prelude::Entity, query::Changed, system::Query};
use log::{error, debug};
use parking_lot::Mutex;
use tokio::sync::mpsc;
use crate::{local_player::{Dead, LocalPlayer}, Event};
/// Something that receives packets from the server.
#[derive(Component, Clone)]
pub struct PacketReceiver {
@ -24,12 +27,12 @@ pub fn handle_packets(
for (entity, packet_events) in query.iter_mut(ecs) {
for packet in packet_events.packets.lock().iter() {
handle_packet(entity, packet);
handle_packet(ecs, entity, packet);
}
}
}
pub fn handle_packet(entity: Entity, packet: &ClientboundGamePacket) {
pub fn handle_packet(ecs: &mut bevy_ecs::world::World, entity: Entity, packet: &ClientboundGamePacket) {
match packet {
ClientboundGamePacket::Login(p) => {
debug!("Got login packet");
@ -458,13 +461,18 @@ pub fn handle_packet(entity: Entity, packet: &ClientboundGamePacket) {
// debug!("Got rotate head packet {:?}", p);
}
ClientboundGamePacket::MoveEntityPos(p) => {
let mut world = client.world.write();
let _ = world.move_entity_with_delta(EntityId(p.entity_id),
&p.delta); }
let mut local_player = ecs.query::<&mut LocalPlayer>().get_mut(ecs, entity).unwrap();
let mut partial_entity_infos = local_player.partial_world.write().entity_infos;
let entity = partial_entity_infos.entity_by_id(p.entity_id);
let mut position = ecs.query::<&mut Position>().get_mut(ecs, entity).unwrap();
**position = position.with_delta(&p.delta);
},
ClientboundGamePacket::MoveEntityPosRot(p) => {
let mut world = client.world.write();
let _ = world.move_entity_with_delta(EntityId(p.entity_id),
&p.delta); }
let entity_infos = ecs.resource::<EntityInfos>();
let entity = entity_infos.entity_by_id(p.entity_id);
let mut position = ecs.query::<&mut Position>().get_mut(ecs, entity).unwrap();
**position += p.delta;
}
ClientboundGamePacket::MoveEntityRot(_p) => {
// debug!("Got move entity rot packet {:?}", p);
}
@ -551,13 +559,11 @@ pub fn handle_packet(entity: Entity, packet: &ClientboundGamePacket) {
ClientboundGamePacket::PlayerCombatEnter(_) => {}
ClientboundGamePacket::PlayerCombatKill(p) => {
debug!("Got player kill packet {:?}", p);
let entity_id =
if client.entity() == EntityId(p.player_id) {
// we can't define a variable here with client.dead.lock()
// because of https://github.com/rust-lang/rust/issues/57478
if !*client.dead.lock() {
*client.dead.lock() = true;
tx.send(Event::Death(Some(Arc::new(p.clone())))).await?;
let (entity_id, mut dead, mut local_player) = ecs.query::<(&MinecraftEntityId, &mut Dead, &mut LocalPlayer)>().get(ecs, entity).unwrap();
if **entity_id == p.player_id {
if !**dead {
**dead = true;
local_player.tx.send(Event::Death(Some(Arc::new(p.clone()))));
}
}
}
@ -567,8 +573,8 @@ pub fn handle_packet(entity: Entity, packet: &ClientboundGamePacket) {
ClientboundGamePacket::Respawn(p) => {
debug!("Got respawn packet {:?}", p);
// Sets clients dead state to false.
let mut dead_lock = client.dead.lock();
*dead_lock = false;
let mut dead = ecs.query::<&mut Dead>().get(ecs, entity).unwrap();
**dead = false;
}
ClientboundGamePacket::SelectAdvancementsTab(_) => {}
ClientboundGamePacket::SetActionBarText(_) => {}

View file

@ -149,8 +149,9 @@ pub fn on_pos(
pub struct EntityUuid(Uuid);
/// The position of the entity right now.
/// This can be changed with unsafe_move, but the correct way is with
/// world.move_entity
///
/// You are free to change this; there's systems that update the indexes
/// automatically.
#[derive(Component, Clone, Copy, Debug, Default, PartialEq, Deref, DerefMut)]
pub struct Position(Vec3);
impl From<Position> for ChunkPos {

View file

@ -11,12 +11,7 @@ use bevy_ecs::{
};
use log::warn;
use nohash_hasher::{IntMap, IntSet};
use once_cell::sync::Lazy;
use std::{
collections::{HashMap, HashSet},
fmt::Debug,
ops::DerefMut,
};
use std::{collections::HashMap, fmt::Debug, ops::DerefMut};
use uuid::Uuid;
/// Plugin handling some basic entity functionality.
@ -74,6 +69,9 @@ pub struct PartialEntityInfos {
pub updates_received: IntMap<MinecraftEntityId, u32>,
/// A set of all the entity ids in render distance.
pub(crate) loaded_entity_ids: IntSet<MinecraftEntityId>,
/// A map of Minecraft entity ids to Azalea ECS entities.
pub(crate) entity_by_id: IntMap<u32, Entity>,
}
impl PartialEntityInfos {
@ -85,33 +83,22 @@ impl PartialEntityInfos {
owner_entity,
updates_received: IntMap::default(),
loaded_entity_ids: IntSet::default(),
entity_by_id: IntMap::default(),
}
}
/// Whether the entity with the given id is being loaded by this storage.
/// If you want to check whether the entity is in the shared storage, use
/// [`WeakEntityStorage::contains_id`].
/// Whether the entity with the given protocol ID is being loaded by this
/// storage.
#[inline]
pub fn limited_contains_id(&self, id: MinecraftEntityId) -> bool {
pub fn contains_id(&self, id: MinecraftEntityId) -> bool {
self.loaded_entity_ids.contains(&id)
}
/// Get an [`Entity`] from the given [`MinecraftEntityId`] (which is just a
/// u32 internally) if the entity is being loaded by this storage.
#[inline]
pub fn limited_get_by_id(
&self,
id: MinecraftEntityId,
entity_infos: &mut EntityInfos,
) -> Option<Entity> {
if self.limited_contains_id(id) {
entity_infos
.minecraft_entity_ids_to_azalea_entities
.get(&id)
.copied()
} else {
None
}
pub fn get_by_id(&self, id: MinecraftEntityId) -> Option<Entity> {
self.entity_by_id.get(&id).copied()
}
/// Returns whether we're allowed to update this entity (to prevent two
@ -163,9 +150,6 @@ pub struct EntityInfos {
/// The canonical number of updates we've gotten for every entity.
pub updates_received: HashMap<Entity, u32>,
/// The map of Minecraft entity ids to Azalea ECS entities.
pub minecraft_entity_ids_to_azalea_entities: HashMap<u32, Entity>,
}
impl EntityInfos {
@ -174,8 +158,6 @@ impl EntityInfos {
entity_reference_count: HashMap::default(),
entity_by_uuid: HashMap::default(),
updates_received: HashMap::default(),
minecraft_entity_ids_to_azalea_entities: HashMap::default(),
}
}
@ -224,6 +206,14 @@ impl EntityInfos {
self.entity_reference_count.contains_key(&id)
}
/// Get an [`Entity`] by its UUID.
///
/// If you want to get an entity by its protocol ID, use
/// [`PartialEntityInfos::entity_by_id`].
///
/// Also note that if you're using a shared world (i.e. a client swarm),
/// this function might return the wrong entity if there's multiple
/// entities with the same uuid in different worlds.
pub fn entity_by_uuid(&self, uuid: &Uuid) -> Option<&Entity> {
self.entity_by_uuid.get(uuid)
}

View file

@ -95,11 +95,6 @@ impl PartialWorld {
}
}
pub unsafe fn move_entity_with_delta(delta: &PositionDelta8, position: &mut entity::Position) {
let new_pos = position.with_delta(delta);
**position = new_pos;
}
/// A component marker signifying that the entity may have been removed from the
/// world, but we're not entirely sure.
#[derive(Component)]