mirror of https://github.com/hannobraun/Fornjot
Merge pull request #1815 from hannobraun/operations
Add API for building and updating `Solid`s
This commit is contained in:
commit
6fc68a996c
|
@ -2,12 +2,14 @@ mod cycle;
|
||||||
mod edge;
|
mod edge;
|
||||||
mod face;
|
mod face;
|
||||||
mod shell;
|
mod shell;
|
||||||
|
mod solid;
|
||||||
mod surface;
|
mod surface;
|
||||||
|
|
||||||
pub use self::{
|
pub use self::{
|
||||||
cycle::BuildCycle,
|
cycle::BuildCycle,
|
||||||
edge::BuildHalfEdge,
|
edge::BuildHalfEdge,
|
||||||
face::{BuildFace, Polygon},
|
face::{BuildFace, Polygon},
|
||||||
shell::{BuildShell, Tetrahedron},
|
shell::{BuildShell, TetrahedronShell},
|
||||||
|
solid::{BuildSolid, Tetrahedron},
|
||||||
surface::BuildSurface,
|
surface::BuildSurface,
|
||||||
};
|
};
|
||||||
|
|
|
@ -2,7 +2,9 @@ use fj_math::Point;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
objects::{Face, Shell},
|
objects::{Face, Shell},
|
||||||
operations::{Insert, IsInsertedYes, JoinCycle, UpdateFace},
|
operations::{
|
||||||
|
Insert, IsInserted, IsInsertedNo, IsInsertedYes, JoinCycle, UpdateFace,
|
||||||
|
},
|
||||||
services::Services,
|
services::Services,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -31,7 +33,7 @@ pub trait BuildShell {
|
||||||
fn tetrahedron(
|
fn tetrahedron(
|
||||||
points: [impl Into<Point<3>>; 4],
|
points: [impl Into<Point<3>>; 4],
|
||||||
services: &mut Services,
|
services: &mut Services,
|
||||||
) -> Tetrahedron {
|
) -> TetrahedronShell {
|
||||||
let [a, b, c, d] = points.map(Into::into);
|
let [a, b, c, d] = points.map(Into::into);
|
||||||
|
|
||||||
let abc = Face::triangle([a, b, c], services);
|
let abc = Face::triangle([a, b, c], services);
|
||||||
|
@ -64,7 +66,7 @@ pub trait BuildShell {
|
||||||
|
|
||||||
let [abc, bad, dac, cbd] = triangles;
|
let [abc, bad, dac, cbd] = triangles;
|
||||||
|
|
||||||
Tetrahedron {
|
TetrahedronShell {
|
||||||
shell,
|
shell,
|
||||||
abc,
|
abc,
|
||||||
bad,
|
bad,
|
||||||
|
@ -83,9 +85,9 @@ impl BuildShell for Shell {}
|
||||||
/// `d`, in the order in which they are passed.
|
/// `d`, in the order in which they are passed.
|
||||||
///
|
///
|
||||||
/// Returned by [`BuildShell::tetrahedron`].
|
/// Returned by [`BuildShell::tetrahedron`].
|
||||||
pub struct Tetrahedron {
|
pub struct TetrahedronShell<I: IsInserted = IsInsertedNo> {
|
||||||
/// The shell that forms the tetrahedron
|
/// The shell that forms the tetrahedron
|
||||||
pub shell: Shell,
|
pub shell: I::T<Shell>,
|
||||||
|
|
||||||
/// The face formed by the points `a`, `b`, and `c`.
|
/// The face formed by the points `a`, `b`, and `c`.
|
||||||
pub abc: Polygon<3, IsInsertedYes>,
|
pub abc: Polygon<3, IsInsertedYes>,
|
||||||
|
|
|
@ -0,0 +1,44 @@
|
||||||
|
use fj_math::Point;
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
objects::{Shell, Solid},
|
||||||
|
operations::{
|
||||||
|
build::shell::BuildShell, Insert, IsInsertedYes, TetrahedronShell,
|
||||||
|
UpdateSolid,
|
||||||
|
},
|
||||||
|
services::Services,
|
||||||
|
};
|
||||||
|
|
||||||
|
/// Build a [`Solid`]
|
||||||
|
pub trait BuildSolid {
|
||||||
|
/// Build an empty solid
|
||||||
|
fn empty() -> Solid {
|
||||||
|
Solid::new([])
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Build a tetrahedron from the provided points
|
||||||
|
///
|
||||||
|
/// See [`BuildShell::tetrahedron`] for more information.
|
||||||
|
fn tetrahedron(
|
||||||
|
points: [impl Into<Point<3>>; 4],
|
||||||
|
services: &mut Services,
|
||||||
|
) -> Tetrahedron {
|
||||||
|
let shell = Shell::tetrahedron(points, services).insert(services);
|
||||||
|
let solid = Solid::empty().add_shell(shell.shell.clone());
|
||||||
|
|
||||||
|
Tetrahedron { solid, shell }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl BuildSolid for Solid {}
|
||||||
|
|
||||||
|
/// A tetrahedron
|
||||||
|
///
|
||||||
|
/// Returned by [`BuildSolid::tetrahedron`].
|
||||||
|
pub struct Tetrahedron {
|
||||||
|
/// The solid that forms the tetrahedron
|
||||||
|
pub solid: Solid,
|
||||||
|
|
||||||
|
/// The shell of the tetrahedron
|
||||||
|
pub shell: TetrahedronShell<IsInsertedYes>,
|
||||||
|
}
|
|
@ -7,7 +7,7 @@ use crate::{
|
||||||
storage::Handle,
|
storage::Handle,
|
||||||
};
|
};
|
||||||
|
|
||||||
use super::Polygon;
|
use super::{Polygon, TetrahedronShell};
|
||||||
|
|
||||||
/// Insert an object into its respective store
|
/// Insert an object into its respective store
|
||||||
///
|
///
|
||||||
|
@ -91,3 +91,17 @@ impl<const D: usize> Insert for Polygon<D, IsInsertedNo> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Insert for TetrahedronShell<IsInsertedNo> {
|
||||||
|
type Inserted = TetrahedronShell<IsInsertedYes>;
|
||||||
|
|
||||||
|
fn insert(self, services: &mut Services) -> Self::Inserted {
|
||||||
|
TetrahedronShell {
|
||||||
|
shell: self.shell.insert(services),
|
||||||
|
abc: self.abc,
|
||||||
|
bad: self.bad,
|
||||||
|
dac: self.dac,
|
||||||
|
cbd: self.cbd,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -7,10 +7,12 @@ mod update;
|
||||||
|
|
||||||
pub use self::{
|
pub use self::{
|
||||||
build::{
|
build::{
|
||||||
BuildCycle, BuildFace, BuildHalfEdge, BuildShell, BuildSurface,
|
BuildCycle, BuildFace, BuildHalfEdge, BuildShell, BuildSolid,
|
||||||
Polygon, Tetrahedron,
|
BuildSurface, Polygon, Tetrahedron, TetrahedronShell,
|
||||||
},
|
},
|
||||||
insert::{Insert, IsInserted, IsInsertedNo, IsInsertedYes},
|
insert::{Insert, IsInserted, IsInsertedNo, IsInsertedYes},
|
||||||
join::JoinCycle,
|
join::JoinCycle,
|
||||||
update::{UpdateCycle, UpdateFace, UpdateHalfEdge, UpdateShell},
|
update::{
|
||||||
|
UpdateCycle, UpdateFace, UpdateHalfEdge, UpdateShell, UpdateSolid,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
|
|
|
@ -2,8 +2,9 @@ mod cycle;
|
||||||
mod edge;
|
mod edge;
|
||||||
mod face;
|
mod face;
|
||||||
mod shell;
|
mod shell;
|
||||||
|
mod solid;
|
||||||
|
|
||||||
pub use self::{
|
pub use self::{
|
||||||
cycle::UpdateCycle, edge::UpdateHalfEdge, face::UpdateFace,
|
cycle::UpdateCycle, edge::UpdateHalfEdge, face::UpdateFace,
|
||||||
shell::UpdateShell,
|
shell::UpdateShell, solid::UpdateSolid,
|
||||||
};
|
};
|
||||||
|
|
|
@ -0,0 +1,17 @@
|
||||||
|
use crate::{
|
||||||
|
objects::{Shell, Solid},
|
||||||
|
storage::Handle,
|
||||||
|
};
|
||||||
|
|
||||||
|
/// Update a [`Solid`]
|
||||||
|
pub trait UpdateSolid {
|
||||||
|
/// Add a shell to the solid
|
||||||
|
fn add_shell(&self, shell: Handle<Shell>) -> Solid;
|
||||||
|
}
|
||||||
|
|
||||||
|
impl UpdateSolid for Solid {
|
||||||
|
fn add_shell(&self, shell: Handle<Shell>) -> Solid {
|
||||||
|
let shells = self.shells().cloned().chain([shell]);
|
||||||
|
Solid::new(shells)
|
||||||
|
}
|
||||||
|
}
|
|
@ -235,6 +235,7 @@ mod tests {
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn shell_not_watertight() -> anyhow::Result<()> {
|
fn shell_not_watertight() -> anyhow::Result<()> {
|
||||||
let mut services = Services::new();
|
let mut services = Services::new();
|
||||||
|
|
Loading…
Reference in New Issue