Skip to content

Commit 117b754

Browse files
Jammy2211Jammy2211
authored andcommitted
move outside border should be safer
1 parent a2e3c05 commit 117b754

File tree

1 file changed

+16
-24
lines changed

1 file changed

+16
-24
lines changed

autoarray/inversion/pixelization/border_relocator.py

Lines changed: 16 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -263,25 +263,15 @@ def ellipse_params_via_border_pca_from(border_grid, xp=np, eps=1e-12):
263263
return origin, a, b, phi
264264

265265

266-
def relocated_grid_via_ellipse_border_from(grid, origin, a, b, phi, xp=np, border_frac=1e-2):
266+
def relocated_grid_via_ellipse_border_from(
267+
grid, origin, a, b, phi, xp=np, eps=1e-12, border_frac=1e-3
268+
):
267269
"""
268-
Rotated ellipse centered at origin with semi-axes a (major, x'), b (minor, y'),
269-
rotated by phi radians (counterclockwise).
270+
Move points outside the ellipse to a contour slightly *outside* the border
271+
to avoid geometric degeneracy in Voronoi/Delaunay.
270272
271-
Parameters
272-
----------
273-
grid : (N,2)
274-
Coordinates in (y, x) order.
275-
origin : (2,)
276-
Ellipse center (y0, x0).
277-
a, b : float
278-
Semi-major and semi-minor axes.
279-
phi : float
280-
Rotation angle in radians.
281-
xp : module
282-
numpy-like module (np, jnp, cupy, etc.).
283-
eps : float
284-
Numerical safety epsilon.
273+
border_frac: fractional expansion of ellipse radius
274+
(e.g. 1e-3 = +0.1% outside).
285275
"""
286276

287277
dy = grid[:, 0] - origin[0]
@@ -290,26 +280,27 @@ def relocated_grid_via_ellipse_border_from(grid, origin, a, b, phi, xp=np, borde
290280
c = xp.cos(phi)
291281
s = xp.sin(phi)
292282

283+
# Rotate into ellipse-aligned frame
293284
xprime = c * dx + s * dy
294285
yprime = -s * dx + c * dy
295286

287+
# Normalized ellipse radius
296288
q = (xprime / a) ** 2 + (yprime / b) ** 2
297289

298290
outside = q > 1.0
299291

300-
# Target radius in normalized coords (slightly inside 1.0)
301-
# Using squared target so it matches q's definition.
302-
shrink = xp.asarray(1.0 - border_frac, dtype=q.dtype)
303-
q_target = shrink * shrink # (1 - border_frac)^2
292+
# Target radius slightly OUTSIDE ellipse
293+
expand = xp.asarray(1.0 + border_frac, dtype=q.dtype)
294+
q_target = expand * expand # (1 + border_frac)^2
304295

305-
# Project outside points to q = q_target
306-
# scale^2 * q = q_target -> scale = sqrt(q_target / q)
307-
safe_q = xp.maximum(q, xp.asarray(1.0, dtype=q.dtype)) # outside => q>=1; inside => 1
296+
# Project only outside points
297+
safe_q = xp.maximum(q, xp.asarray(1.0, dtype=q.dtype))
308298
scale = xp.sqrt(q_target / safe_q)
309299

310300
xprime2 = xprime * scale
311301
yprime2 = yprime * scale
312302

303+
# Rotate back
313304
dx2 = c * xprime2 - s * yprime2
314305
dy2 = s * xprime2 + c * yprime2
315306

@@ -318,6 +309,7 @@ def relocated_grid_via_ellipse_border_from(grid, origin, a, b, phi, xp=np, borde
318309
return xp.where(outside[:, None], moved, grid)
319310

320311

312+
321313
class BorderRelocator:
322314
def __init__(
323315
self,

0 commit comments

Comments
 (0)