Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add SurfaceVertex #1048

Merged
merged 24 commits into from
Sep 6, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion crates/fj-kernel/src/algorithms/approx/curve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ impl Approx for Curve {
tolerance: Tolerance,
range: Self::Params,
) -> Self::Approximation {
self.global()
self.global_form()
.approx(tolerance, range)
.into_iter()
.map(|(point_curve, point_global)| {
Expand Down
7 changes: 4 additions & 3 deletions crates/fj-kernel/src/algorithms/approx/edge.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,16 +15,17 @@ impl Approx for Edge {
) -> Self::Approximation {
// The range is only used for circles right now.
let boundary = match self.vertices().get() {
Some(vertices) => vertices
.map(|vertex| (vertex.position(), vertex.global().position())),
Some(vertices) => vertices.map(|vertex| {
(vertex.position(), vertex.global_form().position())
}),
None => {
let start_curve = Point::from([Scalar::ZERO]);
let end_curve = Point::from([Scalar::TAU]);

// We're dealing with a circle here. Start and end are identical
// points, in global coordinates.
let point_global = self
.global()
.global_form()
.curve()
.kind()
.point_from_curve_coords(start_curve);
Expand Down
6 changes: 3 additions & 3 deletions crates/fj-kernel/src/algorithms/intersect/face_point.rs
Original file line number Diff line number Diff line change
Expand Up @@ -238,8 +238,8 @@ mod tests {
.copied()
.find(|edge| {
let [a, b] = edge.vertices().get_or_panic();
a.global().position() == Point::from([0., 0., 0.])
&& b.global().position() == Point::from([2., 0., 0.])
a.global_form().position() == Point::from([0., 0., 0.])
&& b.global_form().position() == Point::from([2., 0., 0.])
})
.unwrap();
assert_eq!(
Expand All @@ -261,7 +261,7 @@ mod tests {
.vertex_iter()
.copied()
.find(|vertex| {
vertex.global().position() == Point::from([1., 0., 0.])
vertex.global_form().position() == Point::from([1., 0., 0.])
})
.unwrap();
assert_eq!(
Expand Down
6 changes: 3 additions & 3 deletions crates/fj-kernel/src/algorithms/intersect/ray_face.rs
Original file line number Diff line number Diff line change
Expand Up @@ -217,8 +217,8 @@ mod tests {
.copied()
.find(|edge| {
let [a, b] = edge.vertices().get_or_panic();
a.global().position() == Point::from([1., 0., 1.])
&& b.global().position() == Point::from([1., 0., -1.])
a.global_form().position() == Point::from([1., 0., 1.])
&& b.global_form().position() == Point::from([1., 0., -1.])
})
.unwrap();
assert_eq!(
Expand All @@ -240,7 +240,7 @@ mod tests {
.vertex_iter()
.copied()
.find(|vertex| {
vertex.global().position() == Point::from([1., 0., 0.])
vertex.global_form().position() == Point::from([1., 0., 0.])
})
.unwrap();
assert_eq!(
Expand Down
2 changes: 1 addition & 1 deletion crates/fj-kernel/src/algorithms/reverse/curve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ impl Reverse for Curve {
Curve::new(
*self.surface(),
self.kind().reverse(),
self.global().reverse(),
self.global_form().reverse(),
)
}
}
Expand Down
28 changes: 25 additions & 3 deletions crates/fj-kernel/src/algorithms/reverse/face.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
use fj_math::{Circle, Line, Point, Vector};

use crate::objects::{Curve, CurveKind, Cycle, Edge, Face, Vertex};
use crate::objects::{
Curve, CurveKind, Cycle, Edge, Face, SurfaceVertex, Vertex,
};

use super::Reverse;

Expand Down Expand Up @@ -72,12 +74,32 @@ fn reverse_local_coordinates_in_cycle<'r>(
Curve::new(
edge.curve().surface().reverse(),
local,
*edge.curve().global(),
*edge.curve().global_form(),
)
};

let vertices = edge.vertices().map(|vertex| {
Vertex::new(vertex.position(), curve, *vertex.global())
let surface_vertex = {
let vertex = vertex.surface_form();

let position = Point::from([
vertex.position().u,
-vertex.position().v,
]);

SurfaceVertex::new(
position,
vertex.surface().reverse(),
*vertex.global_form(),
)
};

Vertex::new(
vertex.position(),
curve,
surface_vertex,
*vertex.global_form(),
)
});

Edge::from_curve_and_vertices(curve, vertices)
Expand Down
2 changes: 1 addition & 1 deletion crates/fj-kernel/src/algorithms/sweep/curve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ impl Sweep for Curve {
tolerance: impl Into<crate::algorithms::approx::Tolerance>,
color: fj_interop::mesh::Color,
) -> Self::Swept {
self.global().sweep(path, tolerance, color)
self.global_form().sweep(path, tolerance, color)
}
}

Expand Down
93 changes: 67 additions & 26 deletions crates/fj-kernel/src/algorithms/sweep/edge.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@ use crate::{
transform::TransformObject,
},
objects::{
Curve, CurveKind, Cycle, Edge, Face, GlobalEdge, Surface, Vertex,
VerticesOfEdge,
Curve, CurveKind, Cycle, Edge, Face, GlobalEdge, Surface,
SurfaceVertex, Vertex, VerticesOfEdge,
},
};

Expand Down Expand Up @@ -57,27 +57,51 @@ fn create_non_continuous_side_face(
let bottom_edge = {
let vertices = edge.vertices().get_or_panic();

let points_curve_and_surface = vertices.map(|vertex| {
(vertex.position(), [vertex.position().t, Scalar::ZERO])
});

let curve = {
// Please note that creating a line here is correct, even if the
// global curve is a circle. Projected into the side surface, it is
// going to be a line either way.
let points = vertices.map(|vertex| {
(vertex.position(), [vertex.position().t, Scalar::ZERO])
});
let kind =
CurveKind::Line(Line::from_points_with_line_coords(points));
let kind = CurveKind::Line(Line::from_points_with_line_coords(
points_curve_and_surface,
));

Curve::new(surface, kind, *edge.curve().global())
Curve::new(surface, kind, *edge.curve().global_form())
};

let vertices = {
let vertices = vertices.map(|vertex| {
Vertex::new(vertex.position(), curve, *vertex.global())
});
let points_surface = points_curve_and_surface
.map(|(_, point_surface)| point_surface);

// Can be cleaned up, once `zip` is stable:
// https://doc.rust-lang.org/std/primitive.array.html#method.zip
let [a_vertex, b_vertex] = vertices;
let [a_surface, b_surface] = points_surface;
let vertices_with_surface_points =
[(a_vertex, a_surface), (b_vertex, b_surface)];

let vertices =
vertices_with_surface_points.map(|(vertex, point_surface)| {
let surface_vertex = SurfaceVertex::new(
point_surface,
surface,
*vertex.global_form(),
);

Vertex::new(
vertex.position(),
curve,
surface_vertex,
*vertex.global_form(),
)
});
VerticesOfEdge::from_vertices(vertices)
};

Edge::new(curve, vertices, *edge.global())
Edge::new(curve, vertices, *edge.global_form())
};

let side_edges = bottom_edge
Expand All @@ -90,40 +114,57 @@ fn create_non_continuous_side_face(

let global_vertices = side_edges.map(|edge| {
let [_, vertex] = edge.vertices().get_or_panic();
*vertex.global()
*vertex.global_form()
});

let points_curve_and_surface = bottom_vertices.map(|vertex| {
(vertex.position(), [vertex.position().t, Scalar::ONE])
});

let curve = {
let global = bottom_edge.curve().global().translate(path.inner());
let global =
bottom_edge.curve().global_form().translate(path.inner());

// Please note that creating a line here is correct, even if the
// global curve is a circle. Projected into the side surface, it is
// going to be a line either way.
let points = bottom_vertices.map(|vertex| {
(vertex.position(), [vertex.position().t, Scalar::ONE])
});
let kind =
CurveKind::Line(Line::from_points_with_line_coords(points));
let kind = CurveKind::Line(Line::from_points_with_line_coords(
points_curve_and_surface,
));

Curve::new(surface, kind, global)
};

let global = {
GlobalEdge::new(
*curve.global(),
*curve.global_form(),
VerticesOfEdge::from_vertices(global_vertices),
)
};

let vertices = {
let surface_points = points_curve_and_surface
.map(|(_, point_surface)| point_surface);

// Can be cleaned up, once `zip` is stable:
// https://doc.rust-lang.org/std/primitive.array.html#method.zip
let [a_bottom, b_bottom] = bottom_vertices;
let [a_vertex, b_vertex] = bottom_vertices;
let [a_surface, b_surface] = surface_points;
let [a_global, b_global] = global_vertices;
let vertices = [(a_bottom, a_global), (b_bottom, b_global)];

vertices.map(|(bottom, global)| {
Vertex::new(bottom.position(), curve, global)
let vertices = [
(a_vertex, a_surface, a_global),
(b_vertex, b_surface, b_global),
];

vertices.map(|(vertex, point_surface, vertex_global)| {
let vertex_surface =
SurfaceVertex::new(point_surface, surface, vertex_global);
Vertex::new(
vertex.position(),
curve,
vertex_surface,
vertex_global,
)
})
};

Expand All @@ -145,7 +186,7 @@ fn create_non_continuous_side_face(
let [_, prev_last] = edges[i].vertices().get_or_panic();
let [next_first, _] = edges[j].vertices().get_or_panic();

if prev_last.global() != next_first.global() {
if prev_last.global_form() != next_first.global_form() {
edges[j] = edges[j].reverse();
}

Expand Down
57 changes: 41 additions & 16 deletions crates/fj-kernel/src/algorithms/sweep/vertex.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ use crate::{
algorithms::approx::Tolerance,
objects::{
Curve, CurveKind, Edge, GlobalCurve, GlobalEdge, GlobalVertex, Surface,
SweptCurve, Vertex, VerticesOfEdge,
SurfaceVertex, SweptCurve, Vertex, VerticesOfEdge,
},
};

Expand Down Expand Up @@ -61,14 +61,14 @@ impl Sweep for (Vertex, Surface) {
path: surface_path,
}) = surface;

assert_eq!(vertex.curve().global().kind(), &surface_curve);
assert_eq!(vertex.curve().global_form().kind(), &surface_curve);
assert_eq!(path.inner(), surface_path);
}

// With that out of the way, let's start by creating the `GlobalEdge`,
// as that is the most straight-forward part of this operations, and
// we're going to need it soon anyway.
let edge_global = vertex.global().sweep(path, tolerance, color);
let edge_global = vertex.global_form().sweep(path, tolerance, color);

// Next, let's compute the surface coordinates of the two vertices of
// the output `Edge`, as we're going to need these for the rest of this
Expand All @@ -84,29 +84,54 @@ impl Sweep for (Vertex, Surface) {
// thereby defined its coordinate system. That makes the v-coordinates
// straight-forward: The start of the edge is at zero, the end is at
// one.
let u = vertex.position().t;
let v_a = Scalar::ZERO;
let v_b = Scalar::ONE;
let points_surface = [
Point::from([vertex.position().t, Scalar::ZERO]),
Point::from([vertex.position().t, Scalar::ONE]),
];

// Armed with those coordinates, creating the `Curve` of the output
// `Edge` becomes straight-forward.
let curve = {
let a = Point::from([u, v_a]);
let b = Point::from([u, v_b]);

let line = Line::from_points([a, b]);
let line = Line::from_points(points_surface);

Curve::new(surface, CurveKind::Line(line), *edge_global.curve())
};

// And now the vertices. Again, nothing wild here.
let vertices = {
let [&a, &b] = edge_global.vertices().get_or_panic();

let a = Vertex::new([v_a], curve, a);
let b = Vertex::new([v_b], curve, b);

VerticesOfEdge::from_vertices([a, b])
let vertices_global = edge_global.vertices().get_or_panic();

// Can be cleaned up, once `zip` is stable:
// https://doc.rust-lang.org/std/primitive.array.html#method.zip
let [a_surface, b_surface] = points_surface;
let [a_global, b_global] = vertices_global;
let vertices_surface =
[(a_surface, a_global), (b_surface, b_global)].map(
|(point_surface, &vertex_global)| {
SurfaceVertex::new(
point_surface,
surface,
vertex_global,
)
},
);

// Can be cleaned up, once `zip` is stable:
// https://doc.rust-lang.org/std/primitive.array.html#method.zip
let [a_surface, b_surface] = vertices_surface;
let [a_global, b_global] = vertices_global;
let vertices = [(a_surface, a_global), (b_surface, b_global)];

let vertices = vertices.map(|(vertex_surface, &vertex_global)| {
Vertex::new(
[vertex_surface.position().v],
curve,
vertex_surface,
vertex_global,
)
});

VerticesOfEdge::from_vertices(vertices)
};

// And finally, creating the output `Edge` is just a matter of
Expand Down
Loading