From 62de0816e0c1bf0f71400cb9f62896e393256bae Mon Sep 17 00:00:00 2001 From: Avi Weinstock Date: Tue, 16 Mar 2021 11:55:01 -0400 Subject: [PATCH] Apply ForcedUpdate messages to the interpolation system, potentially improving the handling of teleports. --- common/net/src/msg/ecs_packet.rs | 28 ++++++++++++++++++++-------- common/net/src/sync/interpolation.rs | 28 +++++++++++++++++++++------- common/net/src/sync/packet.rs | 18 ++++++++++++------ common/net/src/sync/sync_ext.rs | 13 +++++++++---- 4 files changed, 62 insertions(+), 25 deletions(-) diff --git a/common/net/src/msg/ecs_packet.rs b/common/net/src/msg/ecs_packet.rs index 86049f7103..7066667fbe 100644 --- a/common/net/src/msg/ecs_packet.rs +++ b/common/net/src/msg/ecs_packet.rs @@ -76,7 +76,7 @@ sum_type! { impl sync::CompPacket for EcsCompPacket { type Phantom = EcsCompPhantom; - fn apply_insert(self, entity: specs::Entity, world: &specs::World) { + fn apply_insert(self, entity: specs::Entity, world: &specs::World, force_update: bool) { match self { EcsCompPacket::Body(comp) => sync::handle_insert(comp, entity, world), EcsCompPacket::Player(comp) => sync::handle_insert(comp, entity, world), @@ -100,15 +100,21 @@ impl sync::CompPacket for EcsCompPacket { EcsCompPacket::Gravity(comp) => sync::handle_insert(comp, entity, world), EcsCompPacket::Sticky(comp) => sync::handle_insert(comp, entity, world), EcsCompPacket::CharacterState(comp) => sync::handle_insert(comp, entity, world), - EcsCompPacket::Pos(comp) => sync::handle_interp_insert(comp, entity, world), - EcsCompPacket::Vel(comp) => sync::handle_interp_insert(comp, entity, world), - EcsCompPacket::Ori(comp) => sync::handle_interp_insert(comp, entity, world), + EcsCompPacket::Pos(comp) => { + sync::handle_interp_insert(comp, entity, world, force_update) + }, + EcsCompPacket::Vel(comp) => { + sync::handle_interp_insert(comp, entity, world, force_update) + }, + EcsCompPacket::Ori(comp) => { + sync::handle_interp_insert(comp, entity, world, force_update) + }, EcsCompPacket::Shockwave(comp) => sync::handle_insert(comp, entity, world), EcsCompPacket::BeamSegment(comp) => sync::handle_insert(comp, entity, world), } } - fn apply_modify(self, entity: specs::Entity, world: &specs::World) { + fn apply_modify(self, entity: specs::Entity, world: &specs::World, force_update: bool) { match self { EcsCompPacket::Body(comp) => sync::handle_modify(comp, entity, world), EcsCompPacket::Player(comp) => sync::handle_modify(comp, entity, world), @@ -132,9 +138,15 @@ impl sync::CompPacket for EcsCompPacket { EcsCompPacket::Gravity(comp) => sync::handle_modify(comp, entity, world), EcsCompPacket::Sticky(comp) => sync::handle_modify(comp, entity, world), EcsCompPacket::CharacterState(comp) => sync::handle_modify(comp, entity, world), - EcsCompPacket::Pos(comp) => sync::handle_interp_modify(comp, entity, world), - EcsCompPacket::Vel(comp) => sync::handle_interp_modify(comp, entity, world), - EcsCompPacket::Ori(comp) => sync::handle_interp_modify(comp, entity, world), + EcsCompPacket::Pos(comp) => { + sync::handle_interp_modify(comp, entity, world, force_update) + }, + EcsCompPacket::Vel(comp) => { + sync::handle_interp_modify(comp, entity, world, force_update) + }, + EcsCompPacket::Ori(comp) => { + sync::handle_interp_modify(comp, entity, world, force_update) + }, EcsCompPacket::Shockwave(comp) => sync::handle_modify(comp, entity, world), EcsCompPacket::BeamSegment(comp) => sync::handle_modify(comp, entity, world), } diff --git a/common/net/src/sync/interpolation.rs b/common/net/src/sync/interpolation.rs index 2b2207ad09..5f24f657a7 100644 --- a/common/net/src/sync/interpolation.rs +++ b/common/net/src/sync/interpolation.rs @@ -14,7 +14,7 @@ pub struct InterpBuffer { pub i: usize, } -impl InterpBuffer { +impl InterpBuffer { fn push(&mut self, time: f64, x: T) { let InterpBuffer { ref mut buf, @@ -24,6 +24,20 @@ impl InterpBuffer { *i %= buf.len(); buf[*i] = (time, x); } + + fn force_update(&mut self, time: f64, x: T) { + for i in 0..self.buf.len() { + self.buf[i] = (time, x.clone()); + } + } + + fn update(&mut self, time: f64, x: T, force_update: bool) { + if force_update { + self.force_update(time, x); + } else { + self.push(time, x); + } + } } impl Component for InterpBuffer { @@ -40,8 +54,8 @@ impl InterpolatableComponent for Pos { type InterpData = InterpBuffer; type ReadData = InterpBuffer; - fn update_component(&self, interp_data: &mut Self::InterpData, time: f64) { - interp_data.push(time, *self); + fn update_component(&self, interp_data: &mut Self::InterpData, time: f64, force_update: bool) { + interp_data.update(time, *self, force_update); } fn interpolate(self, interp_data: &Self::InterpData, t2: f64, vel: &InterpBuffer) -> Self { @@ -94,8 +108,8 @@ impl InterpolatableComponent for Vel { type InterpData = InterpBuffer; type ReadData = (); - fn update_component(&self, interp_data: &mut Self::InterpData, time: f64) { - interp_data.push(time, *self); + fn update_component(&self, interp_data: &mut Self::InterpData, time: f64, force_update: bool) { + interp_data.update(time, *self, force_update); } fn interpolate(self, interp_data: &Self::InterpData, t2: f64, _: &()) -> Self { @@ -129,8 +143,8 @@ impl InterpolatableComponent for Ori { type InterpData = InterpBuffer; type ReadData = (); - fn update_component(&self, interp_data: &mut Self::InterpData, time: f64) { - interp_data.push(time, *self); + fn update_component(&self, interp_data: &mut Self::InterpData, time: f64, force_update: bool) { + interp_data.update(time, *self, force_update); } fn interpolate(self, interp_data: &Self::InterpData, t2: f64, _: &()) -> Self { diff --git a/common/net/src/sync/packet.rs b/common/net/src/sync/packet.rs index 152b7946d6..af4727dec2 100644 --- a/common/net/src/sync/packet.rs +++ b/common/net/src/sync/packet.rs @@ -19,8 +19,8 @@ use tracing::error; pub trait CompPacket: Clone + Debug + Send + 'static { type Phantom: Clone + Debug + Serialize + DeserializeOwned; - fn apply_insert(self, entity: Entity, world: &World); - fn apply_modify(self, entity: Entity, world: &World); + fn apply_insert(self, entity: Entity, world: &World, force_update: bool); + fn apply_modify(self, entity: Entity, world: &World, force_update: bool); fn apply_remove(phantom: Self::Phantom, entity: Entity, world: &World); } @@ -50,14 +50,19 @@ pub trait InterpolatableComponent: Component { type InterpData: Component + Default; type ReadData; - fn update_component(&self, data: &mut Self::InterpData, time: f64); + fn update_component(&self, data: &mut Self::InterpData, time: f64, force_update: bool); fn interpolate(self, data: &Self::InterpData, time: f64, read_data: &Self::ReadData) -> Self; } -pub fn handle_interp_insert(comp: C, entity: Entity, world: &World) { +pub fn handle_interp_insert( + comp: C, + entity: Entity, + world: &World, + force_update: bool, +) { let mut interp_data = C::InterpData::default(); let time = world.read_resource::