engine library

The dot engine behind morph_orbs, for packages that build their own dotted animations on top of it: the reusable OrbFrame buffer and its index-mapped morph, the shared painter, every orb geometry resolved for a size, and the small math kit the geometries use.

import 'package:morph_orbs/engine.dart';

Most apps only need package:morph_orbs/morph_orbs.dart.

Classes

OrbFrame
One rendered instant: a reusable, growable buffer of dots. Each dot is stride doubles — x, y, z, radius, ink (0 = full ink, 1 = none), alpha. order holds the indices sorted far → near after sortByDepth.
OrbGeometry
Pure geometry for one instant: writes the dots for (size, t, profile) into out. No rendering surface, no colour — ink is resolved at paint time. Implementations are stateless and deterministic, so any two geometries can be morphed dot-for-dot by the controller.
OrbProfile
Density and mark tuning for one geometry, after preset multipliers. Lattice pairs (rings × dots-per-ring, lanes × segs) scale by √factor on each side so the total count scales linearly; flat counts scale directly.
OrbStateSpec
What one MorphOrbState renders: a geometry, the per-state tweaks on its resolved profile, and how it is framed.
Projector
Spin + tilt + orthographic projection. Mutable scratch output avoids a list allocation per projected point.
ResolvedOrbState
A state resolved for one size: the geometry to run and its profile.
Vec3

Constants

kTau → const double

Functions

angleDelta(double a, double b) → double
Shortest signed angular distance, wrapped to (-π, π].
clamp01(double x) → double
fibDir(int i, int n, Vec3 out) → void
Stable directions on a unit sphere (Fibonacci lattice), written to out.
frac(double x) → double
hashD(double a, double b) → double
Deterministic hash in [0, 1).
lerp(double a, double b, double f) → double
lerpLog(double a, double b, double f) → double
Interpolates ratios in log space, so a multiplier halfway between 1 and 4 is 2, not 2.5.
paintOrbFrame(Canvas canvas, OrbFrame frame, {required Color ink, required Color? background, required Offset offset, required Paint dotPaint, required Paint linePaint}) → void
Draws frame onto canvas: stroked lines first, then dots far → near.
radiusScale(double size, double pow) → double
Dot radii were tuned for a 300pt frame; sub-linear scaling keeps small orbs legible.
resolveOrbState(MorphOrbState state, double size, {MorphOrbVariant? variant, double density = 1, double dotScale = 1}) → ResolvedOrbState
smoothStep(double x) → double
vnoise(double x, double y) → double
Value noise on a 2D lattice — smooth, deterministic, cheap.