Construction axes, points and planes from model geometry (SOLID ▸ CONSTRUCT): axes through a cylinder/cone/torus, perpendicular to a face at a point, through two planes, two points or an edge; points at a vertex, through two edges, three planes, at the centre of a circle/sphere/torus, at an edge and a plane, along a path; midplane, planes through two edges or three points, tangent to a face, along a path. References (doc::construct::GeoRef) keep picked faces and edges by persistent name and resolve on each evaluation (they follow the model); results live in ModelState.construct, in the component's frame; view::construction_axes/points/planes for the viewport; kernel::face_surface for a face's analytic surface
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01AS5Tn3xieewUSg3uxrMVdL
This commit is contained in:
1 parent
68271137a5
commit
846bb112e2
21 files changed
+1400
-46
No files matched your search
@@ -39,6 +39,7 @@ mod splitface;
|
||||
mod step;
|
||||
mod step_in;
|
||||
mod step_out;
|
||||
mod surface_kind;
|
||||
mod surfaces;
|
||||
mod sweep_path;
|
||||
#[cfg(test)]
|
||||
@@ -65,6 +66,7 @@ pub use splitface::{SplitTool, split_body, split_faces, split_faces_with_map};
|
||||
pub use step::step_export;
|
||||
pub use step_in::{ImportedBody, StepImport, StepNode, step_import, step_import_shared, step_orientation_errors, step_validate};
|
||||
pub use step_out::{ExportBody, ExportProduct, StepHeader, step_export_bodies, step_export_products};
|
||||
pub use surface_kind::{FaceSurface, face_surface};
|
||||
pub use surfaces::{copy_faces, extend, patch_edges, patch_region, stitch, thicken, trim};
|
||||
pub use sweep_path::sweep_path;
|
||||
pub use topo::{CylinderFace, cylinder_face_at};
|
||||
|
||||
@@ -14,7 +14,7 @@ use crate::body::{Body, Solid, from_p3, p3};
|
||||
use crate::{KernelError, Result, guard};
|
||||
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
enum Surf {
|
||||
pub(crate) enum Surf {
|
||||
/// Outward normal and offset: n·x = d.
|
||||
Plane { n: Vec3, d: f64 },
|
||||
/// Axis point and direction, radius; `convex` when the outward normal points away from
|
||||
@@ -211,7 +211,7 @@ fn samples(f: &mt::Face) -> Vec<(Vec3, Vec3)> {
|
||||
}
|
||||
|
||||
/// What surface a face lies on (planes and cylinders only).
|
||||
fn surf_of(f: &mt::Face, tol: f64) -> Option<Surf> {
|
||||
pub(crate) fn surf_of(f: &mt::Face, tol: f64) -> Option<Surf> {
|
||||
if let mt::Surface::Plane(pl) = f.oriented_surface() {
|
||||
let n = pl.normal();
|
||||
let n = Vec3::new(n.x, n.y, n.z).normalized()?;
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
//! What surface a face lies on (plane, cylinder, cone, sphere, torus), for construction
|
||||
//! geometry: axes through round faces, centres of spheres and tori.
|
||||
|
||||
use solvecraft_geom::Vec3;
|
||||
|
||||
use crate::Body;
|
||||
use crate::offset::{Surf, surf_of};
|
||||
|
||||
/// A face's analytic surface. Axes are unit vectors.
|
||||
#[derive(Clone, Copy, Debug, PartialEq)]
|
||||
pub enum FaceSurface {
|
||||
/// Outward unit normal and a point on the plane.
|
||||
Plane {
|
||||
normal: Vec3,
|
||||
point: Vec3,
|
||||
},
|
||||
Cylinder {
|
||||
origin: Vec3,
|
||||
axis: Vec3,
|
||||
radius: f64,
|
||||
},
|
||||
/// Apex, axis pointing into the cone, half-angle (radians).
|
||||
Cone {
|
||||
apex: Vec3,
|
||||
axis: Vec3,
|
||||
half_angle: f64,
|
||||
},
|
||||
Sphere {
|
||||
center: Vec3,
|
||||
radius: f64,
|
||||
},
|
||||
/// Centre of the ring, its axis, the ring (major) and tube (minor) radii.
|
||||
Torus {
|
||||
center: Vec3,
|
||||
axis: Vec3,
|
||||
major: f64,
|
||||
minor: f64,
|
||||
},
|
||||
}
|
||||
|
||||
/// The surface of face `face` (in face order), if it is one of the analytic kinds.
|
||||
pub fn face_surface(b: &Body, face: usize) -> Option<FaceSurface> {
|
||||
let f = b.solid.face_iter().nth(face)?;
|
||||
let tol = (b.size() * 1e-7).max(1e-9) * 100.0;
|
||||
Some(match surf_of(f, tol)? {
|
||||
Surf::Plane { n, d } => FaceSurface::Plane { normal: n, point: n * d },
|
||||
Surf::Cylinder { o, a, r, .. } => FaceSurface::Cylinder { origin: o, axis: a, radius: r },
|
||||
Surf::Cone { v, a, half, .. } => FaceSurface::Cone { apex: v, axis: a, half_angle: half },
|
||||
Surf::Sphere { c, r, .. } => FaceSurface::Sphere { center: c, radius: r },
|
||||
Surf::Torus { o, a, big, h, r, .. } => FaceSurface::Torus { center: o + a * h, axis: a, major: big, minor: r },
|
||||
})
|
||||
}
|
||||
Reference in new issue
Block a user