Effect authoring API
An effect is a plain object. It does not require registration or subclassing.
const pulseRing = (options = {}) => ({
name: "pulseRing",
stage: "above",
z: 10,
duration: 1800,
hold: 200,
loop: true,
setup(globe) {
return { color: options.color ?? "#67e8f9" };
},
frame(ctx, globe, t, state) {
const point = globe.project(72.58, 23.03);
if (!point?.visible) return;
ctx.strokeStyle = state.color;
ctx.globalAlpha = 1 - t;
ctx.lineWidth = 2;
ctx.beginPath();
ctx.arc(point.x, point.y, 8 + t * 36, 0, Math.PI * 2);
ctx.stroke();
},
dispose(state, globe) {
// Remove listeners or timers created by setup().
},
});
globe.use(pulseRing());
GlobeEffect fields
| Field | Meaning |
|---|---|
name | Optional identifier used by globe.remove(name) |
stage | beneath, above, or post |
z | Paint order inside the stage; lower values paint first |
duration | Milliseconds for one cycle; default 1000 |
hold | Milliseconds held at the end of a cycle |
loop | Whether the effect repeats; default true |
setup(globe) | Runs once and returns private state |
frame(ctx, globe, t, state) | Paints the current frame, where t is from 0 to 1 |
dispose(state, globe) | Cleans up listeners, timers, and other resources |
Each frame runs inside its own ctx.save() and ctx.restore(). A thrown error is isolated and reported once so one custom effect does not stop the globe.
Paint stages
beneathpaints before the globe and is suitable for backgrounds.abovepaints after the globe and is the default for most overlays.postpaints last and is intended for full-frame processing.
Deterministic animation
Derive the complete visual result from t, the effect state, and fixed input data. Do not call Math.random() on every frame. Use the seeded rng() and particles() helpers instead.
import { particles, rng, stagger } from "canvas-globe/fx";
const dots = particles(80, 42, (random) => ({
angle: random() * Math.PI * 2,
radius: 20 + random() * 80,
}));
seek(ms) and renderFrame(ms) can then recreate the same frame. Effects that intentionally accumulate prior frames should be exported in sequential order.
Geometry and drawing helpers
The authoring toolkit includes:
- timing:
linear,easeIn,easeOut,easeInOut,backOut,pingPong,clamp01,lerp,stagger - deterministic data:
rng,particles - reusable canvases:
scratch,releaseScratch - spherical geometry:
destination,ring,centroid,drawPath - interface drawing:
panel,label,readout,bar - pointer handling:
onTap,onDragPath,nearest,pointInPath
The globe instance also provides project(), unproject(), tracePath(), landPoints(), and a read-only pointer state.
Cleanup rules
Anything created in setup() should be removed in dispose(). This includes DOM listeners, intervals, animation handles, scratch resources, and subscriptions. globe.remove(), clearEffects(), and destroy() all invoke the cleanup hook.
See the effects catalogue for production-ready examples.