diff --git a/src/app/properties.rs b/src/app/properties.rs index 1bfa1bc9e..f7a40df88 100644 --- a/src/app/properties.rs +++ b/src/app/properties.rs @@ -93,6 +93,11 @@ impl OpenCADStudio { crate::entities::common::UnitContext::from_header(h), ); } + { + // Which text styles fix their own height — the height rows read it + // to decide whether they are editable. + crate::entities::common::set_fixed_text_heights(&self.tabs[i].scene.document); + } let layer_names: Vec = self.tabs[i] .scene diff --git a/src/entities/attribute.rs b/src/entities/attribute.rs index 0d9d2aca6..b0910983d 100644 --- a/src/entities/attribute.rs +++ b/src/entities/attribute.rs @@ -468,7 +468,13 @@ impl PropertyEditable for AttributeDefinition { .collect(), }, }, - edit(t!("Height").as_ref(), "att_h", self.height), + // Fixed by the style when the style fixes its height. + crate::entities::common::num_prop( + t!("Height").as_ref(), + "att_h", + self.height, + crate::entities::common::style_fixed_height(&self.text_style).is_none(), + ), edit_angle(t!("Rotation").as_ref(), "att_rot", self.rotation.to_degrees()), edit(t!("Width factor").as_ref(), "att_wf", self.width_factor), edit_angle(t!("Obliquing").as_ref(), "att_ob", self.oblique_angle.to_degrees()), @@ -739,7 +745,13 @@ impl PropertyEditable for AttributeEntity { "atte_annotative", bool_yn(self.flags.annotative), ), - edit(t!("Height").as_ref(), "atte_h", self.height), + // Fixed by the style when the style fixes its height. + crate::entities::common::num_prop( + t!("Height").as_ref(), + "atte_h", + self.height, + crate::entities::common::style_fixed_height(&self.text_style).is_none(), + ), edit_angle(t!("Rotation").as_ref(), "atte_rot", self.rotation.to_degrees()), edit(t!("Width factor").as_ref(), "atte_wf", self.width_factor), edit_angle(t!("Obliquing").as_ref(), "atte_ob", self.oblique_angle.to_degrees()), diff --git a/src/entities/common.rs b/src/entities/common.rs index 6d1315ceb..8a18702c5 100644 --- a/src/entities/common.rs +++ b/src/entities/common.rs @@ -53,6 +53,38 @@ thread_local! { }) }; } +thread_local! { + /// Text styles that fix their own height, by lowercased name. + /// + /// A style with a non-zero height fixes the size of everything drawn in it + /// — the CAD that writes the file skips the height prompt for such a style, + /// and the properties palette shows the height without letting it be + /// changed. The panel builders are handed an entity, not the document it + /// came from, so the lookup rides here beside the unit context, seeded from + /// the same place. + static FIXED_TEXT_HEIGHTS: std::cell::RefCell> = + std::cell::RefCell::new(rustc_hash::FxHashMap::default()); +} + +/// Record which text styles fix their height, from the drawing's style table. +pub fn set_fixed_text_heights(document: &acadrust::CadDocument) { + FIXED_TEXT_HEIGHTS.with(|cell| { + let mut map = cell.borrow_mut(); + map.clear(); + for style in document.text_styles.iter() { + if style.height > 0.0 { + map.insert(style.name.to_ascii_lowercase(), style.height); + } + } + }); +} + +/// The height `style` fixes, or `None` when it leaves the height to the entity. +pub fn style_fixed_height(style: &str) -> Option { + let key = style.trim().to_ascii_lowercase(); + FIXED_TEXT_HEIGHTS.with(|cell| cell.borrow().get(&key).copied()) +} + /// Set the per-thread unit context. Properties helpers consult it when /// they format f64 values into display strings. pub fn set_unit_context(ctx: UnitContext) { diff --git a/src/entities/mtext.rs b/src/entities/mtext.rs index 74b2dfcbb..0abf0adef 100644 --- a/src/entities/mtext.rs +++ b/src/entities/mtext.rs @@ -311,7 +311,13 @@ fn properties(t: &MText, text_style_names: &[String]) -> Vec { .collect(), }, }, - edit(t!("Text height").as_ref(), "height", t.height), + // Fixed by the style when the style says so — see Text. + crate::entities::common::num_prop( + t!("Text height").as_ref(), + "height", + t.height, + crate::entities::common::style_fixed_height(&t.style).is_none(), + ), edit_angle(t!("Rotation").as_ref(), "rotation", t.rotation.to_degrees()), edit(t!("Line space factor").as_ref(), "line_spacing", t.line_spacing_factor), edit(t!("Line space distance").as_ref(), "line_space_distance", line_space_distance), diff --git a/src/entities/text.rs b/src/entities/text.rs index 7b47673ea..e8eed635e 100644 --- a/src/entities/text.rs +++ b/src/entities/text.rs @@ -325,7 +325,14 @@ fn properties(t: &Text, text_style_names: &[String]) -> Vec { .collect(), }, }, - edit(t!("Height").as_ref(), "height", t.height), + // A style that fixes its height fixes this text's too, so the + // value shows but cannot be changed here. + crate::entities::common::num_prop( + t!("Height").as_ref(), + "height", + t.height, + crate::entities::common::style_fixed_height(&t.style).is_none(), + ), edit_angle(t!("Rotation").as_ref(), "rotation", t.rotation.to_degrees()), edit(t!("Width factor").as_ref(), "width_factor", t.width_factor), edit_angle(t!("Obliquing").as_ref(), "oblique_angle", t.oblique_angle.to_degrees()),