From cf24503a29ffb1b3a6d913f085a5e703770a177e Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:33:40 +0200 Subject: [PATCH 01/11] Document module --- crates/fj-kernel/src/algorithms/approx/mod.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/crates/fj-kernel/src/algorithms/approx/mod.rs b/crates/fj-kernel/src/algorithms/approx/mod.rs index e17e84a51..893c871f5 100644 --- a/crates/fj-kernel/src/algorithms/approx/mod.rs +++ b/crates/fj-kernel/src/algorithms/approx/mod.rs @@ -1,3 +1,5 @@ +//! Approximation of objects + mod curves; mod cycles; mod edges; From 76a7990801847920e476e107fd7145b772f2f121 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:33:45 +0200 Subject: [PATCH 02/11] Make module public --- crates/fj-kernel/src/algorithms/mod.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/fj-kernel/src/algorithms/mod.rs b/crates/fj-kernel/src/algorithms/mod.rs index 2ff51f54d..865312017 100644 --- a/crates/fj-kernel/src/algorithms/mod.rs +++ b/crates/fj-kernel/src/algorithms/mod.rs @@ -3,11 +3,11 @@ //! Algorithmic code is collected in this module, to keep other modules focused //! on their respective purpose. -mod approx; mod reverse; mod transform; mod triangulate; +pub mod approx; pub mod intersect; pub mod sweep; From 4e2f43fb0236ec40b9e3f7fd9486f7bdf14e7669 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:37:03 +0200 Subject: [PATCH 03/11] Remove re-exports of approximation types --- crates/fj-app/src/args.rs | 2 +- crates/fj-kernel/src/algorithms/approx/curves.rs | 2 +- crates/fj-kernel/src/algorithms/mod.rs | 1 - crates/fj-kernel/src/algorithms/sweep/edge.rs | 2 +- crates/fj-kernel/src/algorithms/sweep/face.rs | 2 +- crates/fj-kernel/src/algorithms/sweep/mod.rs | 2 +- crates/fj-kernel/src/algorithms/sweep/sketch.rs | 4 ++-- crates/fj-kernel/src/algorithms/triangulate/mod.rs | 4 ++-- crates/fj-operations/src/difference_2d.rs | 2 +- crates/fj-operations/src/group.rs | 2 +- crates/fj-operations/src/lib.rs | 2 +- crates/fj-operations/src/shape_processor.rs | 5 ++++- crates/fj-operations/src/sketch.rs | 2 +- crates/fj-operations/src/sweep.rs | 2 +- crates/fj-operations/src/transform.rs | 2 +- 15 files changed, 19 insertions(+), 17 deletions(-) diff --git a/crates/fj-app/src/args.rs b/crates/fj-app/src/args.rs index d72c7d1ef..b0828cb79 100644 --- a/crates/fj-app/src/args.rs +++ b/crates/fj-app/src/args.rs @@ -2,7 +2,7 @@ use std::{path::PathBuf, str::FromStr as _}; use anyhow::anyhow; use fj_host::Parameters; -use fj_kernel::algorithms::Tolerance; +use fj_kernel::algorithms::approx::Tolerance; use fj_math::Scalar; /// Fornjot - Experimental CAD System diff --git a/crates/fj-kernel/src/algorithms/approx/curves.rs b/crates/fj-kernel/src/algorithms/approx/curves.rs index 33f763442..8534f60df 100644 --- a/crates/fj-kernel/src/algorithms/approx/curves.rs +++ b/crates/fj-kernel/src/algorithms/approx/curves.rs @@ -69,7 +69,7 @@ fn number_of_vertices_for_circle(tolerance: Tolerance, radius: Scalar) -> u64 { mod tests { use fj_math::Scalar; - use crate::algorithms::Tolerance; + use crate::algorithms::approx::Tolerance; #[test] fn number_of_vertices_for_circle() { diff --git a/crates/fj-kernel/src/algorithms/mod.rs b/crates/fj-kernel/src/algorithms/mod.rs index 865312017..14333948a 100644 --- a/crates/fj-kernel/src/algorithms/mod.rs +++ b/crates/fj-kernel/src/algorithms/mod.rs @@ -12,7 +12,6 @@ pub mod intersect; pub mod sweep; pub use self::{ - approx::{CycleApprox, FaceApprox, InvalidTolerance, Tolerance}, reverse::reverse_face, transform::{transform_faces, TransformObject}, triangulate::triangulate, diff --git a/crates/fj-kernel/src/algorithms/sweep/edge.rs b/crates/fj-kernel/src/algorithms/sweep/edge.rs index ff9930281..3dc962241 100644 --- a/crates/fj-kernel/src/algorithms/sweep/edge.rs +++ b/crates/fj-kernel/src/algorithms/sweep/edge.rs @@ -2,7 +2,7 @@ use fj_interop::mesh::Color; use fj_math::{Point, Transform, Triangle}; use crate::{ - algorithms::{CycleApprox, Tolerance}, + algorithms::approx::{CycleApprox, Tolerance}, objects::{ Curve, CurveKind, Cycle, Edge, Face, GlobalCurve, GlobalVertex, Surface, Vertex, VerticesOfEdge, diff --git a/crates/fj-kernel/src/algorithms/sweep/face.rs b/crates/fj-kernel/src/algorithms/sweep/face.rs index dccca595d..e6f412a50 100644 --- a/crates/fj-kernel/src/algorithms/sweep/face.rs +++ b/crates/fj-kernel/src/algorithms/sweep/face.rs @@ -1,7 +1,7 @@ use fj_interop::mesh::Color; use crate::{ - algorithms::{reverse_face, Tolerance, TransformObject}, + algorithms::{approx::Tolerance, reverse_face, TransformObject}, objects::{Face, Shell}, }; diff --git a/crates/fj-kernel/src/algorithms/sweep/mod.rs b/crates/fj-kernel/src/algorithms/sweep/mod.rs index 4ced4d0df..746bba07a 100644 --- a/crates/fj-kernel/src/algorithms/sweep/mod.rs +++ b/crates/fj-kernel/src/algorithms/sweep/mod.rs @@ -7,7 +7,7 @@ mod sketch; use fj_interop::mesh::Color; use fj_math::{Scalar, Vector}; -use super::Tolerance; +use super::approx::Tolerance; /// Sweep an object along a path to create another object pub trait Sweep { diff --git a/crates/fj-kernel/src/algorithms/sweep/sketch.rs b/crates/fj-kernel/src/algorithms/sweep/sketch.rs index cf10fe25c..fa1986d2b 100644 --- a/crates/fj-kernel/src/algorithms/sweep/sketch.rs +++ b/crates/fj-kernel/src/algorithms/sweep/sketch.rs @@ -1,7 +1,7 @@ use fj_interop::mesh::Color; use crate::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, objects::{Sketch, Solid}, }; @@ -35,7 +35,7 @@ mod tests { use fj_math::{Point, Scalar, Vector}; use crate::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, iter::ObjectIters, objects::{Face, Sketch, Surface}, }; diff --git a/crates/fj-kernel/src/algorithms/triangulate/mod.rs b/crates/fj-kernel/src/algorithms/triangulate/mod.rs index 27ddb01e8..955f4bafb 100644 --- a/crates/fj-kernel/src/algorithms/triangulate/mod.rs +++ b/crates/fj-kernel/src/algorithms/triangulate/mod.rs @@ -8,7 +8,7 @@ use crate::objects::Face; use self::polygon::Polygon; -use super::{FaceApprox, Tolerance}; +use super::approx::{FaceApprox, Tolerance}; /// Triangulate a shape pub fn triangulate( @@ -65,7 +65,7 @@ mod tests { use fj_math::{Point, Scalar}; use crate::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, objects::{Face, Surface}, }; diff --git a/crates/fj-operations/src/difference_2d.rs b/crates/fj-operations/src/difference_2d.rs index ade0640e9..d00c0af77 100644 --- a/crates/fj-operations/src/difference_2d.rs +++ b/crates/fj-operations/src/difference_2d.rs @@ -1,6 +1,6 @@ use fj_interop::{debug::DebugInfo, mesh::Color}; use fj_kernel::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, iter::ObjectIters, objects::{Curve, Cycle, Edge, Face, GlobalCurve, Sketch}, validation::{validate, Validated, ValidationConfig, ValidationError}, diff --git a/crates/fj-operations/src/group.rs b/crates/fj-operations/src/group.rs index 610f1ec77..ebc91725b 100644 --- a/crates/fj-operations/src/group.rs +++ b/crates/fj-operations/src/group.rs @@ -1,6 +1,6 @@ use fj_interop::debug::DebugInfo; use fj_kernel::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, objects::Face, validation::{validate, Validated, ValidationConfig, ValidationError}, }; diff --git a/crates/fj-operations/src/lib.rs b/crates/fj-operations/src/lib.rs index da6d659fc..4aea443fd 100644 --- a/crates/fj-operations/src/lib.rs +++ b/crates/fj-operations/src/lib.rs @@ -26,7 +26,7 @@ mod transform; use fj_interop::debug::DebugInfo; use fj_kernel::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, objects::{Face, Sketch}, validation::{validate, Validated, ValidationConfig, ValidationError}, }; diff --git a/crates/fj-operations/src/shape_processor.rs b/crates/fj-operations/src/shape_processor.rs index 3ea3f3777..6e3ecbcc2 100644 --- a/crates/fj-operations/src/shape_processor.rs +++ b/crates/fj-operations/src/shape_processor.rs @@ -2,7 +2,10 @@ use fj_interop::{debug::DebugInfo, processed_shape::ProcessedShape}; use fj_kernel::{ - algorithms::{triangulate, InvalidTolerance, Tolerance}, + algorithms::{ + approx::{InvalidTolerance, Tolerance}, + triangulate, + }, validation::{ValidationConfig, ValidationError}, }; use fj_math::Scalar; diff --git a/crates/fj-operations/src/sketch.rs b/crates/fj-operations/src/sketch.rs index 50c028df7..d0c535254 100644 --- a/crates/fj-operations/src/sketch.rs +++ b/crates/fj-operations/src/sketch.rs @@ -1,6 +1,6 @@ use fj_interop::{debug::DebugInfo, mesh::Color}; use fj_kernel::{ - algorithms::Tolerance, + algorithms::approx::Tolerance, objects::{Cycle, Edge, Face, Sketch, Surface}, validation::{validate, Validated, ValidationConfig, ValidationError}, }; diff --git a/crates/fj-operations/src/sweep.rs b/crates/fj-operations/src/sweep.rs index 828ad0702..754e01c6d 100644 --- a/crates/fj-operations/src/sweep.rs +++ b/crates/fj-operations/src/sweep.rs @@ -1,6 +1,6 @@ use fj_interop::{debug::DebugInfo, mesh::Color}; use fj_kernel::{ - algorithms::{sweep::Sweep, Tolerance}, + algorithms::{approx::Tolerance, sweep::Sweep}, objects::Solid, validation::{validate, Validated, ValidationConfig, ValidationError}, }; diff --git a/crates/fj-operations/src/transform.rs b/crates/fj-operations/src/transform.rs index 6d4c2998d..e999859f2 100644 --- a/crates/fj-operations/src/transform.rs +++ b/crates/fj-operations/src/transform.rs @@ -1,6 +1,6 @@ use fj_interop::debug::DebugInfo; use fj_kernel::{ - algorithms::{transform_faces, Tolerance}, + algorithms::{approx::Tolerance, transform_faces}, objects::Face, validation::{validate, Validated, ValidationConfig, ValidationError}, }; From 9ef3f23640800e3b0858fbd36ddd8836ff21dfde Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:39:23 +0200 Subject: [PATCH 04/11] Update module names Other modules in `algorithms` use the singular form for module names that refer to objects, so let's keep it consistent. --- .../src/algorithms/approx/{curves.rs => curve.rs} | 0 .../src/algorithms/approx/{cycles.rs => cycle.rs} | 2 +- .../src/algorithms/approx/{edges.rs => edge.rs} | 0 .../src/algorithms/approx/{faces.rs => face.rs} | 0 crates/fj-kernel/src/algorithms/approx/mod.rs | 12 ++++++------ 5 files changed, 7 insertions(+), 7 deletions(-) rename crates/fj-kernel/src/algorithms/approx/{curves.rs => curve.rs} (100%) rename crates/fj-kernel/src/algorithms/approx/{cycles.rs => cycle.rs} (96%) rename crates/fj-kernel/src/algorithms/approx/{edges.rs => edge.rs} (100%) rename crates/fj-kernel/src/algorithms/approx/{faces.rs => face.rs} (100%) diff --git a/crates/fj-kernel/src/algorithms/approx/curves.rs b/crates/fj-kernel/src/algorithms/approx/curve.rs similarity index 100% rename from crates/fj-kernel/src/algorithms/approx/curves.rs rename to crates/fj-kernel/src/algorithms/approx/curve.rs diff --git a/crates/fj-kernel/src/algorithms/approx/cycles.rs b/crates/fj-kernel/src/algorithms/approx/cycle.rs similarity index 96% rename from crates/fj-kernel/src/algorithms/approx/cycles.rs rename to crates/fj-kernel/src/algorithms/approx/cycle.rs index 4a3ec9a6c..e42d70fbe 100644 --- a/crates/fj-kernel/src/algorithms/approx/cycles.rs +++ b/crates/fj-kernel/src/algorithms/approx/cycle.rs @@ -2,7 +2,7 @@ use fj_math::{Point, Segment}; use crate::objects::Cycle; -use super::{curves::approx_curve, edges::approx_edge, Local, Tolerance}; +use super::{curve::approx_curve, edge::approx_edge, Local, Tolerance}; /// An approximation of a [`Cycle`] #[derive(Debug, Eq, PartialEq, Hash)] diff --git a/crates/fj-kernel/src/algorithms/approx/edges.rs b/crates/fj-kernel/src/algorithms/approx/edge.rs similarity index 100% rename from crates/fj-kernel/src/algorithms/approx/edges.rs rename to crates/fj-kernel/src/algorithms/approx/edge.rs diff --git a/crates/fj-kernel/src/algorithms/approx/faces.rs b/crates/fj-kernel/src/algorithms/approx/face.rs similarity index 100% rename from crates/fj-kernel/src/algorithms/approx/faces.rs rename to crates/fj-kernel/src/algorithms/approx/face.rs diff --git a/crates/fj-kernel/src/algorithms/approx/mod.rs b/crates/fj-kernel/src/algorithms/approx/mod.rs index 893c871f5..c101a7e91 100644 --- a/crates/fj-kernel/src/algorithms/approx/mod.rs +++ b/crates/fj-kernel/src/algorithms/approx/mod.rs @@ -1,15 +1,15 @@ //! Approximation of objects -mod curves; -mod cycles; -mod edges; -mod faces; +mod curve; +mod cycle; +mod edge; +mod face; mod local; mod tolerance; pub use self::{ - cycles::CycleApprox, - faces::FaceApprox, + cycle::CycleApprox, + face::FaceApprox, local::{Local, LocalForm}, tolerance::{InvalidTolerance, Tolerance}, }; From 716508a919588c142341c1cb50b88a190ea75b12 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:38:11 +0200 Subject: [PATCH 05/11] Add `Approx` trait --- crates/fj-kernel/src/algorithms/approx/mod.rs | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/crates/fj-kernel/src/algorithms/approx/mod.rs b/crates/fj-kernel/src/algorithms/approx/mod.rs index c101a7e91..3e389255f 100644 --- a/crates/fj-kernel/src/algorithms/approx/mod.rs +++ b/crates/fj-kernel/src/algorithms/approx/mod.rs @@ -13,3 +13,15 @@ pub use self::{ local::{Local, LocalForm}, tolerance::{InvalidTolerance, Tolerance}, }; + +/// Approximate an object +pub trait Approx { + /// The approximation of the object + type Approximation; + + /// Approximate the object + /// + /// `tolerance` defines how far the approximation is allowed to deviate from + /// the actual object. + fn approx(&self, tolerance: Tolerance) -> Self::Approximation; +} From 37dc85f075fb283d295e73d6f2c18f132055da11 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:48:35 +0200 Subject: [PATCH 06/11] Implement `Approx` for `Face` --- .../fj-kernel/src/algorithms/approx/face.rs | 52 +++++++++---------- .../src/algorithms/triangulate/mod.rs | 4 +- 2 files changed, 27 insertions(+), 29 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/face.rs b/crates/fj-kernel/src/algorithms/approx/face.rs index 602b1c702..1849faf61 100644 --- a/crates/fj-kernel/src/algorithms/approx/face.rs +++ b/crates/fj-kernel/src/algorithms/approx/face.rs @@ -4,30 +4,12 @@ use fj_math::Point; use crate::objects::Face; -use super::{CycleApprox, Local, Tolerance}; +use super::{Approx, CycleApprox, Local, Tolerance}; -/// An approximation of a [`Face`] -#[derive(Debug, Eq, PartialEq)] -pub struct FaceApprox { - /// All points that make up the approximation - /// - /// These could be actual vertices from the model, points that approximate - /// an edge, or points that approximate a face. - pub points: HashSet>>, +impl Approx for Face { + type Approximation = FaceApprox; - /// Approximation of the exterior cycle - pub exterior: CycleApprox, - - /// Approximations of the interior cycles - pub interiors: HashSet, -} - -impl FaceApprox { - /// Compute the approximation of a face - /// - /// `tolerance` defines how far the approximation is allowed to deviate from - /// the actual face. - pub fn new(face: &Face, tolerance: Tolerance) -> Self { + fn approx(&self, tolerance: Tolerance) -> Self::Approximation { // Curved faces whose curvature is not fully defined by their edges // are not supported yet. For that reason, we can fully ignore `face`'s // `surface` field and just pass the edges to `Self::for_edges`. @@ -45,13 +27,13 @@ impl FaceApprox { let mut exteriors = Vec::new(); let mut interiors = HashSet::new(); - for cycle in face.exteriors() { + for cycle in self.exteriors() { let cycle = CycleApprox::new(cycle, tolerance); points.extend(cycle.points.iter().copied()); exteriors.push(cycle); } - for cycle in face.interiors() { + for cycle in self.interiors() { let cycle = CycleApprox::new(cycle, tolerance); points.extend(cycle.points.iter().copied()); @@ -70,7 +52,7 @@ impl FaceApprox { "Approximation only supports faces with one exterior cycle", ); - Self { + FaceApprox { points, exterior, interiors, @@ -78,13 +60,29 @@ impl FaceApprox { } } +/// An approximation of a [`Face`] +#[derive(Debug, Eq, PartialEq)] +pub struct FaceApprox { + /// All points that make up the approximation + /// + /// These could be actual vertices from the model, points that approximate + /// an edge, or points that approximate a face. + pub points: HashSet>>, + + /// Approximation of the exterior cycle + pub exterior: CycleApprox, + + /// Approximations of the interior cycles + pub interiors: HashSet, +} + #[cfg(test)] mod tests { use fj_math::{Point, Scalar}; use map_macro::set; use crate::{ - algorithms::approx::Local, + algorithms::approx::{Approx, Local}, objects::{Face, Surface}, }; @@ -120,7 +118,7 @@ mod tests { let g = Local::new(g, g.to_xyz()); let h = Local::new(h, h.to_xyz()); - let approx = FaceApprox::new(&face, tolerance); + let approx = face.approx(tolerance); let expected = FaceApprox { points: set![a, b, c, d, e, f, g, h], exterior: CycleApprox { diff --git a/crates/fj-kernel/src/algorithms/triangulate/mod.rs b/crates/fj-kernel/src/algorithms/triangulate/mod.rs index 955f4bafb..3eed06237 100644 --- a/crates/fj-kernel/src/algorithms/triangulate/mod.rs +++ b/crates/fj-kernel/src/algorithms/triangulate/mod.rs @@ -8,7 +8,7 @@ use crate::objects::Face; use self::polygon::Polygon; -use super::approx::{FaceApprox, Tolerance}; +use super::approx::{Approx, Tolerance}; /// Triangulate a shape pub fn triangulate( @@ -27,7 +27,7 @@ pub fn triangulate( } let surface = face.surface(); - let approx = FaceApprox::new(&face, tolerance); + let approx = face.approx(tolerance); let points: Vec<_> = approx.points.into_iter().collect(); let face_as_polygon = Polygon::new(*surface) From 085432a7c8b8835f25472d2ea2e822cf2c7b8a3c Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:51:23 +0200 Subject: [PATCH 07/11] Implement `Approx` for `Cycle` --- .../fj-kernel/src/algorithms/approx/cycle.rs | 30 +++++++++---------- .../fj-kernel/src/algorithms/approx/face.rs | 4 +-- crates/fj-kernel/src/algorithms/sweep/edge.rs | 4 +-- 3 files changed, 19 insertions(+), 19 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/cycle.rs b/crates/fj-kernel/src/algorithms/approx/cycle.rs index e42d70fbe..06a9368ab 100644 --- a/crates/fj-kernel/src/algorithms/approx/cycle.rs +++ b/crates/fj-kernel/src/algorithms/approx/cycle.rs @@ -2,24 +2,15 @@ use fj_math::{Point, Segment}; use crate::objects::Cycle; -use super::{curve::approx_curve, edge::approx_edge, Local, Tolerance}; +use super::{curve::approx_curve, edge::approx_edge, Approx, Local, Tolerance}; -/// An approximation of a [`Cycle`] -#[derive(Debug, Eq, PartialEq, Hash)] -pub struct CycleApprox { - /// The points that approximate the cycle - pub points: Vec>>, -} +impl Approx for Cycle { + type Approximation = CycleApprox; -impl CycleApprox { - /// Compute the approximation of a cycle - /// - /// `tolerance` defines how far the approximation is allowed to deviate from - /// the actual face. - pub fn new(cycle: &Cycle, tolerance: Tolerance) -> Self { + fn approx(&self, tolerance: Tolerance) -> Self::Approximation { let mut points = Vec::new(); - for edge in cycle.edges() { + for edge in self.edges() { let mut edge_points = Vec::new(); approx_curve(edge.curve().global(), tolerance, &mut edge_points); approx_edge(*edge.vertices(), &mut edge_points); @@ -37,9 +28,18 @@ impl CycleApprox { // could lead to subtly different surface coordinates. points.dedup_by(|a, b| a.global_form() == b.global_form()); - Self { points } + CycleApprox { points } } +} +/// An approximation of a [`Cycle`] +#[derive(Debug, Eq, PartialEq, Hash)] +pub struct CycleApprox { + /// The points that approximate the cycle + pub points: Vec>>, +} + +impl CycleApprox { /// Construct the segments that approximate the cycle pub fn segments(&self) -> Vec> { let mut segments = Vec::new(); diff --git a/crates/fj-kernel/src/algorithms/approx/face.rs b/crates/fj-kernel/src/algorithms/approx/face.rs index 1849faf61..a88aeee77 100644 --- a/crates/fj-kernel/src/algorithms/approx/face.rs +++ b/crates/fj-kernel/src/algorithms/approx/face.rs @@ -28,13 +28,13 @@ impl Approx for Face { let mut interiors = HashSet::new(); for cycle in self.exteriors() { - let cycle = CycleApprox::new(cycle, tolerance); + let cycle = cycle.approx(tolerance); points.extend(cycle.points.iter().copied()); exteriors.push(cycle); } for cycle in self.interiors() { - let cycle = CycleApprox::new(cycle, tolerance); + let cycle = cycle.approx(tolerance); points.extend(cycle.points.iter().copied()); interiors.insert(cycle); diff --git a/crates/fj-kernel/src/algorithms/sweep/edge.rs b/crates/fj-kernel/src/algorithms/sweep/edge.rs index 3dc962241..21ce2e32b 100644 --- a/crates/fj-kernel/src/algorithms/sweep/edge.rs +++ b/crates/fj-kernel/src/algorithms/sweep/edge.rs @@ -2,7 +2,7 @@ use fj_interop::mesh::Color; use fj_math::{Point, Transform, Triangle}; use crate::{ - algorithms::approx::{CycleApprox, Tolerance}, + algorithms::approx::{Approx, Tolerance}, objects::{ Curve, CurveKind, Cycle, Edge, Face, GlobalCurve, GlobalVertex, Surface, Vertex, VerticesOfEdge, @@ -119,7 +119,7 @@ fn create_continuous_side_face( let placeholder = Surface::xy_plane(); let cycle = Cycle::new(placeholder).with_edges([edge]); - let approx = CycleApprox::new(&cycle, tolerance); + let approx = cycle.approx(tolerance); let mut quads = Vec::new(); for segment in approx.segments() { From 1e29d63674a99d9cf0698bacc1b89c1278f9b50c Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 10:57:41 +0200 Subject: [PATCH 08/11] Implement `Approx` for `Edge` --- crates/fj-kernel/src/algorithms/approx/cycle.rs | 6 ++---- crates/fj-kernel/src/algorithms/approx/edge.rs | 17 +++++++++++++++-- 2 files changed, 17 insertions(+), 6 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/cycle.rs b/crates/fj-kernel/src/algorithms/approx/cycle.rs index 06a9368ab..727b77699 100644 --- a/crates/fj-kernel/src/algorithms/approx/cycle.rs +++ b/crates/fj-kernel/src/algorithms/approx/cycle.rs @@ -2,7 +2,7 @@ use fj_math::{Point, Segment}; use crate::objects::Cycle; -use super::{curve::approx_curve, edge::approx_edge, Approx, Local, Tolerance}; +use super::{Approx, Local, Tolerance}; impl Approx for Cycle { type Approximation = CycleApprox; @@ -11,9 +11,7 @@ impl Approx for Cycle { let mut points = Vec::new(); for edge in self.edges() { - let mut edge_points = Vec::new(); - approx_curve(edge.curve().global(), tolerance, &mut edge_points); - approx_edge(*edge.vertices(), &mut edge_points); + let edge_points = edge.approx(tolerance); points.extend(edge_points.into_iter().map(|point| { let local = edge diff --git a/crates/fj-kernel/src/algorithms/approx/edge.rs b/crates/fj-kernel/src/algorithms/approx/edge.rs index 13c440311..74aa731c3 100644 --- a/crates/fj-kernel/src/algorithms/approx/edge.rs +++ b/crates/fj-kernel/src/algorithms/approx/edge.rs @@ -1,8 +1,21 @@ use fj_math::Point; -use crate::objects::{Vertex, VerticesOfEdge}; +use crate::objects::{Edge, Vertex, VerticesOfEdge}; -use super::Local; +use super::{curve::approx_curve, Approx, Local}; + +impl Approx for Edge { + type Approximation = Vec>>; + + fn approx(&self, tolerance: super::Tolerance) -> Self::Approximation { + let mut points = Vec::new(); + + approx_curve(self.curve().global(), tolerance, &mut points); + approx_edge(*self.vertices(), &mut points); + + points + } +} pub fn approx_edge( vertices: VerticesOfEdge, From 20986a6e8e5f6e1be94997da09e5ff29d05dbac8 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 11:06:42 +0200 Subject: [PATCH 09/11] Implement `Approx` for `Curve` --- crates/fj-kernel/src/algorithms/approx/curve.rs | 14 ++++++++++++-- crates/fj-kernel/src/algorithms/approx/edge.rs | 6 ++---- 2 files changed, 14 insertions(+), 6 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/curve.rs b/crates/fj-kernel/src/algorithms/approx/curve.rs index 8534f60df..13b22dc2d 100644 --- a/crates/fj-kernel/src/algorithms/approx/curve.rs +++ b/crates/fj-kernel/src/algorithms/approx/curve.rs @@ -2,9 +2,19 @@ use std::cmp::max; use fj_math::{Circle, Point, Scalar}; -use crate::objects::{CurveKind, GlobalCurve}; +use crate::objects::{Curve, CurveKind, GlobalCurve}; -use super::{Local, Tolerance}; +use super::{Approx, Local, Tolerance}; + +impl Approx for Curve { + type Approximation = Vec>>; + + fn approx(&self, tolerance: Tolerance) -> Self::Approximation { + let mut points = Vec::new(); + approx_curve(self.global(), tolerance, &mut points); + points + } +} /// Compute an approximation of the curve /// diff --git a/crates/fj-kernel/src/algorithms/approx/edge.rs b/crates/fj-kernel/src/algorithms/approx/edge.rs index 74aa731c3..c632c967a 100644 --- a/crates/fj-kernel/src/algorithms/approx/edge.rs +++ b/crates/fj-kernel/src/algorithms/approx/edge.rs @@ -2,15 +2,13 @@ use fj_math::Point; use crate::objects::{Edge, Vertex, VerticesOfEdge}; -use super::{curve::approx_curve, Approx, Local}; +use super::{Approx, Local}; impl Approx for Edge { type Approximation = Vec>>; fn approx(&self, tolerance: super::Tolerance) -> Self::Approximation { - let mut points = Vec::new(); - - approx_curve(self.curve().global(), tolerance, &mut points); + let mut points = self.curve().approx(tolerance); approx_edge(*self.vertices(), &mut points); points From f3023c775b4f794a57fc7e5d8ee9904358a67150 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 11:12:33 +0200 Subject: [PATCH 10/11] Implement `Approx` for `GlobalCurve` --- .../fj-kernel/src/algorithms/approx/curve.rs | 50 +++++++++---------- 1 file changed, 25 insertions(+), 25 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/curve.rs b/crates/fj-kernel/src/algorithms/approx/curve.rs index 13b22dc2d..36a800a13 100644 --- a/crates/fj-kernel/src/algorithms/approx/curve.rs +++ b/crates/fj-kernel/src/algorithms/approx/curve.rs @@ -10,34 +10,34 @@ impl Approx for Curve { type Approximation = Vec>>; fn approx(&self, tolerance: Tolerance) -> Self::Approximation { - let mut points = Vec::new(); - approx_curve(self.global(), tolerance, &mut points); - points + self.global().approx(tolerance) } } -/// Compute an approximation of the curve -/// -/// `tolerance` defines how far the approximation is allowed to deviate from the -/// actual edge. -/// -/// # Implementation Note -/// -/// This only works as it is, because edges are severely limited and don't -/// define which section of the curve they inhabit. Once they do that, we need -/// an `approximate_between(a, b)` method instead, where `a` and `b` are the -/// vertices that bound the edge on the curve. -/// -/// The `approximate_between` methods of the curves then need to make sure to -/// only return points in between those vertices, not the vertices themselves. -pub fn approx_curve( - curve: &GlobalCurve, - tolerance: Tolerance, - out: &mut Vec>>, -) { - match curve.kind() { - CurveKind::Circle(curve) => approx_circle(curve, tolerance, out), - CurveKind::Line(_) => {} +impl Approx for GlobalCurve { + type Approximation = Vec>>; + + /// Approximate the global curve + /// + /// # Implementation Note + /// + /// This only works as-is, because only circles need to be approximated + /// right now and because only edges that are full circles are supported, as + /// opposed to edges that only inhabit part of the circle. + /// + /// To support that, we will need additional information here, to define + /// between which points the curve needs to be approximated. + fn approx(&self, tolerance: Tolerance) -> Self::Approximation { + let mut points = Vec::new(); + + match self.kind() { + CurveKind::Circle(curve) => { + approx_circle(curve, tolerance, &mut points) + } + CurveKind::Line(_) => {} + } + + points } } From a29e849dd74739a99bbb7025329729c3a67b9e37 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 26 Aug 2022 11:12:56 +0200 Subject: [PATCH 11/11] Update doc comment --- crates/fj-kernel/src/algorithms/approx/curve.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/fj-kernel/src/algorithms/approx/curve.rs b/crates/fj-kernel/src/algorithms/approx/curve.rs index 36a800a13..34c0a9cde 100644 --- a/crates/fj-kernel/src/algorithms/approx/curve.rs +++ b/crates/fj-kernel/src/algorithms/approx/curve.rs @@ -41,7 +41,7 @@ impl Approx for GlobalCurve { } } -/// Approximate the circle +/// Approximate a circle /// /// `tolerance` specifies how much the approximation is allowed to deviate /// from the circle.