Warp travel shimmers at the threshold, not around the traveler

Green rings at the traveler's squares become a portal curtain: the
opening LINE itself shimmers on both boards — resolved from the warp
table via the step's direction — in iridescent cyan over a soft
violet breath, dashes drifting like light through a veil. Dimensional
warp tokens, whose mouths are whole squares, wrap in the same veil
around the square instead.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
Eric Wagoner
2026-08-17 09:11:29 -04:00
co-authored by Claude Fable 5
parent 68b0da6301
commit a82b25b0e8
2 changed files with 58 additions and 17 deletions
+16 -5
View File
@@ -10,8 +10,9 @@ type Side = "N" | "E" | "S" | "W";
type FxShape =
| { kind: "fireball" | "bolt" | "waterbolt" | "streak"; from: Cell; to: Cell }
| { kind: "burst" | "splash" | "shimmer" | "shield" | "sparkle" | "whiff" | "hit"
| "pow" | "claw" | "absorb" | "warp-glow" | "soul" | "fireworks" | "chaos-swirl"
| "pow" | "claw" | "absorb" | "portal-cell" | "soul" | "fireworks" | "chaos-swirl"
| "pit-fall" | "ooze-slip" | "tacks-ow" | "thorn-snap" | "slime-stuck" | "dust-puff"; at: Cell }
| { kind: "portal"; cell: Cell; side: Side }
| { kind: "sector-spin"; origin: Cell; clockwise: boolean }
| { kind: "sector-slide"; from: Cell; to: Cell }
| { kind: "edge-dust"; cell: Cell; side: Side };
@@ -24,6 +25,7 @@ export function fxTtl(kind: BoardFx["kind"]): number {
switch (kind) {
case "fireball": case "waterbolt": return 700;
case "bolt": case "streak": return 600;
case "portal": case "portal-cell":
case "soul": case "fireworks": case "chaos-swirl":
case "sector-spin": case "sector-slide": return 1500;
default: return 900;
@@ -131,14 +133,23 @@ export function fxForEvents(
break;
case "moved":
if (e.via === "warp") {
push({ kind: "warp-glow", at: e.from });
push({ kind: "warp-glow", at: e.to }, 150);
// The mouths are edges: shimmer the opening lines on both boards.
const w = view.board.warps.find((w) =>
w.from.cell.x === e.from.x && w.from.cell.y === e.from.y && w.from.side === e.direction);
if (w) {
push({ kind: "portal", cell: w.from.cell, side: w.from.side });
push({ kind: "portal", cell: w.to.cell, side: w.to.side }, 150);
} else {
push({ kind: "portal-cell", at: e.from });
push({ kind: "portal-cell", at: e.to }, 150);
}
beat++;
}
break;
case "warpStepped":
push({ kind: "warp-glow", at: e.from });
push({ kind: "warp-glow", at: e.to }, 150);
// Dimensional warp tokens fill their squares; the veil wraps them.
push({ kind: "portal-cell", at: e.from });
push({ kind: "portal-cell", at: e.to }, 150);
beat++;
break;
case "wallCreated":