import type { StickDistanceMode, StickPositioning } from "../model/markerDomTypes"; export type TipPoint = Readonly<{ x: number; y: number; }>; export type PillCSSPlacement = Readonly<{ pillLeft: number; pillTop: number; translateXPct: number; }>; export type StickSvgExtent = Readonly<{ halfWidth: number; halfHeight: number; }>; /** * Converts a user-facing distance to the internal stick-tip distance (where the * SVG line physically ends). The three modes differ in what the user distance * measures relative to the pill silhouette: * * - `"centerline"` — user distance IS the tip distance (line ends at cap center) * - `"rounded-edge"` — user distance is to the tangent surface; add cap radius (`pillHeight/2`) * - `"bbox-edge"` — user distance is to the nearest bbox face; add the angle-dependent half-extent. * Requires `pillWidth` for correct rectangle geometry; falls back to a square assumption if omitted. */ export declare function resolveStickInternalLength(userDist: number, mode: StickDistanceMode, angleRad: number, pillHeight: number, pillWidth?: number): number; /** * Resolves the stick tip position from a `StickPositioning` descriptor. * * The returned point is in anchor-relative coordinates (anchor = (0, 0)) and * represents the physical end of the SVG stick line. A soft floor prevents the * tip from being closer to the anchor than `dotRadius + pillHeight/2`, which * would obscure the dot or overlap the pill over the anchor. * * @param pillWidth — pill outer width in px, used by `"bbox-edge"` mode for accurate * rectangular bounding box geometry. Omit (or pass undefined) to fall back to a square * approximation (safe for circle-mode markers where width ≈ height). */ export declare function resolveTentativeTip(positioning: StickPositioning, pillHeight: number, dotRadius: number, pillWidth?: number): TipPoint; /** * Computes the CSS `left`, `top`, and `translateX(%)` needed to align the pill * so the correct rounded cap is tangent to the stick tip. * * Uses a smooth blend parameterized by `t ∈ [0, 1]`: * - `t = 1` (tipX ≥ +pillHeight/2): left cap at tipX, pill extends right * - `t = 0.5` (tipX = 0): pill centered on tipX * - `t = 0` (tipX ≤ -pillHeight/2): right cap at tipX, pill extends left * * The blend zone radius is `r = pillHeight/2` (the cap radius). This ensures * the facing cap center sits at (tipX, tipY) for any `|tipX| ≥ r`, which keeps * the visible stick length angle-independent for `rounded-edge` distance mode. * A wider blend zone (e.g. `pillHeight`) displaces the cap from tipX by an * amount proportional to pill width, causing the stick to appear shorter at * oblique angles. * * `translateX(-N%)` is relative to the element's own width, so no JS pill-width * measurement is needed. */ export declare function computePillCSSPlacement(tipX: number, tipY: number, pillHeight: number): PillCSSPlacement; /** * Computes the half-extents of the SVG element that draws the stick line, dot, * and (visually) covers the worst-case pill envelope around the anchor. * * The container itself is anchor-zero (zero-size, positioned exactly at the * geographic anchor); the SVG sits centered on that anchor with its internal * origin at `(halfWidth, halfHeight)`. The returned extents only need to be * recomputed when layout-affecting inputs change (size tier, tip angle, label * budget) — never per animation frame. */ export declare function computeStickSvgExtent(tip: TipPoint, pillHeight: number, dotRadius: number, maxPillWidth: number): StickSvgExtent;