gizmo_physics/components/
collision_layer.rs1use serde::{Deserialize, Serialize};
2
3pub const LAYER_DEFAULT: u32 = 0;
4pub const LAYER_PLAYER: u32 = 1;
5pub const LAYER_ENEMY: u32 = 2;
6pub const LAYER_TRIGGER: u32 = 3;
7
8#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize)]
9pub struct CollisionLayer {
10 pub layer: u32, pub mask: u32, }
13
14impl Default for CollisionLayer {
15 fn default() -> Self {
16 Self {
17 layer: LAYER_DEFAULT,
18 mask: u32::MAX, }
20 }
21}
22
23impl CollisionLayer {
24 pub fn new(layer: u32) -> Self {
25 Self {
26 layer,
27 mask: u32::MAX,
28 }
29 }
30
31 pub fn from_layer(layer: u32) -> Self {
32 Self::new(layer)
33 }
34
35 pub fn with_mask(mut self, mask: u32) -> Self {
36 self.mask = mask;
37 self
38 }
39
40 pub fn mask_from_layers(layers: &[u32]) -> u32 {
41 layers
42 .iter()
43 .fold(0u32, |acc, &l| acc | (1u32.checked_shl(l).unwrap_or(0)))
44 }
45
46 #[inline]
47 pub fn can_collide_with(&self, other: &CollisionLayer) -> bool {
48 debug_assert!(
49 self.layer < 32,
50 "CollisionLayer: layer {} >= 32",
51 self.layer
52 );
53 debug_assert!(
54 other.layer < 32,
55 "CollisionLayer: layer {} >= 32",
56 other.layer
57 );
58
59 let layer_bit = 1u32.checked_shl(self.layer).unwrap_or(0);
60 let other_layer_bit = 1u32.checked_shl(other.layer).unwrap_or(0);
61 (self.mask & other_layer_bit) != 0 && (other.mask & layer_bit) != 0
62 }
63}
64
65gizmo_core::impl_component!(CollisionLayer);