# HG changeset patch # User alfadur # Date 1564516746 -10800 # Node ID 478d5372eb4aca2a3e4c9d135fafbe22b8d96ee6 # Parent 8095853811a60e07e61ee11d92338cbe0fb0e916 implement empty gear lookup entries diff -r 8095853811a6 -r 478d5372eb4a rust/hwphysics/src/collision.rs --- a/rust/hwphysics/src/collision.rs Tue Jul 30 19:53:23 2019 +0300 +++ b/rust/hwphysics/src/collision.rs Tue Jul 30 22:59:06 2019 +0300 @@ -3,11 +3,10 @@ use crate::{ common::{GearData, GearDataProcessor, GearId}, grid::Grid, - physics::PhysicsData, }; use fpnum::*; -use integral_geometry::{GridIndex, Point, Size}; +use integral_geometry::{Point, Size}; use land2d::Land2D; pub fn fppoint_round(point: &FPPoint) -> Point { @@ -151,4 +150,8 @@ fn remove(&mut self, gear_id: GearId) { self.grid.remove(gear_id); } + + fn get(&mut self, gear_id: GearId) -> Option { + None + } } diff -r 8095853811a6 -r 478d5372eb4a rust/hwphysics/src/common.rs --- a/rust/hwphysics/src/common.rs Tue Jul 30 19:53:23 2019 +0300 +++ b/rust/hwphysics/src/common.rs Tue Jul 30 22:59:06 2019 +0300 @@ -1,4 +1,4 @@ -use fpnum::{fp, FPNum}; +use fpnum::FPNum; use std::{ collections::BinaryHeap, num::NonZeroU16, @@ -40,6 +40,7 @@ pub trait GearDataProcessor { fn add(&mut self, gear_id: GearId, gear_data: T); fn remove(&mut self, gear_id: GearId); + fn get(&mut self, gear_id: GearId) -> Option; } pub trait GearDataAggregator { @@ -75,13 +76,34 @@ #[derive(Clone, Copy, Default)] pub struct LookupEntry { - pub index: u16, - pub value: T, + index: Option, + value: T, } impl LookupEntry { - pub fn new(index: u16, value: T) -> Self { - Self { index, value } + #[inline] + pub fn index(&self) -> u16 { + self.index.map(|i| i.get()).unwrap_or(0) - 1 + } + + #[inline] + pub fn set_index(&mut self, index: u16) { + self.index = unsafe { Some(NonZeroU16::new_unchecked(index.saturating_add(1))) }; + } + + #[inline] + pub fn value(&self) -> &T { + &self.value + } + + #[inline] + pub fn value_mut(&mut self) -> &mut T { + &mut self.value + } + + #[inline] + pub fn set_value(&mut self, value: T) { + self.value = value; } } @@ -98,14 +120,31 @@ } impl GearDataLookup { - pub fn get(&self, gear_id: GearId) -> &LookupEntry { + pub fn add(&mut self, gear_id: GearId, index: u16, value: T) { // All possible Gear IDs are valid indices - unsafe { self.lookup.get_unchecked(gear_id.get() as usize - 1) } + let entry = unsafe { self.lookup.get_unchecked_mut(gear_id.get() as usize - 1) }; + entry.set_index(index); + entry.set_value(value); } - pub fn get_mut(&mut self, gear_id: GearId) -> &mut LookupEntry { + pub fn get(&self, gear_id: GearId) -> Option<&LookupEntry> { // All possible Gear IDs are valid indices - unsafe { self.lookup.get_unchecked_mut(gear_id.get() as usize - 1) } + let entry = unsafe { self.lookup.get_unchecked(gear_id.get() as usize - 1) }; + if let Some(index) = entry.index { + Some(entry) + } else { + None + } + } + + pub fn get_mut(&mut self, gear_id: GearId) -> Option<&mut LookupEntry> { + // All possible Gear IDs are valid indices + let entry = unsafe { self.lookup.get_unchecked_mut(gear_id.get() as usize - 1) }; + if let Some(index) = entry.index { + Some(entry) + } else { + None + } } } @@ -113,12 +152,12 @@ type Output = LookupEntry; fn index(&self, index: GearId) -> &Self::Output { - self.get(index) + self.get(index).unwrap() } } impl IndexMut for GearDataLookup { fn index_mut(&mut self, index: GearId) -> &mut Self::Output { - self.get_mut(index) + self.get_mut(index).unwrap() } } diff -r 8095853811a6 -r 478d5372eb4a rust/hwphysics/src/physics.rs --- a/rust/hwphysics/src/physics.rs Tue Jul 30 19:53:23 2019 +0300 +++ b/rust/hwphysics/src/physics.rs Tue Jul 30 22:59:06 2019 +0300 @@ -1,6 +1,5 @@ -use crate::common::{GearData, GearDataLookup, GearDataProcessor, GearId, LookupEntry, Millis}; +use crate::common::{GearData, GearDataLookup, GearDataProcessor, GearId, Millis}; use fpnum::*; -use integral_geometry::{GridIndex, Point, Size}; #[derive(PartialEq, Eq, Clone, Copy, Debug)] pub struct PhysicsData { @@ -164,19 +163,40 @@ self.static_physics.push(gear_id, gear_data) }; - self.gear_lookup[gear_id] = LookupEntry::new(index, is_dynamic); + self.gear_lookup.add(gear_id, index, is_dynamic); } fn remove(&mut self, gear_id: GearId) { - let location = self.gear_lookup[gear_id]; - let relocated_gear_id = if location.value { - self.dynamic_physics.remove(location.index as usize) + if let Some(entry) = self.gear_lookup.get(gear_id) { + let relocated_gear_id = if *entry.value() { + self.dynamic_physics.remove(entry.index() as usize) + } else { + self.static_physics.remove(entry.index() as usize) + }; + + if let Some(id) = relocated_gear_id { + let index = entry.index(); + self.gear_lookup[id].set_index(index); + } + } + } + + fn get(&mut self, gear_id: GearId) -> Option { + if let Some(entry) = self.gear_lookup.get(gear_id) { + let data = if *entry.value() { + PhysicsData { + position: self.dynamic_physics.positions[entry.index() as usize], + velocity: self.dynamic_physics.velocities[entry.index() as usize], + } + } else { + PhysicsData { + position: self.static_physics.positions[entry.index() as usize], + velocity: FPPoint::zero(), + } + }; + Some(data) } else { - self.static_physics.remove(location.index as usize) - }; - - if let Some(id) = relocated_gear_id { - self.gear_lookup[id].index = location.index; + None } } } diff -r 8095853811a6 -r 478d5372eb4a rust/hwphysics/src/time.rs --- a/rust/hwphysics/src/time.rs Tue Jul 30 19:53:23 2019 +0300 +++ b/rust/hwphysics/src/time.rs Tue Jul 30 22:59:06 2019 +0300 @@ -1,4 +1,4 @@ -use crate::common::{GearDataProcessor, GearId, Millis}; +use crate::common::{GearId, Millis}; use std::{ cmp::{Eq, Ord, Ordering, PartialEq, PartialOrd}, collections::BinaryHeap,