qhull_enhanced/types/
set.rs1use std::ffi::c_void;
2use std::fmt::Debug;
3use std::marker::PhantomData;
4use std::ops::Not;
5
6use crate::helpers::QhTypeRef;
7
8use crate::{sys, Facet, Qh};
9
10#[derive(Clone, Copy)]
12pub struct Set<'a, T: QhTypeRef> {
13 set: *mut sys::setT,
14 dim: usize,
15 _phantom: PhantomData<&'a T>,
16}
17
18impl<'a, T: QhTypeRef> Debug for Set<'a, T>
19where
20 T: Debug,
21{
22 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
23 f.debug_struct(&format!("Set<{}>", std::any::type_name::<T>()))
24 .field("elements:", &self.iter().collect::<Vec<_>>())
25 .finish()
26 }
27}
28
29impl<'a, T: QhTypeRef> Set<'a, T> {
30 pub(crate) fn maybe_new(set: *mut sys::setT, dim: usize) -> Option<Self> {
31 set.is_null().not().then(|| Self {
32 set,
33 dim,
34 _phantom: PhantomData,
35 })
36 }
37
38 pub fn iter(&self) -> impl Iterator<Item = T> + 'a {
40 SetIterator::new(self)
41 }
42
43 pub fn maxsize(&self) -> i32 {
44 let set = unsafe { &*self.set };
45 set.maxsize
46 }
47
48 pub fn size(&self, qh: &Qh) -> usize {
49 unsafe {
50 sys::qh_setsize(Qh::raw_ptr(qh) as *mut _, self.set) as usize
51 }
52 }
53}
54
55pub(crate) fn dbg_face_set(set: Option<Set<Facet>>) -> Option<Vec<u32>> {
56 set.map(|s| s.iter().map(|f| f.id()).collect())
57}
58
59#[derive(Clone, Copy)]
60struct SetIterator<'a, T: QhTypeRef> {
61 ptr: *mut *mut T::FFIType,
62 dim: usize,
63 _phantom: PhantomData<&'a T>,
64}
65
66impl<'a, T: QhTypeRef> SetIterator<'a, T> {
67 pub fn new(set: &Set<'a, T>) -> Self {
68 let dim = set.dim;
69 assert!(!set.set.is_null());
70 let set = unsafe { &*set.set };
71 let ptr = unsafe { (&(set.e[0].p)) as *const *mut c_void as *mut *mut T::FFIType };
72 Self {
73 ptr,
74 dim,
75 _phantom: PhantomData,
76 }
77 }
78}
79
80impl<'a, T: QhTypeRef> Iterator for SetIterator<'a, T> {
81 type Item = T;
82
83 fn next(&mut self) -> Option<Self::Item> {
84 let value_ptr = unsafe { *self.ptr };
86 let element = T::from_ptr(value_ptr, self.dim);
87 if element.is_some() {
88 self.ptr = unsafe { self.ptr.add(1) };
89 }
90 element
91 }
92}