diff --git a/src/integer.rs b/src/integer.rs index 56c25e2..6c41595 100644 --- a/src/integer.rs +++ b/src/integer.rs @@ -404,11 +404,12 @@ impl TryFrom<[f32;3]> for Unit32Vec3{ */ ///[-1.0,1.0] = [-2^32,2^32] -#[derive(Clone,Copy,Hash,Eq,Ord,PartialEq,PartialOrd)] +#[derive(Clone,Copy,Debug,Hash,Eq,Ord,PartialEq,PartialOrd)] pub struct Planar64(i64); impl Planar64{ pub const ZERO:Self=Self(0); pub const ONE:Self=Self(1<<32); + pub const FRAC_1_SQRT2:Self=Self(3_037_000_500); #[inline] pub const fn int(num:i32)->Self{ Self(Self::ONE.0*num as i64) @@ -563,7 +564,7 @@ impl std::ops::Div for Planar64{ ///[-1.0,1.0] = [-2^32,2^32] -#[derive(Clone,Copy,Default,Hash,Eq,PartialEq)] +#[derive(Clone,Copy,Debug,Default,Hash,Eq,PartialEq)] pub struct Planar64Vec3(glam::I64Vec3); impl Planar64Vec3{ pub const ZERO:Self=Planar64Vec3(glam::I64Vec3::ZERO); @@ -629,6 +630,14 @@ impl Planar64Vec3{ )>>32) as i64) } #[inline] +/* pub fn cross(&self,rhs:Self)->Planar64Vec3{ + Planar64Vec3((( + (self.0.x as i128)*(rhs.0.x as i128)+ + (self.0.y as i128)*(rhs.0.y as i128)+ + (self.0.z as i128)*(rhs.0.z as i128) + )>>32) as i64) + }*/ + #[inline] pub fn length(&self)->Planar64{ let radicand=(self.0.x as i128)*(self.0.x as i128)+(self.0.y as i128)*(self.0.y as i128)+(self.0.z as i128)*(self.0.z as i128); Planar64(unsafe{(radicand as f64).sqrt().to_int_unchecked()}) diff --git a/src/load_roblox.rs b/src/load_roblox.rs index 751e42d..16c58a9 100644 --- a/src/load_roblox.rs +++ b/src/load_roblox.rs @@ -49,6 +49,7 @@ fn get_attributes(name:&str,can_collide:bool,velocity:Planar64Vec3,force_interse let mut intersecting=crate::model::IntersectingAttributes::default(); let mut contacting=crate::model::ContactingAttributes::default(); let mut force_can_collide=can_collide; + const GRAVITY:Planar64Vec3=Planar64Vec3::int(0,-100,0); match name{ "Water"=>{ force_can_collide=false; @@ -123,7 +124,20 @@ fn get_attributes(name:&str,can_collide:bool,velocity:Planar64Vec3,force_interse } //need some way to skip this if velocity!=Planar64Vec3::ZERO{ - general.booster=Some(crate::model::GameMechanicBooster::Velocity(velocity)); + //assume all vertical boosters are targetting a height + let vg=velocity.dot(GRAVITY); + if Planar64::ZERO<=vg{ + //weird down booster + general.booster=Some(crate::model::GameMechanicBooster::Velocity(velocity)); + }else{ + println!("set attr"); + let gg=GRAVITY.dot(GRAVITY); + let height=-vg*gg.sqrt().sqrt()*Planar64::FRAC_1_SQRT2/gg;//vi/sqrt(-2*a)=d + let v=velocity-GRAVITY*(vg/gg); + //if we are adding zero SO BE IT, the check to see if the vectors are parallel is too sensitive + general.booster=Some(crate::model::GameMechanicBooster::Velocity(v)); + general.trajectory=Some(crate::model::GameMechanicSetTrajectory::Height(height)); + } } match force_can_collide{ true=>{ diff --git a/src/model.rs b/src/model.rs index 76024c7..dd088c2 100644 --- a/src/model.rs +++ b/src/model.rs @@ -119,12 +119,12 @@ pub enum GameMechanicBooster{ Velocity(Planar64Vec3),//straight up boost velocity adds to your current velocity Energy{direction:Planar64Vec3,energy:Planar64},//increase energy in direction } -#[derive(Clone)] +#[derive(Clone,Debug)] pub enum TrajectoryChoice{ HighArcLongDuration,//underhand lob at target: less horizontal speed and more air time LowArcShortDuration,//overhand throw at target: more horizontal speed and less air time } -#[derive(Clone)] +#[derive(Clone,Debug)] pub enum GameMechanicSetTrajectory{ AirTime(Time),//air time (relative to gravity direction) is invariant across mass and gravity changes Height(Planar64),//boost height (relative to gravity direction) is invariant across mass and gravity changes diff --git a/src/physics.rs b/src/physics.rs index fa7e1e5..9fb0df9 100644 --- a/src/physics.rs +++ b/src/physics.rs @@ -1395,13 +1395,25 @@ impl crate::instruction::InstructionConsumer for PhysicsStat } match &general.trajectory{ Some(trajectory)=>{ + println!("??? {:?}",trajectory); match trajectory{ - crate::model::GameMechanicSetTrajectory::AirTime(_) => todo!(), - crate::model::GameMechanicSetTrajectory::Height(_) => todo!(), - crate::model::GameMechanicSetTrajectory::TargetPointTime { target_point, time } => todo!(), - crate::model::GameMechanicSetTrajectory::TrajectoryTargetPoint { target_point, speed, trajectory_choice } => todo!(), + &crate::model::GameMechanicSetTrajectory::Height(height)=>{ + //vg=sqrt(-2*gg*height) + println!("height booster h={}",height); + let vg=v.dot(self.style.gravity); + let gg=self.style.gravity.dot(self.style.gravity); + let hb=(gg.sqrt()*height*2).sqrt()*gg.sqrt(); + println!("hb={} vg={}",hb,vg); + let b=self.style.gravity*((-hb-vg)/gg); + println!("bopo {}",b); + v+=b; + }, &crate::model::GameMechanicSetTrajectory::Velocity(velocity)=>v=velocity, - crate::model::GameMechanicSetTrajectory::DotVelocity { direction, dot } => todo!(), + crate::model::GameMechanicSetTrajectory::AirTime(_) + |crate::model::GameMechanicSetTrajectory::TargetPointTime{target_point:_,time:_} + |crate::model::GameMechanicSetTrajectory::TrajectoryTargetPoint{target_point:_,speed:_,trajectory_choice:_} + |crate::model::GameMechanicSetTrajectory::DotVelocity{direction:_,dot:_} + =>(), } self.touching.constrain_velocity(&self.models,&mut v); },