use crate::{trids::node::VertexNode, utils::types::TetIteratorIdx};
use super::{half_tri_iterator::HalfTriIterator, tet_data_structure::TetDataStructure};
pub struct TetIterator<'a> {
pub tds: &'a TetDataStructure,
pub tet_idx: usize,
}
impl<'a> TetIterator<'a> {
pub fn half_triangles(&self) -> [HalfTriIterator<'a>; 4] {
let idx_first = self.idx() << 2;
[
HalfTriIterator {
tds: self.tds,
half_tri_idx: idx_first,
},
HalfTriIterator {
tds: self.tds,
half_tri_idx: idx_first + 1,
},
HalfTriIterator {
tds: self.tds,
half_tri_idx: idx_first + 2,
},
HalfTriIterator {
tds: self.tds,
half_tri_idx: idx_first + 3,
},
]
}
pub fn idx(&self) -> TetIteratorIdx {
self.tet_idx
}
pub fn is_casual(&self) -> bool {
!self.is_conceptual()
}
pub fn is_conceptual(&self) -> bool {
self.nodes().iter().any(|n| n.is_conceptual())
}
pub fn is_sound(&self) -> bool {
if self.should_del() || self.should_keep() {
log::error!("{}: tetrahedron remaining after triangulation.", self);
return false;
}
let [n0, n1, n2, n3] = self.nodes();
let mut sound = true;
if n0 == n1 || n0 == n2 || n0 == n3 || n1 == n2 || n1 == n3 || n2 == n3 {
log::error!("{}: tetrahedron with duplicate nodes.", self);
sound = false;
}
sound
}
pub fn nodes(&self) -> [VertexNode; 4] {
let idx_first = self.idx() << 2; [
self.tds.tet_nodes[idx_first],
self.tds.tet_nodes[idx_first + 1],
self.tds.tet_nodes[idx_first + 2],
self.tds.tet_nodes[idx_first + 3],
]
}
pub fn should_del(&self) -> bool {
self.tds.should_del_tet[self.idx()]
}
pub fn should_keep(&self) -> bool {
self.tds.should_keep_tet[self.idx()]
}
}
impl std::fmt::Display for TetIterator<'_> {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
let [n0, n1, n2, n3] = self.nodes();
write!(
f,
"Tetrahedron {}: {} -> {} -> {} -> {}",
self.idx(),
n0,
n1,
n2,
n3
)
}
}