mesh_graph/
selection.rs

1use hashbrown::HashSet;
2use tracing::error;
3
4use super::{FaceId, HalfedgeId, MeshGraph, VertexId};
5
6#[derive(Debug, Clone, Default)]
7#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
8pub struct Selection {
9    pub vertices: HashSet<VertexId>,
10    pub halfedges: HashSet<HalfedgeId>,
11    pub faces: HashSet<FaceId>,
12}
13
14impl Selection {
15    pub fn select_all(mesh_graph: &MeshGraph) -> Self {
16        Self {
17            faces: mesh_graph.faces.keys().collect(),
18            ..Default::default()
19        }
20    }
21
22    pub fn resolve_to_halfedges(&self, mesh_graph: &MeshGraph) -> HashSet<HalfedgeId> {
23        let mut halfedges = self.halfedges.clone();
24
25        for face in &self.faces {
26            halfedges.extend(mesh_graph.faces[*face].halfedges(mesh_graph));
27        }
28
29        for vertex in &self.vertices {
30            halfedges.extend(mesh_graph.vertices[*vertex].outgoing_halfedges(mesh_graph));
31        }
32
33        halfedges
34    }
35
36    pub fn resolve_to_vertices(&self, mesh_graph: &MeshGraph) -> HashSet<VertexId> {
37        let mut vertices = self.vertices.clone();
38
39        for halfedge in &self.halfedges {
40            let he = mesh_graph.halfedges[*halfedge];
41            if let Some(start_vertex) = he.start_vertex(mesh_graph) {
42                vertices.insert(start_vertex);
43            } else {
44                error!("Start vertex not found");
45            }
46            vertices.insert(he.end_vertex);
47        }
48
49        for face in &self.faces {
50            vertices.extend(mesh_graph.faces[*face].vertices(mesh_graph));
51        }
52
53        vertices
54    }
55
56    // TODO : also resolve to faces
57}
58
59pub trait SelectionOps<T> {
60    fn insert(&mut self, item: T);
61    fn remove(&mut self, item: T);
62}
63
64impl SelectionOps<VertexId> for Selection {
65    fn insert(&mut self, item: VertexId) {
66        self.vertices.insert(item);
67    }
68
69    fn remove(&mut self, item: VertexId) {
70        self.vertices.remove(&item);
71    }
72}
73
74impl SelectionOps<HalfedgeId> for Selection {
75    fn insert(&mut self, item: HalfedgeId) {
76        self.halfedges.insert(item);
77    }
78
79    fn remove(&mut self, item: HalfedgeId) {
80        self.halfedges.remove(&item);
81    }
82}
83
84impl SelectionOps<FaceId> for Selection {
85    fn insert(&mut self, item: FaceId) {
86        self.faces.insert(item);
87    }
88
89    fn remove(&mut self, item: FaceId) {
90        self.faces.remove(&item);
91    }
92}
93
94impl From<VertexId> for Selection {
95    fn from(value: VertexId) -> Self {
96        Self::from_iter(vec![value])
97    }
98}
99
100impl From<HalfedgeId> for Selection {
101    fn from(value: HalfedgeId) -> Self {
102        Self::from_iter(vec![value])
103    }
104}
105
106impl From<FaceId> for Selection {
107    fn from(value: FaceId) -> Self {
108        Self::from_iter(vec![value])
109    }
110}
111
112impl FromIterator<VertexId> for Selection {
113    fn from_iter<T: IntoIterator<Item = VertexId>>(iter: T) -> Self {
114        Selection {
115            vertices: HashSet::from_iter(iter),
116            ..Default::default()
117        }
118    }
119}
120
121impl FromIterator<HalfedgeId> for Selection {
122    fn from_iter<T: IntoIterator<Item = HalfedgeId>>(iter: T) -> Self {
123        Selection {
124            halfedges: HashSet::from_iter(iter),
125            ..Default::default()
126        }
127    }
128}
129
130impl FromIterator<FaceId> for Selection {
131    fn from_iter<T: IntoIterator<Item = FaceId>>(iter: T) -> Self {
132        Selection {
133            faces: HashSet::from_iter(iter),
134            ..Default::default()
135        }
136    }
137}
138
139macro_rules! impl_from_for_selection {
140    ($type:ident) => {
141        impl From<$type<VertexId>> for Selection {
142            fn from(value: $type<VertexId>) -> Self {
143                Self::from_iter(value)
144            }
145        }
146        impl From<$type<HalfedgeId>> for Selection {
147            fn from(value: $type<HalfedgeId>) -> Self {
148                Self::from_iter(value)
149            }
150        }
151        impl From<$type<FaceId>> for Selection {
152            fn from(value: $type<FaceId>) -> Self {
153                Self::from_iter(value)
154            }
155        }
156    };
157}
158
159impl_from_for_selection!(Vec);
160impl_from_for_selection!(HashSet);