diff --git a/strafe-client/src/model_physics.rs b/strafe-client/src/model_physics.rs index be7382ef..9aa0d716 100644 --- a/strafe-client/src/model_physics.rs +++ b/strafe-client/src/model_physics.rs @@ -1,5 +1,6 @@ use std::borrow::{Borrow,Cow}; use std::collections::{HashSet,HashMap}; +use core::ops::Range; use strafesnet_common::integer::vec3::Vector3; use strafesnet_common::model::{self,MeshId,PolygonIter}; use strafesnet_common::integer::{self,vec3,Fixed,Planar64,Planar64Vec3,Ratio}; @@ -718,7 +719,7 @@ impl MinkowskiMesh<'_>{ // // Most of the calculation time is just calculating the starting point // for the "actual" crawling algorithm below (predict_collision_{in|out}). - fn closest_fev_not_inside(&self,mut infinity_body:Body,start_time:Time,)->Option<FEV<MinkowskiMesh>>{ + fn closest_fev_not_inside(&self,mut infinity_body:Body,start_time:Time)->Option<FEV<MinkowskiMesh>>{ infinity_body.infinity_dir().map_or(None,|dir|{ let infinity_fev=self.infinity_fev(-dir,infinity_body.position); //a line is simpler to solve than a parabola @@ -729,13 +730,13 @@ impl MinkowskiMesh<'_>{ infinity_fev.crawl(self,&infinity_body,Time::MIN/4,start_time).miss() }) } - pub fn predict_collision_in(&self,relative_body:&Body,start_time:Time,time_limit:Time)->Option<(MinkowskiFace,GigaTime)>{ + pub fn predict_collision_in(&self,relative_body:&Body,Range{start:start_time,end:time_limit}:Range<Time>)->Option<(MinkowskiFace,GigaTime)>{ self.closest_fev_not_inside(relative_body.clone(),start_time).map_or(None,|fev|{ //continue forwards along the body parabola fev.crawl(self,relative_body,start_time,time_limit).hit() }) } - pub fn predict_collision_out(&self,relative_body:&Body,start_time:Time,time_limit:Time)->Option<(MinkowskiFace,GigaTime)>{ + pub fn predict_collision_out(&self,relative_body:&Body,Range{start:start_time,end:time_limit}:Range<Time>)->Option<(MinkowskiFace,GigaTime)>{ //create an extrapolated body at time_limit let infinity_body=-relative_body.clone(); self.closest_fev_not_inside(infinity_body,-time_limit).map_or(None,|fev|{ @@ -745,7 +746,7 @@ impl MinkowskiMesh<'_>{ .map(|(face,time)|(face,-time)) }) } - pub fn predict_collision_face_out(&self,relative_body:&Body,start_time:Time,time_limit:Time,contact_face_id:MinkowskiFace)->Option<(MinkowskiEdge,GigaTime)>{ + pub fn predict_collision_face_out(&self,relative_body:&Body,Range{start:start_time,end:time_limit}:Range<Time>,contact_face_id:MinkowskiFace)->Option<(MinkowskiEdge,GigaTime)>{ //no algorithm needed, there is only one state and two cases (Edge,None) //determine when it passes an edge ("sliding off" case) let start_time={ diff --git a/strafe-client/src/physics.rs b/strafe-client/src/physics.rs index 814345df..1ce44121 100644 --- a/strafe-client/src/physics.rs +++ b/strafe-client/src/physics.rs @@ -836,7 +836,7 @@ impl TouchingState{ //detect face slide off let model_mesh=models.contact_mesh(contact); let minkowski=model_physics::MinkowskiMesh::minkowski_sum(model_mesh,hitbox_mesh.transformed_mesh()); - collector.collect(minkowski.predict_collision_face_out(&relative_body,start_time,collector.time(),contact.face_id).map(|(_face,time)|{ + collector.collect(minkowski.predict_collision_face_out(&relative_body,start_time..collector.time(),contact.face_id).map(|(_face,time)|{ TimedInstruction{ time:relative_body.time+time.into(), instruction:InternalInstruction::CollisionEnd( @@ -850,7 +850,7 @@ impl TouchingState{ //detect model collision in reverse let model_mesh=models.intersect_mesh(intersect); let minkowski=model_physics::MinkowskiMesh::minkowski_sum(model_mesh,hitbox_mesh.transformed_mesh()); - collector.collect(minkowski.predict_collision_out(&relative_body,start_time,collector.time()).map(|(_face,time)|{ + collector.collect(minkowski.predict_collision_out(&relative_body,start_time..collector.time()).map(|(_face,time)|{ TimedInstruction{ time:relative_body.time+time.into(), instruction:InternalInstruction::CollisionEnd( @@ -1185,7 +1185,7 @@ impl PhysicsData{ //no checks are needed because of the time limits. let model_mesh=data.models.mesh(convex_mesh_id); let minkowski=model_physics::MinkowskiMesh::minkowski_sum(model_mesh,data.hitbox_mesh.transformed_mesh()); - collector.collect(minkowski.predict_collision_in(relative_body,state.time,collector.time()) + collector.collect(minkowski.predict_collision_in(relative_body,state.time..collector.time()) //temp (?) code to avoid collision loops .map_or(None,|(face,dt)|{ // this must be rounded to avoid the infinite loop when hitting the start zone @@ -1922,7 +1922,7 @@ mod test{ let hitbox_mesh=h1.transformed_mesh(); let platform_mesh=h0.transformed_mesh(); let minkowski=model_physics::MinkowskiMesh::minkowski_sum(platform_mesh,hitbox_mesh); - let collision=minkowski.predict_collision_in(&relative_body,Time::ZERO,Time::from_secs(10)); + let collision=minkowski.predict_collision_in(&relative_body,Time::ZERO..Time::from_secs(10)); assert_eq!(collision.map(|tup|relative_body.time+tup.1.into()),expected_collision_time,"Incorrect time of collision"); } fn test_collision_rotated(relative_body:Body,expected_collision_time:Option<Time>){ @@ -1940,7 +1940,7 @@ mod test{ let hitbox_mesh=h1.transformed_mesh(); let platform_mesh=h0.transformed_mesh(); let minkowski=model_physics::MinkowskiMesh::minkowski_sum(platform_mesh,hitbox_mesh); - let collision=minkowski.predict_collision_in(&relative_body,Time::ZERO,Time::from_secs(10)); + let collision=minkowski.predict_collision_in(&relative_body,Time::ZERO..Time::from_secs(10)); assert_eq!(collision.map(|tup|relative_body.time+tup.1.into()),expected_collision_time,"Incorrect time of collision"); } fn test_collision(relative_body:Body,expected_collision_time:Option<Time>){