From ae788361afc6de29a8a0d4ed214a84f2c7585ad6 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 20 May 2022 12:36:08 +0200 Subject: [PATCH 1/3] Expect surface coordinates in `FaceBuilder` --- .../fj-kernel/src/algorithms/approx/faces.rs | 25 ++++++++----- .../src/algorithms/triangulation/mod.rs | 36 ++++++++++++------- crates/fj-kernel/src/topology/builder.rs | 14 +++++--- crates/fj-operations/src/sketch.rs | 6 +--- 4 files changed, 52 insertions(+), 29 deletions(-) diff --git a/crates/fj-kernel/src/algorithms/approx/faces.rs b/crates/fj-kernel/src/algorithms/approx/faces.rs index 69127929f..5cb6afd63 100644 --- a/crates/fj-kernel/src/algorithms/approx/faces.rs +++ b/crates/fj-kernel/src/algorithms/approx/faces.rs @@ -97,21 +97,30 @@ mod tests { let mut shape = Shape::new(); - let a = Point::from([0., 0., 0.]); - let b = Point::from([3., 0., 0.]); - let c = Point::from([3., 3., 0.]); - let d = Point::from([0., 3., 0.]); + let a = Point::from([0., 0.]); + let b = Point::from([3., 0.]); + let c = Point::from([3., 3.]); + let d = Point::from([0., 3.]); - let e = Point::from([1., 1., 0.]); - let f = Point::from([2., 1., 0.]); - let g = Point::from([2., 2., 0.]); - let h = Point::from([1., 2., 0.]); + let e = Point::from([1., 1.]); + let f = Point::from([2., 1.]); + let g = Point::from([2., 2.]); + let h = Point::from([1., 2.]); let face = Face::builder(Surface::xy_plane(), &mut shape) .with_exterior_polygon([a, b, c, d]) .with_interior_polygon([e, f, g, h]) .build()?; + let a = a.to_xyz(); + let b = b.to_xyz(); + let c = c.to_xyz(); + let d = d.to_xyz(); + let e = e.to_xyz(); + let f = f.to_xyz(); + let g = g.to_xyz(); + let h = h.to_xyz(); + let a = geometry::Point::new(a, a); let b = geometry::Point::new(b, b); let c = geometry::Point::new(c, c); diff --git a/crates/fj-kernel/src/algorithms/triangulation/mod.rs b/crates/fj-kernel/src/algorithms/triangulation/mod.rs index 7dcc47ab7..06072e0b4 100644 --- a/crates/fj-kernel/src/algorithms/triangulation/mod.rs +++ b/crates/fj-kernel/src/algorithms/triangulation/mod.rs @@ -95,15 +95,20 @@ mod tests { fn simple() -> anyhow::Result<()> { let mut shape = Shape::new(); - let a = [0., 0., 0.]; - let b = [2., 0., 0.]; - let c = [2., 2., 0.]; - let d = [0., 1., 0.]; + let a = [0., 0.]; + let b = [2., 0.]; + let c = [2., 2.]; + let d = [0., 1.]; Face::builder(Surface::xy_plane(), &mut shape) .with_exterior_polygon([a, b, c, d]) .build()?; + let a = Point::from(a).to_xyz(); + let b = Point::from(b).to_xyz(); + let c = Point::from(c).to_xyz(); + let d = Point::from(d).to_xyz(); + let triangles = triangulate(shape)?; assert!(triangles.contains_triangle([a, b, d])); assert!(triangles.contains_triangle([b, c, d])); @@ -117,15 +122,15 @@ mod tests { fn simple_hole() -> anyhow::Result<()> { let mut shape = Shape::new(); - let a = [0., 0., 0.]; - let b = [4., 0., 0.]; - let c = [4., 4., 0.]; - let d = [0., 4., 0.]; + let a = [0., 0.]; + let b = [4., 0.]; + let c = [4., 4.]; + let d = [0., 4.]; - let e = [1., 1., 0.]; - let f = [3., 1., 0.]; - let g = [3., 3., 0.]; - let h = [1., 2., 0.]; + let e = [1., 1.]; + let f = [3., 1.]; + let g = [3., 3.]; + let h = [1., 2.]; Face::builder(Surface::xy_plane(), &mut shape) .with_exterior_polygon([a, b, c, d]) @@ -134,6 +139,13 @@ mod tests { let triangles = triangulate(shape)?; + let a = Point::from(a).to_xyz(); + let d = Point::from(d).to_xyz(); + let e = Point::from(e).to_xyz(); + let f = Point::from(f).to_xyz(); + let g = Point::from(g).to_xyz(); + let h = Point::from(h).to_xyz(); + // Should contain some triangles from the polygon. Don't need to test // them all. assert!(triangles.contains_triangle([a, e, h])); diff --git a/crates/fj-kernel/src/topology/builder.rs b/crates/fj-kernel/src/topology/builder.rs index 61ab5e259..316503a75 100644 --- a/crates/fj-kernel/src/topology/builder.rs +++ b/crates/fj-kernel/src/topology/builder.rs @@ -144,8 +144,8 @@ impl<'r> CycleBuilder<'r> { #[must_use] pub struct FaceBuilder<'r> { surface: Surface, - exterior: Option>>, - interiors: Vec>>, + exterior: Option>>, + interiors: Vec>>, shape: &'r mut Shape, } @@ -165,7 +165,7 @@ impl<'r> FaceBuilder<'r> { /// Make the exterior or the face a polygon pub fn with_exterior_polygon( self, - points: impl IntoIterator>>, + points: impl IntoIterator>>, ) -> Self { let points = points.into_iter().map(Into::into).collect(); @@ -178,7 +178,7 @@ impl<'r> FaceBuilder<'r> { /// Add an interior polygon to the face pub fn with_interior_polygon( self, - points: impl IntoIterator>>, + points: impl IntoIterator>>, ) -> Self { let points = points.into_iter().map(Into::into).collect(); @@ -194,12 +194,18 @@ impl<'r> FaceBuilder<'r> { let mut exteriors = Vec::new(); if let Some(points) = self.exterior { + let points = points + .into_iter() + .map(|point| surface.get().point_from_surface_coords(point)); let cycle = Cycle::builder(self.shape).build_polygon(points)?; exteriors.push(cycle); } let mut interiors = Vec::new(); for points in self.interiors { + let points = points + .into_iter() + .map(|point| surface.get().point_from_surface_coords(point)); let cycle = Cycle::builder(self.shape).build_polygon(points)?; interiors.push(cycle); } diff --git a/crates/fj-operations/src/sketch.rs b/crates/fj-operations/src/sketch.rs index 1100fc540..9b3bebfdf 100644 --- a/crates/fj-operations/src/sketch.rs +++ b/crates/fj-operations/src/sketch.rs @@ -18,11 +18,7 @@ impl ToShape for fj::Sketch { let mut shape = Shape::new(); let surface = Surface::xy_plane(); - let points = self - .to_points() - .into_iter() - .map(Point::from) - .map(|point| surface.point_from_surface_coords(point)); + let points = self.to_points().into_iter().map(Point::from); Face::builder(surface, &mut shape) .with_exterior_polygon(points) From 8b4eb528606883c4bccee4fe64ab87864a1951cf Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 20 May 2022 12:44:55 +0200 Subject: [PATCH 2/3] Require `Surface` when building cycle --- crates/fj-kernel/src/topology/builder.rs | 14 ++++++++++---- crates/fj-kernel/src/topology/cycle.rs | 9 ++++++--- 2 files changed, 16 insertions(+), 7 deletions(-) diff --git a/crates/fj-kernel/src/topology/builder.rs b/crates/fj-kernel/src/topology/builder.rs index 316503a75..3ae800a3c 100644 --- a/crates/fj-kernel/src/topology/builder.rs +++ b/crates/fj-kernel/src/topology/builder.rs @@ -102,13 +102,17 @@ impl<'r> EdgeBuilder<'r> { /// API for building a [`Cycle`] #[must_use] pub struct CycleBuilder<'r> { + _surface: Surface, shape: &'r mut Shape, } impl<'r> CycleBuilder<'r> { /// Construct a new instance of `CycleBuilder` - pub fn new(shape: &'r mut Shape) -> Self { - Self { shape } + pub fn new(surface: Surface, shape: &'r mut Shape) -> Self { + Self { + _surface: surface, + shape, + } } /// Build a polygon from a list of points @@ -197,7 +201,8 @@ impl<'r> FaceBuilder<'r> { let points = points .into_iter() .map(|point| surface.get().point_from_surface_coords(point)); - let cycle = Cycle::builder(self.shape).build_polygon(points)?; + let cycle = Cycle::builder(self.surface, self.shape) + .build_polygon(points)?; exteriors.push(cycle); } @@ -206,7 +211,8 @@ impl<'r> FaceBuilder<'r> { let points = points .into_iter() .map(|point| surface.get().point_from_surface_coords(point)); - let cycle = Cycle::builder(self.shape).build_polygon(points)?; + let cycle = Cycle::builder(self.surface, self.shape) + .build_polygon(points)?; interiors.push(cycle); } diff --git a/crates/fj-kernel/src/topology/cycle.rs b/crates/fj-kernel/src/topology/cycle.rs index 8f18b9d94..005b431b0 100644 --- a/crates/fj-kernel/src/topology/cycle.rs +++ b/crates/fj-kernel/src/topology/cycle.rs @@ -1,4 +1,7 @@ -use crate::shape::{Handle, LocalForm, Shape}; +use crate::{ + geometry::Surface, + shape::{Handle, LocalForm, Shape}, +}; use super::{CycleBuilder, Edge}; @@ -32,8 +35,8 @@ impl Cycle<3> { } /// Build a cycle using the [`CycleBuilder`] API - pub fn builder(shape: &mut Shape) -> CycleBuilder { - CycleBuilder::new(shape) + pub fn builder(surface: Surface, shape: &mut Shape) -> CycleBuilder { + CycleBuilder::new(surface, shape) } /// Access the edges that this cycle refers to From 89fd88dbe9e0389690e1e2190d07635756f60240 Mon Sep 17 00:00:00 2001 From: Hanno Braun Date: Fri, 20 May 2022 12:48:13 +0200 Subject: [PATCH 3/3] Expect points in surface coords in `CycleBuilder` --- crates/fj-kernel/src/topology/builder.rs | 20 +++++++------------- 1 file changed, 7 insertions(+), 13 deletions(-) diff --git a/crates/fj-kernel/src/topology/builder.rs b/crates/fj-kernel/src/topology/builder.rs index 3ae800a3c..234f75187 100644 --- a/crates/fj-kernel/src/topology/builder.rs +++ b/crates/fj-kernel/src/topology/builder.rs @@ -102,25 +102,25 @@ impl<'r> EdgeBuilder<'r> { /// API for building a [`Cycle`] #[must_use] pub struct CycleBuilder<'r> { - _surface: Surface, + surface: Surface, shape: &'r mut Shape, } impl<'r> CycleBuilder<'r> { /// Construct a new instance of `CycleBuilder` pub fn new(surface: Surface, shape: &'r mut Shape) -> Self { - Self { - _surface: surface, - shape, - } + Self { surface, shape } } /// Build a polygon from a list of points pub fn build_polygon( self, - points: impl IntoIterator>>, + points: impl IntoIterator>>, ) -> ValidationResult> { - let mut points: Vec<_> = points.into_iter().map(Into::into).collect(); + let mut points: Vec<_> = points + .into_iter() + .map(|point| self.surface.point_from_surface_coords(point)) + .collect(); // A polygon is closed, so we need to add the first point at the end // again, for the next step. @@ -198,9 +198,6 @@ impl<'r> FaceBuilder<'r> { let mut exteriors = Vec::new(); if let Some(points) = self.exterior { - let points = points - .into_iter() - .map(|point| surface.get().point_from_surface_coords(point)); let cycle = Cycle::builder(self.surface, self.shape) .build_polygon(points)?; exteriors.push(cycle); @@ -208,9 +205,6 @@ impl<'r> FaceBuilder<'r> { let mut interiors = Vec::new(); for points in self.interiors { - let points = points - .into_iter() - .map(|point| surface.get().point_from_surface_coords(point)); let cycle = Cycle::builder(self.surface, self.shape) .build_polygon(points)?; interiors.push(cycle);