forked from 1b-agent/opencadstudio-upstream
Merge PR #1586 from ramox81/codex/solid-history-graph: no history on edge fillet/chamfer of plain solids; undo evaluation graph
The PR pinned codec and kernel to its fork through [patch]; codec #76 and kernel #71 are merged upstream and main already points at them, so the patch sections are dropped.
This commit is contained in:
commit
34cc5cf435
3 files changed
+60
-36
No files matched your search
+19
-30
@@ -655,16 +655,9 @@ impl super::OpenCADStudio {
|
|||||||
};
|
};
|
||||||
|
|
||||||
self.push_undo_snapshot(i, "FILLETEDGE");
|
self.push_undo_snapshot(i, "FILLETEDGE");
|
||||||
if self.tabs[i].scene.document.solid_history_graph(handle).is_none()
|
// A solid without history stays without one, as in the reference.
|
||||||
&& !self.tabs[i]
|
let has_history = self.tabs[i].scene.document.solid_history_graph(handle).is_some();
|
||||||
.scene
|
if has_history && !self.tabs[i].scene.append_solid_history(
|
||||||
.create_solid_history(handle, solid_history::brep_op(source))
|
|
||||||
{
|
|
||||||
self.command_line
|
|
||||||
.push_error(crate::t!("The edge body history could not be created.").as_ref());
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if !self.tabs[i].scene.append_solid_history(
|
|
||||||
handle,
|
handle,
|
||||||
solid_history::fillet_op(history_edges, radius),
|
solid_history::fillet_op(history_edges, radius),
|
||||||
) {
|
) {
|
||||||
@@ -672,11 +665,13 @@ impl super::OpenCADStudio {
|
|||||||
.push_error(crate::t!("The fillet history could not be recorded.").as_ref());
|
.push_error(crate::t!("The fillet history could not be recorded.").as_ref());
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
let _ = self.tabs[i].scene.apply_solid_history_choice(
|
if has_history {
|
||||||
handle,
|
let _ = self.tabs[i].scene.apply_solid_history_choice(
|
||||||
solid_history::PROP_HISTORY,
|
handle,
|
||||||
"Record",
|
solid_history::PROP_HISTORY,
|
||||||
);
|
"Record",
|
||||||
|
);
|
||||||
|
}
|
||||||
let Some(entity) = self.tabs[i].scene.document.get_entity(handle).cloned() else {
|
let Some(entity) = self.tabs[i].scene.document.get_entity(handle).cloned() else {
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
@@ -743,16 +738,8 @@ impl super::OpenCADStudio {
|
|||||||
};
|
};
|
||||||
|
|
||||||
self.push_undo_snapshot(i, "CHAMFEREDGE");
|
self.push_undo_snapshot(i, "CHAMFEREDGE");
|
||||||
if self.tabs[i].scene.document.solid_history_graph(handle).is_none()
|
let has_history = self.tabs[i].scene.document.solid_history_graph(handle).is_some();
|
||||||
&& !self.tabs[i]
|
if has_history && !self.tabs[i].scene.append_solid_history(
|
||||||
.scene
|
|
||||||
.create_solid_history(handle, solid_history::brep_op(source))
|
|
||||||
{
|
|
||||||
self.command_line
|
|
||||||
.push_error(crate::t!("The edge body history could not be created.").as_ref());
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if !self.tabs[i].scene.append_solid_history(
|
|
||||||
handle,
|
handle,
|
||||||
solid_history::chamfer_op(
|
solid_history::chamfer_op(
|
||||||
history_edges,
|
history_edges,
|
||||||
@@ -765,11 +752,13 @@ impl super::OpenCADStudio {
|
|||||||
.push_error(crate::t!("The chamfer history could not be recorded.").as_ref());
|
.push_error(crate::t!("The chamfer history could not be recorded.").as_ref());
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
let _ = self.tabs[i].scene.apply_solid_history_choice(
|
if has_history {
|
||||||
handle,
|
let _ = self.tabs[i].scene.apply_solid_history_choice(
|
||||||
solid_history::PROP_HISTORY,
|
handle,
|
||||||
"Record",
|
solid_history::PROP_HISTORY,
|
||||||
);
|
"Record",
|
||||||
|
);
|
||||||
|
}
|
||||||
let Some(entity) = self.tabs[i].scene.document.get_entity(handle).cloned() else {
|
let Some(entity) = self.tabs[i].scene.document.get_entity(handle).cloned() else {
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -60,7 +60,7 @@ pub fn sweep_record(profile: &EntityType, path: &EntityType, options: SweepOptio
|
|||||||
};
|
};
|
||||||
let mut base = SolidHistoryNodeBase::new(1);
|
let mut base = SolidHistoryNodeBase::new(1);
|
||||||
base.transform = glam::DMat4::IDENTITY.to_cols_array();
|
base.transform = glam::DMat4::IDENTITY.to_cols_array();
|
||||||
Some(SolidHistorySweep {
|
let record = SolidHistorySweep {
|
||||||
base,
|
base,
|
||||||
operation_major: 1,
|
operation_major: 1,
|
||||||
sweep_entity: Some(sweep_entity),
|
sweep_entity: Some(sweep_entity),
|
||||||
@@ -74,7 +74,40 @@ pub fn sweep_record(profile: &EntityType, path: &EntityType, options: SweepOptio
|
|||||||
path_entity_transform: glam::DMat4::IDENTITY.to_cols_array(),
|
path_entity_transform: glam::DMat4::IDENTITY.to_cols_array(),
|
||||||
reference_point: Vector3::new(base_point[0], base_point[1], base_point[2]),
|
reference_point: Vector3::new(base_point[0], base_point[1], base_point[2]),
|
||||||
..SolidHistorySweep::default()
|
..SolidHistorySweep::default()
|
||||||
})
|
};
|
||||||
|
placed_sweep_record(profile, record)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// The record the reference reads: the profile stored already placed at the
|
||||||
|
/// path start (base point, alignment and profile rotation applied) with flag
|
||||||
|
/// 295 set, and no reference point.
|
||||||
|
fn placed_sweep_record(profile: &EntityType, mut record: SolidHistorySweep) -> Option<SolidHistorySweep> {
|
||||||
|
let (placed, _) = kernel::acis::sweep_history_placements(&record).ok()?;
|
||||||
|
let embedded_to_world = glam::DMat4::from_cols(
|
||||||
|
glam::DVec4::new(placed.x_axis[0], placed.x_axis[1], placed.x_axis[2], 0.0),
|
||||||
|
glam::DVec4::new(placed.y_axis[0], placed.y_axis[1], placed.y_axis[2], 0.0),
|
||||||
|
glam::DVec4::new(placed.z_axis[0], placed.z_axis[1], placed.z_axis[2], 0.0),
|
||||||
|
glam::DVec4::new(placed.origin[0], placed.origin[1], placed.origin[2], 1.0),
|
||||||
|
);
|
||||||
|
// Source world geometry -> placed world geometry.
|
||||||
|
let map = embedded_to_world * glam::DMat4::from_cols_array(&record.sweep_entity_transform).inverse();
|
||||||
|
let m = map.to_cols_array_2d();
|
||||||
|
let transform = codec::types::Transform::from_matrix(codec::types::Matrix4 {
|
||||||
|
m: [
|
||||||
|
[m[0][0], m[1][0], m[2][0], m[3][0]],
|
||||||
|
[m[0][1], m[1][1], m[2][1], m[3][1]],
|
||||||
|
[m[0][2], m[1][2], m[2][2], m[3][2]],
|
||||||
|
[0.0, 0.0, 0.0, 1.0],
|
||||||
|
],
|
||||||
|
});
|
||||||
|
let mut moved = profile.clone();
|
||||||
|
crate::scene::view::dispatch::apply_transform(&mut moved, &crate::command::EntityTransform::Affine(transform));
|
||||||
|
let (sweep_entity, sweep_entity_transform) = embedded_sweep_profile(&moved)?;
|
||||||
|
record.sweep_entity = Some(sweep_entity);
|
||||||
|
record.sweep_entity_transform = sweep_entity_transform;
|
||||||
|
record.flags_294_296 = [false, true, true];
|
||||||
|
record.reference_point = Vector3::new(0.0, 0.0, 0.0);
|
||||||
|
Some(record)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn swept_with_options(profile: &EntityType, path: &EntityType, mode: ExtrudeMode, options: SweepOptions) -> Option<Body> {
|
pub fn swept_with_options(profile: &EntityType, path: &EntityType, mode: ExtrudeMode, options: SweepOptions) -> Option<Body> {
|
||||||
|
|||||||
+6
-4
@@ -841,6 +841,7 @@ impl Scene {
|
|||||||
};
|
};
|
||||||
std::iter::once(graph.root)
|
std::iter::once(graph.root)
|
||||||
.chain(graph.nodes)
|
.chain(graph.nodes)
|
||||||
|
.chain(graph.evaluation_graph)
|
||||||
.filter_map(|object_handle| {
|
.filter_map(|object_handle| {
|
||||||
self.document
|
self.document
|
||||||
.objects
|
.objects
|
||||||
@@ -869,7 +870,7 @@ impl Scene {
|
|||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
self.record_undo_object_before(graph.root, None);
|
self.record_undo_object_before(graph.root, None);
|
||||||
for node in graph.nodes {
|
for node in graph.nodes.into_iter().chain(graph.evaluation_graph) {
|
||||||
self.record_undo_object_before(node, None);
|
self.record_undo_object_before(node, None);
|
||||||
}
|
}
|
||||||
self.sync_solid_reference_point(handle);
|
self.sync_solid_reference_point(handle);
|
||||||
@@ -881,16 +882,17 @@ impl Scene {
|
|||||||
handle: Handle,
|
handle: Handle,
|
||||||
operation: codec::objects::SolidHistoryOperation,
|
operation: codec::objects::SolidHistoryOperation,
|
||||||
) -> bool {
|
) -> bool {
|
||||||
let previous = self
|
let previous: Vec<Handle> = self
|
||||||
.document
|
.document
|
||||||
.solid_history_graph(handle)
|
.solid_history_graph(handle)
|
||||||
.map(|graph| graph.nodes)
|
.map(|graph| graph.nodes.into_iter().chain(graph.evaluation_graph).collect())
|
||||||
.unwrap_or_default();
|
.unwrap_or_default();
|
||||||
self.record_solid_history_before(handle);
|
self.record_solid_history_before(handle);
|
||||||
let Some(graph) = self.document.append_solid_history(handle, operation) else {
|
let Some(graph) = self.document.append_solid_history(handle, operation) else {
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
for node in graph.nodes {
|
// A history saved without an evaluation graph gets one on append.
|
||||||
|
for node in graph.nodes.into_iter().chain(graph.evaluation_graph) {
|
||||||
if !previous.contains(&node) {
|
if !previous.contains(&node) {
|
||||||
self.record_undo_object_before(node, None);
|
self.record_undo_object_before(node, None);
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in new issue
Block a user