forked from 1b-agent/opencadstudio-upstream
feat(model): align polysolid workflow
This commit is contained in:
1 parent
6d6defa0ad
commit
1dd6b115cf
12 files changed
+857
-250
No files matched your search
@@ -1636,11 +1636,24 @@ impl OpenCADStudio {
|
||||
entity,
|
||||
solid,
|
||||
history,
|
||||
erase_source,
|
||||
} => {
|
||||
let label = self.history_label_from_active_cmd(i, "SOLID");
|
||||
let pending = self.begin_undo(i, label, 1, true);
|
||||
let erase_source = erase_source.filter(|handle| {
|
||||
self.tabs[i].scene.document.header.delete_objects
|
||||
&& !self.tabs[i].scene.is_layer_locked(*handle)
|
||||
});
|
||||
let pending = self.begin_undo(
|
||||
i,
|
||||
label,
|
||||
1 + usize::from(erase_source.is_some()),
|
||||
true,
|
||||
);
|
||||
let handle = self.add_solid_model(entity, *solid, history);
|
||||
if !handle.is_null() {
|
||||
if let Some(source) = erase_source {
|
||||
self.tabs[i].scene.erase_entities(&[source]);
|
||||
}
|
||||
self.tabs[i].dirty = true;
|
||||
if let Some(pd) = pending {
|
||||
self.commit_undo_delta(i, pd);
|
||||
|
||||
+18
-22
@@ -1038,32 +1038,28 @@ impl OpenCADStudio {
|
||||
return Some(self.solid_convtosurface());
|
||||
}
|
||||
|
||||
// POLYSOLID <width> <height> — extrude a selected polyline into a
|
||||
// wall-like solid.
|
||||
"POLYSOLID" => {
|
||||
use crate::command::SelectThenTwoValueCommand;
|
||||
let has_sel = !self.tabs[i].scene.selected_entities().is_empty();
|
||||
let c = SelectThenTwoValueCommand::new(
|
||||
"POLYSOLID",
|
||||
"POLYSOLID wall width:",
|
||||
"POLYSOLID wall height:",
|
||||
has_sel,
|
||||
);
|
||||
use crate::modules::model::polysolid_cmd::PolysolidCommand;
|
||||
let preselected = self.tabs[i]
|
||||
.scene
|
||||
.selected_entities()
|
||||
.into_iter()
|
||||
.find(|(_, entity)| {
|
||||
matches!(
|
||||
entity,
|
||||
acadrust::EntityType::Line(_)
|
||||
| acadrust::EntityType::Arc(_)
|
||||
| acadrust::EntityType::Circle(_)
|
||||
| acadrust::EntityType::Ellipse(_)
|
||||
| acadrust::EntityType::LwPolyline(_)
|
||||
| acadrust::EntityType::Spline(_)
|
||||
)
|
||||
})
|
||||
.map(|(handle, entity)| (handle, entity.clone()));
|
||||
let c = PolysolidCommand::new(preselected);
|
||||
self.command_line.push_info(&c.prompt());
|
||||
self.tabs[i].active_cmd = Some(Box::new(c));
|
||||
}
|
||||
cmd if cmd.starts_with("POLYSOLID ") => {
|
||||
let nums: Vec<f64> = cmd
|
||||
.split_whitespace()
|
||||
.skip(1)
|
||||
.filter_map(|s| s.parse::<f64>().ok())
|
||||
.collect();
|
||||
if nums.len() >= 2 && nums[0] > 0.0 && nums[1] > 0.0 {
|
||||
return Some(self.solid_polysolid(nums[0], nums[1]));
|
||||
}
|
||||
self.command_line
|
||||
.push_info(crate::t!("Usage: POLYSOLID <width> <height> (select a polyline first)").as_ref());
|
||||
}
|
||||
|
||||
// SPLINEFIT — fit a smooth spline through the selected polyline's points.
|
||||
"SPLINEFIT" | "FITSPLINE" => {
|
||||
|
||||
@@ -468,55 +468,6 @@ impl super::OpenCADStudio {
|
||||
Task::none()
|
||||
}
|
||||
|
||||
/// POLYSOLID — build a wall solid around an exact polyline offset.
|
||||
pub(super) fn solid_polysolid(&mut self, width: f64, height: f64) -> Task<Message> {
|
||||
let i = self.active_tab;
|
||||
let found: Option<(Handle, EntityType)> = self.tabs[i]
|
||||
.scene
|
||||
.selected_entities()
|
||||
.iter()
|
||||
.filter(|(h, _)| !self.tabs[i].scene.is_layer_locked(*h))
|
||||
.find_map(|(h, e)| match e {
|
||||
EntityType::LwPolyline(_) => Some((*h, (*e).clone())),
|
||||
_ => None,
|
||||
});
|
||||
let Some((handle, entity)) = found else {
|
||||
self.command_line
|
||||
.push_error(crate::t!("POLYSOLID: select a polyline first.").as_ref());
|
||||
return Task::none();
|
||||
};
|
||||
let Some(result) = crate::scene::model::sweep_model::polysolid(&entity, width, height)
|
||||
else {
|
||||
self.command_line
|
||||
.push_error(crate::t!("POLYSOLID: the kernel could not offset the polyline.").as_ref());
|
||||
return Task::none();
|
||||
};
|
||||
if crate::scene::convert::acis_export::solid_to_sat(&result).is_none() {
|
||||
self.command_line
|
||||
.push_error(crate::t!("POLYSOLID: the result could not be encoded as ACIS.").as_ref());
|
||||
return Task::none();
|
||||
}
|
||||
self.push_undo_snapshot(i, "POLYSOLID");
|
||||
self.tabs[i].scene.erase_entities(&[handle]);
|
||||
let mut s3d = Solid3D::new();
|
||||
s3d.wires = solid_model::edge_wires(&result);
|
||||
let history = solid_history::brep_op(&result);
|
||||
let h = self.add_solid_model(EntityType::Solid3D(s3d), result, history);
|
||||
self.tabs[i].scene.deselect_all();
|
||||
if !h.is_null() {
|
||||
self.tabs[i].scene.select_entity(h, false);
|
||||
}
|
||||
if !h.is_null() {
|
||||
self.tabs[i].dirty = true;
|
||||
self.refresh_properties();
|
||||
self.command_line.push_output(
|
||||
crate::tf!("POLYSOLID: created a wall solid (width {width}, height {height}).")
|
||||
.as_ref(),
|
||||
);
|
||||
}
|
||||
Task::none()
|
||||
}
|
||||
|
||||
/// 3DMIRROR — add a mirrored copy of the one selected solid across the plane
|
||||
/// perpendicular to the X/Y/Z axis (0/1/2) through its centre, keeping the
|
||||
/// original. A reflection loses handedness, so the kernel reverses every
|
||||
|
||||
Reference in new issue
Block a user