forked from StudioInfinity/dyna3
Compare commits
2 commits
46ffd6c285
...
adc60ac5c1
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
adc60ac5c1 | ||
|
|
27edbfb010 |
2 changed files with 52 additions and 28 deletions
|
|
@ -127,7 +127,7 @@ pub trait Element: Serial + ProblemPoser + DisplayItem {
|
|||
}
|
||||
|
||||
impl Debug for dyn Element {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), fmt::Error> {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
|
||||
self.id().fmt(f)
|
||||
}
|
||||
}
|
||||
|
|
@ -305,13 +305,14 @@ impl Element for Point {
|
|||
point(0.0, 0.0, 0.0),
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
fn default_regulators(self: Rc<Self>) -> Vec<Rc<dyn Regulator>> {
|
||||
all::<Axis>()
|
||||
.map(|axis| {
|
||||
Rc::new(PointCoordinateRegulator::new(self.clone(), axis))
|
||||
as Rc::<dyn Regulator>
|
||||
})
|
||||
.map(
|
||||
|axis| Rc::new(
|
||||
PointCoordinateRegulator::new(self.clone(), axis)
|
||||
) as Rc::<dyn Regulator>
|
||||
)
|
||||
.collect()
|
||||
}
|
||||
|
||||
|
|
@ -511,10 +512,18 @@ impl ProblemPoser for HalfCurvatureRegulator {
|
|||
}
|
||||
|
||||
#[derive(Clone, Copy, Sequence)]
|
||||
pub enum Axis {X = 0, Y = 1, Z = 2}
|
||||
pub enum Axis { X = 0, Y = 1, Z = 2 }
|
||||
|
||||
impl Axis {
|
||||
pub const NAME: [&str; Axis::CARDINALITY] = ["X", "Y", "Z"];
|
||||
fn name(&self) -> &'static str {
|
||||
match self { Axis::X => "X", Axis::Y => "Y", Axis::Z => "Z" }
|
||||
}
|
||||
}
|
||||
|
||||
impl fmt::Display for Axis {
|
||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||
f.write_str(self.name())
|
||||
}
|
||||
}
|
||||
|
||||
pub struct PointCoordinateRegulator {
|
||||
|
|
@ -530,19 +539,32 @@ impl PointCoordinateRegulator {
|
|||
let measurement = subject.representation().map(
|
||||
move |rep| rep[axis as usize]
|
||||
);
|
||||
|
||||
let set_point = create_signal(SpecifiedValue::from_empty_spec());
|
||||
Self { subject, axis, measurement, set_point, serial: Self::next_serial() }
|
||||
let serial = Self::next_serial();
|
||||
|
||||
Self { subject, axis, measurement, set_point, serial }
|
||||
}
|
||||
}
|
||||
|
||||
impl Serial for PointCoordinateRegulator {
|
||||
fn serial(&self) -> u64 { self.serial }
|
||||
fn serial(&self) -> u64 {
|
||||
self.serial
|
||||
}
|
||||
}
|
||||
|
||||
impl Regulator for PointCoordinateRegulator {
|
||||
fn subjects(&self) -> Vec<Rc<dyn Element>> { vec![self.subject.clone()] }
|
||||
fn measurement(&self) -> ReadSignal<f64> { self.measurement }
|
||||
fn set_point(&self) -> Signal<SpecifiedValue> { self.set_point }
|
||||
fn subjects(&self) -> Vec<Rc<dyn Element>> {
|
||||
vec![self.subject.clone()]
|
||||
}
|
||||
|
||||
fn measurement(&self) -> ReadSignal<f64> {
|
||||
self.measurement
|
||||
}
|
||||
|
||||
fn set_point(&self) -> Signal<SpecifiedValue> {
|
||||
self.set_point
|
||||
}
|
||||
}
|
||||
|
||||
impl ProblemPoser for PointCoordinateRegulator {
|
||||
|
|
@ -550,22 +572,25 @@ impl ProblemPoser for PointCoordinateRegulator {
|
|||
self.set_point.with_untracked(|set_pt| {
|
||||
if let Some(val) = set_pt.value {
|
||||
let col = self.subject.column_index().expect(
|
||||
"Subject must be indexed before point-coordinate regulator poses.");
|
||||
"Subject should be indexed before point coordinate regulator writes problem data"
|
||||
);
|
||||
problem.frozen.push(self.axis as usize, col, val);
|
||||
// Check if all three spatial coordinates have been frozen, and if so,
|
||||
// freeze the norm component as well
|
||||
let mut coords = [0.0; Axis::CARDINALITY];
|
||||
let mut nset: usize = 0;
|
||||
for &MatrixEntry {index, value} in &(problem.frozen) {
|
||||
if index.1 == col && index.0 < Axis::CARDINALITY {
|
||||
nset += 1;
|
||||
coords[index.0] = value
|
||||
|
||||
// if all three of the subject's spatial coordinates have been
|
||||
// frozen, then freeze its norm component too
|
||||
let mut coords_frozen = [0.0; Axis::CARDINALITY];
|
||||
let mut n_set: usize = 0;
|
||||
for &MatrixEntry { index, value } in &(problem.frozen) {
|
||||
let (row_frozen, col_frozen) = index;
|
||||
if col_frozen == col && row_frozen < Axis::CARDINALITY {
|
||||
n_set += 1;
|
||||
coords_frozen[row_frozen] = value
|
||||
}
|
||||
}
|
||||
if nset == Axis::CARDINALITY {
|
||||
let [x, y, z] = coords;
|
||||
problem.frozen.push(
|
||||
Point::NORM_COMPONENT, col, point(x,y,z)[Point::NORM_COMPONENT]);
|
||||
if n_set == Axis::CARDINALITY {
|
||||
let [x, y, z] = coords_frozen;
|
||||
let norm = point(x, y, z)[Point::NORM_COMPONENT];
|
||||
problem.frozen.push(Point::NORM_COMPONENT, col, norm);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
|
|
|||
|
|
@ -6,7 +6,6 @@ use web_sys::{KeyboardEvent, MouseEvent, wasm_bindgen::JsCast};
|
|||
use crate::{
|
||||
AppState,
|
||||
assembly::{
|
||||
Axis,
|
||||
Element,
|
||||
HalfCurvatureRegulator,
|
||||
InversiveDistanceRegulator,
|
||||
|
|
@ -123,7 +122,7 @@ impl OutlineItem for HalfCurvatureRegulator {
|
|||
|
||||
impl OutlineItem for PointCoordinateRegulator {
|
||||
fn outline_item(self: Rc<Self>, _element: &Rc<dyn Element>) -> View {
|
||||
let name = format!("{} coordinate", Axis::NAME[self.axis as usize]);
|
||||
let name = format!("{} coordinate", self.axis);
|
||||
view! {
|
||||
li(class = "regulator") {
|
||||
div(class = "regulator-label") // for spacing
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue