Skip to main content

use_surface/
lib.rs

1#![forbid(unsafe_code)]
2#![doc = include_str!("../README.md")]
3
4/// Broad surface families.
5#[derive(Debug, Clone, Copy, PartialEq, Eq)]
6pub enum SurfaceKind {
7    /// A parametric surface.
8    Parametric,
9    /// An implicit surface.
10    Implicit,
11    /// A mesh-backed surface.
12    Mesh,
13}
14
15/// A rectangular parameter-domain surface patch.
16#[derive(Debug, Clone, Copy, PartialEq)]
17pub struct SurfacePatch {
18    kind: SurfaceKind,
19    u_extent: f64,
20    v_extent: f64,
21}
22
23impl SurfacePatch {
24    /// Creates a surface patch with positive finite parameter extents.
25    #[must_use]
26    pub const fn new(kind: SurfaceKind, u_extent: f64, v_extent: f64) -> Option<Self> {
27        if u_extent.is_finite() && v_extent.is_finite() && u_extent > 0.0 && v_extent > 0.0 {
28            Some(Self {
29                kind,
30                u_extent,
31                v_extent,
32            })
33        } else {
34            None
35        }
36    }
37
38    /// Returns the surface kind.
39    #[must_use]
40    pub const fn kind(self) -> SurfaceKind {
41        self.kind
42    }
43
44    /// Returns the parameter-domain area.
45    #[must_use]
46    pub const fn parameter_area(self) -> f64 {
47        self.u_extent * self.v_extent
48    }
49}
50
51#[cfg(test)]
52mod tests {
53    use super::{SurfaceKind, SurfacePatch};
54
55    #[test]
56    fn stores_surface_patch_data() {
57        let patch = SurfacePatch::new(SurfaceKind::Parametric, 2.0, 3.0).expect("valid patch");
58
59        assert_eq!(patch.kind(), SurfaceKind::Parametric);
60        assert_eq!(patch.parameter_area(), 6.0);
61        assert_eq!(SurfacePatch::new(SurfaceKind::Mesh, 0.0, 3.0), None);
62    }
63}