rust/hwphysics/src/collision.rs
changeset 14179 abbb74b9cb62
parent 14178 a4c17cfaa4c9
child 14702 29dbe9ce8b7d
equal deleted inserted replaced
14178:a4c17cfaa4c9 14179:abbb74b9cb62
     1 use std::{
     1 use std::{
     2     ops::RangeInclusive
     2     ops::RangeInclusive
     3 };
     3 };
     4 
     4 
     5 use crate::{
     5 use crate::{
     6     common::GearId,
     6     common::{GearId, GearData, GearDataProcessor},
     7     physics::PhysicsData,
     7     physics::PhysicsData,
     8     grid::Grid
     8     grid::Grid
     9 };
     9 };
    10 
    10 
    11 use fpnum::*;
    11 use fpnum::*;
    40 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
    40 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
    41 pub struct CollisionData {
    41 pub struct CollisionData {
    42     pub bounds: CircleBounds
    42     pub bounds: CircleBounds
    43 }
    43 }
    44 
    44 
       
    45 impl GearData for CollisionData {}
       
    46 
    45 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
    47 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
    46 pub struct ContactData {
    48 pub struct ContactData {
    47     pub elasticity: FPNum,
    49     pub elasticity: FPNum,
    48     pub friction: FPNum
    50     pub friction: FPNum
    49 }
    51 }
       
    52 
       
    53 impl GearData for ContactData {}
    50 
    54 
    51 struct EnabledCollisionsCollection {
    55 struct EnabledCollisionsCollection {
    52     gear_ids: Vec<GearId>,
    56     gear_ids: Vec<GearId>,
    53     collisions: Vec<CollisionData>
    57     collisions: Vec<CollisionData>
    54 }
    58 }
    55 
    59 
    56 impl EnabledCollisionsCollection {
    60 impl EnabledCollisionsCollection {
       
    61     fn new() -> Self {
       
    62         Self {
       
    63             gear_ids: Vec::new(),
       
    64             collisions: Vec::new()
       
    65         }
       
    66     }
       
    67 
    57     fn push(&mut self, gear_id: GearId, collision: CollisionData) {
    68     fn push(&mut self, gear_id: GearId, collision: CollisionData) {
    58         self.gear_ids.push(gear_id);
    69         self.gear_ids.push(gear_id);
    59         self.collisions.push(collision);
    70         self.collisions.push(collision);
    60     }
    71     }
    61 
    72 
    84         }
    95         }
    85     }
    96     }
    86 
    97 
    87     pub fn push(&mut self, contact_gear_id1: GearId, contact_gear_id2: GearId, position: &FPPoint) {
    98     pub fn push(&mut self, contact_gear_id1: GearId, contact_gear_id2: GearId, position: &FPPoint) {
    88         self.pairs.push((contact_gear_id1, contact_gear_id2));
    99         self.pairs.push((contact_gear_id1, contact_gear_id2));
    89         self.positions.push(fppoint_round(position));
   100         self.positions.push(fppoint_round(&position));
    90     }
   101     }
    91 }
   102 }
    92 
   103 
    93 impl CollisionProcessor {
   104 impl CollisionProcessor {
    94     pub fn process(&mut self, land: &Land2D<u32>, updates: &crate::physics::PositionUpdate) {
   105     pub fn new(size: Size) -> Self {
       
   106         Self {
       
   107             grid: Grid::new(size),
       
   108             enabled_collisions: EnabledCollisionsCollection::new(),
       
   109             detected_collisions: DetectedCollisions::new(0)
       
   110         }
       
   111     }
       
   112 
       
   113     pub fn process(&mut self, land: &Land2D<u32>, updates: &crate::physics::PositionUpdates) {
    95         self.grid.check_collisions(&mut self.detected_collisions);
   114         self.grid.check_collisions(&mut self.detected_collisions);
    96 
   115 
    97         for (gear_id, collision) in self.enabled_collisions.iter() {
   116         for (gear_id, collision) in self.enabled_collisions.iter() {
    98             if collision.bounds.rows().any(|(y, r)| (&land[y][r]).iter().any(|v| *v != 0)) {
   117             if collision.bounds.rows().any(|(y, r)| (&land[y][r]).iter().any(|v| *v != 0)) {
    99                 self.detected_collisions.push(0, 0, &collision.bounds.center)
   118                 self.detected_collisions.push(gear_id, 0, &collision.bounds.center)
   100             }
   119             }
   101         }
   120         }
   102     }
   121     }
       
   122 }
   103 
   123 
   104     pub fn push(&mut self, gear_id: GearId, physics_data: PhysicsData, collision_data: CollisionData) {
   124 impl GearDataProcessor<CollisionData> for CollisionProcessor {
   105         if physics_data.velocity.is_zero() {
   125     fn add(&mut self, gear_id: GearId, gear_data: CollisionData) {
   106             self.grid.insert_static(0, &physics_data.position, &collision_data.bounds);
   126         self.grid.insert_static(gear_id, &gear_data.bounds);
   107         } else {
       
   108             self.grid.insert_dynamic(0, &physics_data.position, &collision_data.bounds);
       
   109         }
       
   110     }
   127     }
   111 }
   128 }