gemath 0.1.0

Type-safe game math with type-level units/spaces, typed angles, and explicit fallible ops (plus optional geometry/collision).
Documentation
#[cfg(all(feature = "polygon2", any(feature = "std", feature = "alloc")))]
mod tests {
    use gemath::*;

    #[test]
    fn polygon2_contains_point_convex_square() {
        let poly: Polygon2<(), ()> = Polygon2::new(vec![
            Vec2::new(-1.0, -1.0),
            Vec2::new(1.0, -1.0),
            Vec2::new(1.0, 1.0),
            Vec2::new(-1.0, 1.0),
        ]);

        assert!(poly.contains_point(Vec2::new(0.0, 0.0)));
        assert!(!poly.contains_point(Vec2::new(2.0, 0.0)));

        // Touching boundary is inside.
        assert!(poly.contains_point(Vec2::new(1.0, 0.25)));
        assert!(poly.contains_point(Vec2::new(0.0, -1.0)));
        assert!(poly.contains_point(Vec2::new(-1.0, 1.0)));
    }

    #[test]
    fn polygon2_contains_point_concave_l_shape() {
        // Concave polygon (square with a notch removed):
        //
        //  (0,3) ┌───┐ (2,3)
        //        │   │
        //        │   └─────┐ (3,2)
        //        │         │
        //  (0,0) └─────────┘ (3,0)
        //
        let poly: Polygon2<(), ()> = Polygon2::new(vec![
            Vec2::new(0.0, 0.0),
            Vec2::new(3.0, 0.0),
            Vec2::new(3.0, 2.0),
            Vec2::new(2.0, 2.0),
            Vec2::new(2.0, 3.0),
            Vec2::new(0.0, 3.0),
        ]);

        // Inside the solid "L" area.
        assert!(poly.contains_point(Vec2::new(0.5, 2.5)));
        assert!(poly.contains_point(Vec2::new(2.5, 0.5)));

        // In the concavity "missing" region (should be outside).
        assert!(!poly.contains_point(Vec2::new(2.5, 2.5)));

        // Boundary points are inside.
        assert!(poly.contains_point(Vec2::new(2.0, 2.5))); // on the inner vertical edge
        assert!(poly.contains_point(Vec2::new(2.5, 2.0))); // on the inner horizontal edge
    }
}