fix: derive dimension text rotation from axis geometry
acadrust's DXF reader does not parse group code 53 (text rotation), so DimensionBase.text_rotation is always zero for DXF-loaded files. Fall back to the natural axis-aligned rotation computed from geometry: Linear dimensions use d.rotation (radians), Aligned dimensions use atan2 of the second-first vector. Normalize to (-π/2, π/2] so text never appears upside-down. Explicit non-zero overrides stored by the DWG reader are preserved. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
19bb846c50
commit
db653c5a07
1 changed files with 31 additions and 1 deletions
|
|
@ -799,14 +799,44 @@ fn dimension_text_entity(dim: &Dimension) -> Option<Text> {
|
||||||
let value = dimension_text_value(dim)?;
|
let value = dimension_text_value(dim)?;
|
||||||
let pos = dimension_text_position(dim);
|
let pos = dimension_text_position(dim);
|
||||||
let base = dim.base();
|
let base = dim.base();
|
||||||
|
// acadrust's DXF reader never parses group code 53 (text rotation), so
|
||||||
|
// base.text_rotation is always 0 for DXF files. Fall back to the natural
|
||||||
|
// axis-aligned rotation derived from geometry; only use the stored value
|
||||||
|
// when it represents a genuine user override (non-zero).
|
||||||
|
let rotation = if base.text_rotation.abs() > 1e-9 {
|
||||||
|
base.text_rotation
|
||||||
|
} else {
|
||||||
|
dimension_text_natural_rotation(dim)
|
||||||
|
};
|
||||||
let mut text = Text::with_value(value, Vector3::new(pos.x as f64, pos.y as f64, pos.z as f64))
|
let mut text = Text::with_value(value, Vector3::new(pos.x as f64, pos.y as f64, pos.z as f64))
|
||||||
.with_height(dimension_text_height(dim))
|
.with_height(dimension_text_height(dim))
|
||||||
.with_rotation(base.text_rotation);
|
.with_rotation(rotation);
|
||||||
text.style = base.style_name.clone();
|
text.style = base.style_name.clone();
|
||||||
text.common = base.common.clone();
|
text.common = base.common.clone();
|
||||||
Some(text)
|
Some(text)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn dimension_text_natural_rotation(dim: &Dimension) -> f64 {
|
||||||
|
let angle = match dim {
|
||||||
|
Dimension::Linear(d) => d.rotation,
|
||||||
|
Dimension::Aligned(d) => {
|
||||||
|
let dx = d.second_point.x - d.first_point.x;
|
||||||
|
let dy = d.second_point.y - d.first_point.y;
|
||||||
|
dy.atan2(dx)
|
||||||
|
}
|
||||||
|
_ => 0.0,
|
||||||
|
};
|
||||||
|
// Clamp to (-π/2, π/2] so text never appears upside-down.
|
||||||
|
let pi = std::f64::consts::PI;
|
||||||
|
if angle > pi / 2.0 {
|
||||||
|
angle - pi
|
||||||
|
} else if angle <= -pi / 2.0 {
|
||||||
|
angle + pi
|
||||||
|
} else {
|
||||||
|
angle
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn dimension_text_value(dim: &Dimension) -> Option<String> {
|
fn dimension_text_value(dim: &Dimension) -> Option<String> {
|
||||||
let base = dim.base();
|
let base = dim.base();
|
||||||
if let Some(user_text) = &base.user_text {
|
if let Some(user_text) = &base.user_text {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue