mirror of
https://github.com/bherbruck/solidcraft.git
synced 2026-11-05 03:25:58 +00:00
kernel: SMLib's export keeps every face of a void's shell
The export takes a closed boundary's faces from the side in the empty region and skipped every use there that is not `same`, a rule meant only for a sheet (a shell that is its own mate). It tested the chosen side against the mate instead of the shell against itself, so a cavity's shell, taken from the void's side, lost its faces whose uses run opposite to their surfaces: "a face no shell uses" for every cut that leaves a void. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QWhMwdqJYQKQq8RCLSL1LT
This commit is contained in:
@@ -80,3 +80,16 @@ fn extruded_circles_go_as_cylinders() {
|
||||
let check = r.check(solidcraft_smlib::CheckLevel::All).unwrap();
|
||||
assert!(check.is_valid(), "{check}");
|
||||
}
|
||||
|
||||
/// A cavity cut out of a block: SMLib's result lists the cavity's faces on the void's side with
|
||||
/// mixed orientations, and every one of them comes back.
|
||||
#[test]
|
||||
fn a_cavity_comes_back_from_smlib() {
|
||||
let block = box_solid(v(0., 0., 0.), v(40., 40., 40.)).unwrap();
|
||||
let cavity = box_solid(v(25., 25., 25.), v(30., 30., 30.)).unwrap();
|
||||
let r = super::smlib_body(&block).unwrap().boolean(&super::smlib_body(&cavity).unwrap(), solidcraft_smlib::BooleanOp::Subtract).unwrap().unwrap();
|
||||
let back = super::body_from_smlib(&r).unwrap();
|
||||
assert_eq!((back.solid.boundaries().len(), back.face_count()), (2, 12));
|
||||
let got = super::smlib_body(&back).unwrap().volume(1e-7).unwrap();
|
||||
assert!((got - (64_000.0 - 125.0)).abs() < 1e-6, "{got}");
|
||||
}
|
||||
|
||||
@@ -759,7 +759,7 @@ fn native_ordered(arrays: &Arrays) -> Res<(b::Brep, Report, Order)> {
|
||||
for fu in shell_faceuses.get(side).ok_or_else(|| invalid("shell"))?.clone() {
|
||||
let (f, same) = faceuse(fu)?;
|
||||
// A sheet lists both uses of each face in its one shell: keep the `same` one.
|
||||
if side == mate && !same {
|
||||
if mate == s && !same {
|
||||
continue;
|
||||
}
|
||||
if !face_uses.get(f).is_some_and(|u| u.iter().any(|(o, _)| *o == mate)) {
|
||||
|
||||
Reference in New Issue
Block a user