forked from 1b-agent/opencadstudio-upstream
fix(hatch): align EllipticArc angle logic with CircularArc
Use reflection (TAU - sa, TAU - ea) for CW arcs and span.abs() for segment count, consistent with the CircularArc pattern in both hatch boundary (mod.rs) and tessellate (tessellate.rs). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
1 parent
4b5f4c7ee8
commit
a3efad9caf
2 files changed
+18
-22
No files matched your search
+8
-12
@@ -2175,13 +2175,14 @@ impl Scene {
|
||||
let ccw = arc.counter_clockwise;
|
||||
let (sa, ea) = if ccw { (sa, ea) } else { (TAU - sa, TAU - ea) };
|
||||
let span = ea - sa;
|
||||
let segs = ((span / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
let segs = ((span.abs() / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
for i in 0..=segs {
|
||||
let t = sa + span * (i as f64 / segs as f64);
|
||||
boundary.push(to_xy(cx + r * t.cos(), cy + r * t.sin()));
|
||||
}
|
||||
}
|
||||
BoundaryEdge::EllipticArc(ell) => {
|
||||
const TAU: f32 = std::f32::consts::TAU;
|
||||
let cx = ell.center.x;
|
||||
let cy = ell.center.y;
|
||||
let maj_x = ell.major_axis_endpoint.x as f32;
|
||||
@@ -2189,17 +2190,12 @@ impl Scene {
|
||||
let r_maj = (maj_x * maj_x + maj_y * maj_y).sqrt();
|
||||
let r_min = r_maj * ell.minor_axis_ratio as f32;
|
||||
let rot = maj_y.atan2(maj_x);
|
||||
let (sa, ea) = if ell.counter_clockwise {
|
||||
(ell.start_angle as f32, ell.end_angle as f32)
|
||||
} else {
|
||||
(ell.end_angle as f32, ell.start_angle as f32)
|
||||
};
|
||||
let mut end = ea;
|
||||
if end < sa {
|
||||
end += std::f32::consts::TAU;
|
||||
}
|
||||
let span = end - sa;
|
||||
let segs = ((span / std::f32::consts::TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
let ccw = ell.counter_clockwise;
|
||||
let sa = ell.start_angle as f32;
|
||||
let ea = ell.end_angle as f32;
|
||||
let (sa, ea) = if ccw { (sa, ea) } else { (TAU - sa, TAU - ea) };
|
||||
let span = ea - sa;
|
||||
let segs = ((span.abs() / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
for i in 0..=segs {
|
||||
let t = sa + span * (i as f32 / segs as f32);
|
||||
let lx = r_maj * t.cos();
|
||||
|
||||
+10
-10
@@ -872,7 +872,7 @@ fn legacy_geometry(entity: &EntityType, world_offset: [f64; 3]) -> Geometry {
|
||||
let ccw = arc.counter_clockwise;
|
||||
let (sa, ea) = if ccw { (sa, ea) } else { (TAU - sa, TAU - ea) };
|
||||
let span = ea - sa;
|
||||
let segs = ((span / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
let segs = ((span.abs() / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
if !pts.is_empty() {
|
||||
pts.push([f32::NAN; 3]);
|
||||
}
|
||||
@@ -899,18 +899,18 @@ fn legacy_geometry(entity: &EntityType, world_offset: [f64; 3]) -> Geometry {
|
||||
let r_min = r_maj * ell.minor_axis_ratio as f32;
|
||||
let rot = (ell.major_axis_endpoint.y as f32)
|
||||
.atan2(ell.major_axis_endpoint.x as f32);
|
||||
let (sa, ea) = if ell.counter_clockwise {
|
||||
(ell.start_angle as f32, ell.end_angle as f32)
|
||||
const TAU: f32 = std::f32::consts::TAU;
|
||||
let ccw = ell.counter_clockwise;
|
||||
let sa = ell.start_angle as f32;
|
||||
let ea = ell.end_angle as f32;
|
||||
let (sa, ea) = if ccw {
|
||||
(sa, ea)
|
||||
} else {
|
||||
(ell.end_angle as f32, ell.start_angle as f32)
|
||||
};
|
||||
let span = if ea > sa {
|
||||
ea - sa
|
||||
} else {
|
||||
ea - sa + std::f32::consts::TAU
|
||||
(TAU - sa, TAU - ea)
|
||||
};
|
||||
let span = ea - sa;
|
||||
let segs =
|
||||
((span / std::f32::consts::TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
((span.abs() / TAU) * 32.0).ceil().max(4.0) as u32;
|
||||
if !pts.is_empty() {
|
||||
pts.push([f32::NAN; 3]);
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user