forked from 1b-agent/opencadstudio-upstream
Add versioned host settings API for plugins
This commit is contained in:
1 parent
93afe91afc
commit
ec2271fc9c
13 files changed
+218
-17
No files matched your search
@@ -739,6 +739,16 @@ impl OpenCADStudio {
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
#[test]
|
||||
fn clayer_command_sets_layer_used_by_new_geometry() {
|
||||
let mut app = super::OpenCADStudio::new_for_test();
|
||||
app.automation_op(r#"{"op":"new"}"#);
|
||||
app.automation_op(r#"{"op":"run","cmd":"LAYER NEW Annotations"}"#);
|
||||
app.automation_op(r#"{"op":"run","cmd":"CLAYER Annotations"}"#);
|
||||
app.automation_op(r#"{"op":"run","cmd":"LINE 0,0 10,0"}"#);
|
||||
let lines = app.automation_op(r#"{"op":"query","type":"Line"}"#);
|
||||
assert_eq!(lines["entities"][0]["layer"], "Annotations");
|
||||
}
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
#[test]
|
||||
fn built_in_edits_advance_plugin_document_fingerprint_once() {
|
||||
|
||||
@@ -2649,10 +2649,7 @@ impl OpenCADStudio {
|
||||
self.command_line
|
||||
.push_output(crate::tf!("CLAYER = \"{cur}\"").as_ref());
|
||||
} else {
|
||||
if self.tabs[i].scene.document.layers.contains(name_arg) {
|
||||
self.tabs[i].scene.document.header.current_layer_name =
|
||||
name_arg.to_string();
|
||||
self.tabs[i].dirty = true;
|
||||
if self.set_current_layer_name(i, name_arg).is_ok() {
|
||||
self.command_line
|
||||
.push_output(crate::tf!("CLAYER set to \"{name_arg}\"").as_ref());
|
||||
} else {
|
||||
|
||||
@@ -2,6 +2,27 @@ use super::OpenCADStudio;
|
||||
use crate::ui;
|
||||
|
||||
impl OpenCADStudio {
|
||||
/// Apply the current layer to the document header and all per-tab/UI
|
||||
/// creation state. Both built-in commands and plugin settings use this.
|
||||
pub(super) fn set_current_layer_name(&mut self, tab: usize, layer: &str) -> Result<(), String> {
|
||||
let handle = self.tabs[tab]
|
||||
.scene
|
||||
.document
|
||||
.layers
|
||||
.get(layer)
|
||||
.map(|entry| entry.handle)
|
||||
.ok_or_else(|| format!("layer {layer:?} does not exist"))?;
|
||||
self.tabs[tab].scene.document.header.current_layer_name = layer.to_owned();
|
||||
self.tabs[tab].scene.document.header.current_layer_handle = handle;
|
||||
self.tabs[tab].active_layer = layer.to_owned();
|
||||
self.tabs[tab].layers.current_layer = layer.to_owned();
|
||||
self.tabs[tab].dirty = true;
|
||||
if tab == self.active_tab {
|
||||
self.ribbon.active_layer = layer.to_owned();
|
||||
self.refresh_layer_panel();
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
pub(super) fn load_layer_state_editor(&mut self, selected: Option<String>) {
|
||||
let i = self.active_tab;
|
||||
if let Some(name) = selected {
|
||||
|
||||
+75
-1
@@ -4,7 +4,7 @@ use std::any::Any;
|
||||
|
||||
use acadrust::tables::AppId;
|
||||
use acadrust::xdata::ExtendedDataRecord;
|
||||
use ocs_plugin_api::host::{CadDocument, EntityType, Handle, HostApi};
|
||||
use ocs_plugin_api::host::{CadDocument, EntityType, Handle, HostApi, HostSettingValue};
|
||||
use ocs_plugin_api::shm::{DocumentSnapshotStore, DocumentViewData};
|
||||
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
@@ -250,6 +250,41 @@ impl<'a> HostSession<'a> {
|
||||
self.app.tabs[self.tab].dirty = true;
|
||||
}
|
||||
|
||||
pub fn system_variable(&self, name: &str) -> Option<HostSettingValue> {
|
||||
match name.to_ascii_uppercase().as_str() {
|
||||
"CLAYER" => Some(HostSettingValue::Text(
|
||||
self.document().header.current_layer_name.clone(),
|
||||
)),
|
||||
"SNAPANG" => Some(HostSettingValue::Number(self.app.snap_angle_deg as f64)),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_system_variable(
|
||||
&mut self,
|
||||
name: &str,
|
||||
value: HostSettingValue,
|
||||
) -> Result<HostSettingValue, String> {
|
||||
match (name.to_ascii_uppercase().as_str(), value) {
|
||||
("CLAYER", HostSettingValue::Text(layer)) => {
|
||||
self.app.set_current_layer_name(self.tab, &layer)?;
|
||||
Ok(HostSettingValue::Text(layer))
|
||||
}
|
||||
("SNAPANG", HostSettingValue::Number(angle)) if (angle as f32).is_finite() => {
|
||||
self.app.snap_angle_deg = (angle as f32).rem_euclid(360.0);
|
||||
Ok(HostSettingValue::Number(self.app.snap_angle_deg as f64))
|
||||
}
|
||||
("SNAPANG", HostSettingValue::Number(_)) => {
|
||||
Err("SNAPANG: finite number required".to_owned())
|
||||
}
|
||||
("CLAYER", _) | ("SNAPANG", _) => Err(format!(
|
||||
"{}: wrong value type",
|
||||
name.to_ascii_uppercase()
|
||||
)),
|
||||
_ => Err(format!("unsupported system variable {name:?}")),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn push_info(&mut self, msg: &str) {
|
||||
self.app.command_line.push_info(msg);
|
||||
}
|
||||
@@ -356,6 +391,16 @@ impl HostApi for HostSession<'_> {
|
||||
fn document_path(&self, tab_id: u64) -> Option<std::path::PathBuf> {
|
||||
self.document_path(tab_id)
|
||||
}
|
||||
fn system_variable(&self, name: &str) -> Option<HostSettingValue> {
|
||||
self.system_variable(name)
|
||||
}
|
||||
fn set_system_variable(
|
||||
&mut self,
|
||||
name: &str,
|
||||
value: HostSettingValue,
|
||||
) -> Result<HostSettingValue, String> {
|
||||
self.set_system_variable(name, value)
|
||||
}
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
fn document_view_v4(&mut self, tab_id: u64) -> Option<ocs_plugin_api::shm::DocumentViewInfo> {
|
||||
self.document_view_v4(tab_id)
|
||||
@@ -514,6 +559,35 @@ mod tests {
|
||||
use acadrust::xdata::XDataValue;
|
||||
use ocs_plugin_api::host::DocumentReader;
|
||||
|
||||
#[test]
|
||||
fn system_variables_change_without_command_reentry() {
|
||||
let mut app = OpenCADStudio::new_for_test();
|
||||
app.tabs[0].is_start = false;
|
||||
let mut host = HostSession::new(&mut app, 0);
|
||||
assert_eq!(host.system_variable("clayer"), Some(HostSettingValue::Text("0".into())));
|
||||
assert_eq!(host.system_variable("SNAPANG"), Some(HostSettingValue::Number(0.0)));
|
||||
assert!(host.set_system_variable("CLAYER", HostSettingValue::Text("Missing".into())).is_err());
|
||||
assert_eq!(host.system_variable("CLAYER"), Some(HostSettingValue::Text("0".into())));
|
||||
|
||||
let mut point = Point::new();
|
||||
point.common.layer = "Annotations".into();
|
||||
host.add_entity(EntityType::Point(point));
|
||||
assert_eq!(host.set_system_variable("clayer", HostSettingValue::Text("Annotations".into())),
|
||||
Ok(HostSettingValue::Text("Annotations".into())));
|
||||
assert_eq!(host.system_variable("CLAYER"), Some(HostSettingValue::Text("Annotations".into())));
|
||||
assert_eq!(host.app.tabs[0].active_layer, "Annotations");
|
||||
assert_eq!(host.app.tabs[0].layers.current_layer, "Annotations");
|
||||
assert_eq!(host.app.ribbon.active_layer, "Annotations");
|
||||
assert!(host.app.tabs[0].dirty);
|
||||
|
||||
assert_eq!(host.set_system_variable("snapang", HostSettingValue::Number(450.0)),
|
||||
Ok(HostSettingValue::Number(90.0)));
|
||||
assert_eq!(host.system_variable("SNAPANG"), Some(HostSettingValue::Number(90.0)));
|
||||
assert!(host.set_system_variable("SNAPANG", HostSettingValue::Number(f64::INFINITY)).is_err());
|
||||
assert!(host.set_system_variable("SNAPANG", HostSettingValue::Number(f64::MAX)).is_err());
|
||||
assert_eq!(host.system_variable("SNAPANG"), Some(HostSettingValue::Number(90.0)));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn xdata_record_round_trips_and_registers_appid() {
|
||||
let mut app = OpenCADStudio::new_for_test();
|
||||
|
||||
Reference in new issue
Block a user