@lovo/matter 0.4.0 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,27 @@
1
1
  # @lovo/matter
2
2
 
3
+ ## 0.5.0
4
+
5
+ ### Minor Changes
6
+
7
+ - c67eb98: Rename engine exports to spelled-out, domain-accurate names (breaking).
8
+
9
+ - `fbm` → `fractalNoise` (and `FBMOptions` → `FractalNoiseOptions`)
10
+ - `noise` → `simplexNoise`
11
+ - `sdfCircle` → `signedDistanceFieldCircle`
12
+ - `time` → `elapsedTime`
13
+ - `Vec2` → `Vector2`
14
+
15
+ `TSLNode`, `voronoi`, `colorRamp`, `quantize`, `displace`, `cursorRipple`, and `filmGrain` are unchanged.
16
+
17
+ **Migration:** one-pass find-and-replace in your imports and call sites. No behavioral changes.
18
+
19
+ ## 0.4.1
20
+
21
+ ### Patch Changes
22
+
23
+ - b4ecdda: Reorganize engine source into kebab-case module folders under `inputs/`, `primitives/`, and `runtime/` (matching `matter-react` and `registry` layout). No public API changes.
24
+
3
25
  ## 0.4.0
4
26
 
5
27
  ### Minor Changes
package/README.md CHANGED
@@ -15,18 +15,18 @@ npm install @lovo/matter three
15
15
 
16
16
  ## What's inside
17
17
 
18
- - **TSL primitives**: `fbm`, `voronoi`, `colorRamp`, `quantize`, and a handful of others — composable shader fragments for procedural visuals.
18
+ - **TSL primitives**: `fractalNoise`, `voronoi`, `colorRamp`, `quantize`, and a handful of others — composable shader fragments for procedural visuals.
19
19
  - **Renderer**: thin wrapper around `WebGPURenderer` that handles canvas resize, DPR, and `setClearColor`.
20
20
  - **Scheduler**: visibility/intersection-aware render loop that pauses when the canvas is off-screen or the tab is hidden.
21
21
 
22
22
  ## Minimal usage
23
23
 
24
24
  ```typescript
25
- import { fbm, colorRamp } from '@lovo/matter'
25
+ import { fractalNoise, colorRamp } from '@lovo/matter'
26
26
  import { uv, vec3, time } from 'three/tsl'
27
27
 
28
28
  // Inside your TSL fragment graph:
29
- const noise = fbm(uv().mul(4).add(time.mul(0.1)))
29
+ const noise = fractalNoise(uv().mul(4).add(time.mul(0.1)))
30
30
  const color = colorRamp(noise, [
31
31
  { stop: 0.0, color: vec3(0.05, 0.05, 0.1) },
32
32
  { stop: 1.0, color: vec3(0.3, 0.5, 0.95) },
package/dist/index.cjs CHANGED
@@ -29,20 +29,20 @@ __export(index_exports, {
29
29
  createVisibilityWatcher: () => createVisibilityWatcher,
30
30
  cursorRipple: () => cursorRipple,
31
31
  displace: () => displace,
32
- fbm: () => fbm,
32
+ elapsedTime: () => elapsedTime,
33
33
  filmGrain: () => filmGrain,
34
+ fractalNoise: () => fractalNoise,
34
35
  getReducedMotionPolicy: () => getReducedMotionPolicy,
35
36
  getReducedMotionTimeScale: () => getReducedMotionTimeScale,
36
- noise: () => noise,
37
37
  quantize: () => quantize,
38
- sdfCircle: () => sdfCircle,
39
38
  setReducedMotionPolicy: () => setReducedMotionPolicy,
40
- time: () => time,
39
+ signedDistanceFieldCircle: () => signedDistanceFieldCircle,
40
+ simplexNoise: () => simplexNoise,
41
41
  voronoi: () => voronoi
42
42
  });
43
43
  module.exports = __toCommonJS(index_exports);
44
44
 
45
- // src/runtime/createRenderer.ts
45
+ // src/runtime/create-renderer/create-renderer.ts
46
46
  var import_three = require("three");
47
47
  var import_webgpu = require("three/webgpu");
48
48
  async function createRenderer(canvas, opts = {}) {
@@ -63,10 +63,10 @@ async function createRenderer(canvas, opts = {}) {
63
63
  const resolvedClearColor = clearColor instanceof import_three.Color ? clearColor : new import_three.Color(clearColor);
64
64
  three.setClearColor(resolvedClearColor, clearAlpha);
65
65
  const resize = () => {
66
- const w = canvas.clientWidth;
67
- const h = canvas.clientHeight;
68
- if (canvas.width !== w * three.getPixelRatio() || canvas.height !== h * three.getPixelRatio()) {
69
- three.setSize(w, h, false);
66
+ const canvasWidth = canvas.clientWidth;
67
+ const canvasHeight = canvas.clientHeight;
68
+ if (canvas.width !== canvasWidth * three.getPixelRatio() || canvas.height !== canvasHeight * three.getPixelRatio()) {
69
+ three.setSize(canvasWidth, canvasHeight, false);
70
70
  }
71
71
  };
72
72
  resize();
@@ -80,7 +80,7 @@ async function createRenderer(canvas, opts = {}) {
80
80
  };
81
81
  }
82
82
 
83
- // src/inputs/CursorInput.ts
83
+ // src/inputs/cursor-input/cursor-input.ts
84
84
  var CursorInput = class {
85
85
  value;
86
86
  target;
@@ -100,16 +100,19 @@ var CursorInput = class {
100
100
  this.element = element;
101
101
  this.handleMouseMove = (e) => {
102
102
  if (!(e instanceof MouseEvent)) return;
103
- const me = e;
103
+ const mouseEvent = e;
104
104
  if (this.element) {
105
- const r = this.element.getBoundingClientRect();
106
- const w = r.width || 1;
107
- const h = r.height || 1;
108
- this.target = [(me.clientX - r.left) / w, (me.clientY - r.top) / h];
105
+ const elementRect = this.element.getBoundingClientRect();
106
+ const elementWidth = elementRect.width || 1;
107
+ const elementHeight = elementRect.height || 1;
108
+ this.target = [
109
+ (mouseEvent.clientX - elementRect.left) / elementWidth,
110
+ (mouseEvent.clientY - elementRect.top) / elementHeight
111
+ ];
109
112
  } else {
110
- const w = typeof window !== "undefined" && window.innerWidth || 1;
111
- const h = typeof window !== "undefined" && window.innerHeight || 1;
112
- this.target = [me.clientX / w, me.clientY / h];
113
+ const viewportWidth = typeof window !== "undefined" && window.innerWidth || 1;
114
+ const viewportHeight = typeof window !== "undefined" && window.innerHeight || 1;
115
+ this.target = [mouseEvent.clientX / viewportWidth, mouseEvent.clientY / viewportHeight];
113
116
  }
114
117
  this.targetDirty = true;
115
118
  };
@@ -120,9 +123,9 @@ var CursorInput = class {
120
123
  return this.value;
121
124
  }
122
125
  /** Subscribe to change events. Returns an unsubscribe function. */
123
- on(_event, cb) {
124
- this.listeners.add(cb);
125
- return () => this.listeners.delete(cb);
126
+ on(_eventType, changeListener) {
127
+ this.listeners.add(changeListener);
128
+ return () => this.listeners.delete(changeListener);
126
129
  }
127
130
  /**
128
131
  * Advance the smoothing one tick. Called by the host scheduler; not
@@ -151,10 +154,10 @@ var CursorInput = class {
151
154
  this.listeners.clear();
152
155
  }
153
156
  };
154
- var clamp01 = (n) => Math.max(0, Math.min(1, n));
155
- var lerp = (a, b, t) => a + (b - a) * t;
157
+ var clamp01 = (value) => Math.max(0, Math.min(1, value));
158
+ var lerp = (startValue, endValue, blendFactor) => startValue + (endValue - startValue) * blendFactor;
156
159
 
157
- // src/primitives/colorRamp.ts
160
+ // src/primitives/color-ramp/color-ramp.ts
158
161
  var import_tsl = require("three/tsl");
159
162
  var import_tsl2 = require("three/tsl");
160
163
  function colorRamp(t, stops) {
@@ -163,78 +166,78 @@ function colorRamp(t, stops) {
163
166
  if (stops.length === 1) return (0, import_tsl.mix)(first.color, first.color, 0);
164
167
  let result = (0, import_tsl.mix)(first.color, first.color, 0);
165
168
  for (let i = 1; i < stops.length; i += 1) {
166
- const prev = stops[i - 1];
169
+ const previousStop = stops[i - 1];
167
170
  const next = stops[i];
168
- if (prev === void 0 || next === void 0) continue;
169
- const span = next.position - prev.position;
170
- if (span <= 0) continue;
171
- const localT = (0, import_tsl2.clamp)((0, import_tsl2.div)((0, import_tsl2.sub)(t, prev.position), span), 0, 1);
171
+ if (previousStop === void 0 || next === void 0) continue;
172
+ const positionSpan = next.position - previousStop.position;
173
+ if (positionSpan <= 0) continue;
174
+ const localT = (0, import_tsl2.clamp)((0, import_tsl2.div)((0, import_tsl2.sub)(t, previousStop.position), positionSpan), 0, 1);
172
175
  result = (0, import_tsl.mix)(result, next.color, localT);
173
176
  }
174
177
  return result;
175
178
  }
176
179
 
177
- // src/primitives/noise.ts
180
+ // src/primitives/noise/noise.ts
178
181
  var import_tsl3 = require("three/tsl");
179
- function noise(p) {
182
+ function simplexNoise(p) {
180
183
  return (0, import_tsl3.mx_noise_float)(p);
181
184
  }
182
185
 
183
- // src/primitives/fbm.ts
186
+ // src/primitives/fbm/fbm.ts
184
187
  var import_tsl4 = require("three/tsl");
185
- function fbm(p, opts = {}) {
188
+ function fractalNoise(p, opts = {}) {
186
189
  const octaves = opts.octaves ?? 4;
187
190
  const lacunarity = opts.lacunarity ?? 2;
188
191
  const gain = opts.gain ?? 0.5;
189
- let sum = noise(p);
190
- let amp = 1;
191
- let freq = 1;
192
- let total = amp;
192
+ let sum = simplexNoise(p);
193
+ let amplitude = 1;
194
+ let frequency = 1;
195
+ let total = amplitude;
193
196
  for (let i = 1; i < octaves; i += 1) {
194
- freq *= lacunarity;
195
- amp *= gain;
196
- total += amp;
197
- const pAtFreq = (0, import_tsl4.add)((0, import_tsl4.mul)(p, freq), i * 100);
198
- const layer = noise(pAtFreq).mul(amp);
197
+ frequency *= lacunarity;
198
+ amplitude *= gain;
199
+ total += amplitude;
200
+ const pAtFreq = (0, import_tsl4.add)((0, import_tsl4.mul)(p, frequency), i * 100);
201
+ const layer = simplexNoise(pAtFreq).mul(amplitude);
199
202
  sum = sum.add(layer);
200
203
  }
201
204
  return sum.div(total);
202
205
  }
203
206
 
204
- // src/primitives/voronoi.ts
207
+ // src/primitives/voronoi/voronoi.ts
205
208
  var import_tsl5 = require("three/tsl");
206
209
  function voronoi(p) {
207
210
  return (0, import_tsl5.mx_worley_noise_float)(p);
208
211
  }
209
212
 
210
- // src/primitives/quantize.ts
213
+ // src/primitives/quantize/quantize.ts
211
214
  function quantize(t, steps) {
212
215
  if (steps <= 1) {
213
216
  return t.mul(0);
214
217
  }
215
- const denom = steps - 1;
216
- return t.mul(denom).add(0.5).floor().div(denom);
218
+ const denominator = steps - 1;
219
+ return t.mul(denominator).add(0.5).floor().div(denominator);
217
220
  }
218
221
 
219
- // src/primitives/sdfCircle.ts
222
+ // src/primitives/sdf-circle/sdf-circle.ts
220
223
  var import_tsl6 = require("three/tsl");
221
- function sdfCircle(p, radius) {
224
+ function signedDistanceFieldCircle(p, radius) {
222
225
  return (0, import_tsl6.length)(p).sub(radius);
223
226
  }
224
227
 
225
- // src/primitives/displace.ts
228
+ // src/primitives/displace/displace.ts
226
229
  var import_tsl7 = require("three/tsl");
227
230
  function displace(p, by) {
228
231
  return (0, import_tsl7.add)(p, by);
229
232
  }
230
233
 
231
- // src/primitives/cursorRipple.ts
234
+ // src/primitives/cursor-ripple/cursor-ripple.ts
232
235
  var import_tsl10 = require("three/tsl");
233
236
 
234
- // src/primitives/time.ts
237
+ // src/primitives/time/time.ts
235
238
  var import_tsl9 = require("three/tsl");
236
239
 
237
- // src/runtime/reducedMotion.ts
240
+ // src/runtime/reduced-motion/reduced-motion.ts
238
241
  var import_tsl8 = require("three/tsl");
239
242
  var state = {
240
243
  policy: "auto",
@@ -243,7 +246,7 @@ var state = {
243
246
  function setReducedMotionPolicy(policy) {
244
247
  if (state.policy === policy) return;
245
248
  state.policy = policy;
246
- for (const w of state.watchers) w.recompute();
249
+ for (const watcher of state.watchers) watcher.recompute();
247
250
  }
248
251
  function getReducedMotionPolicy() {
249
252
  return state.policy;
@@ -264,8 +267,8 @@ function createReducedMotionWatcher() {
264
267
  if (typeof matchMedia !== "function") {
265
268
  return {
266
269
  scale: () => computeScale(false),
267
- subscribe: (cb) => {
268
- void cb;
270
+ subscribe: (listener) => {
271
+ void listener;
269
272
  return () => {
270
273
  };
271
274
  },
@@ -274,33 +277,33 @@ function createReducedMotionWatcher() {
274
277
  }
275
278
  };
276
279
  }
277
- const mql = matchMedia("(prefers-reduced-motion: reduce)");
278
- const subs = /* @__PURE__ */ new Set();
279
- let last = computeScale(mql.matches);
280
+ const mediaQueryList = matchMedia("(prefers-reduced-motion: reduce)");
281
+ const subscriptions = /* @__PURE__ */ new Set();
282
+ let lastComputedScale = computeScale(mediaQueryList.matches);
280
283
  const onChange = () => {
281
- const next = computeScale(mql.matches);
282
- if (next !== last) {
283
- last = next;
284
- for (const cb of subs) cb(next);
284
+ const next = computeScale(mediaQueryList.matches);
285
+ if (next !== lastComputedScale) {
286
+ lastComputedScale = next;
287
+ for (const listener of subscriptions) listener(next);
285
288
  }
286
289
  };
287
- mql.addEventListener("change", onChange);
290
+ mediaQueryList.addEventListener("change", onChange);
288
291
  const watcher = {
289
- scale: () => last,
290
- subscribe(cb) {
291
- subs.add(cb);
292
- return () => subs.delete(cb);
292
+ scale: () => lastComputedScale,
293
+ subscribe(listener) {
294
+ subscriptions.add(listener);
295
+ return () => subscriptions.delete(listener);
293
296
  },
294
297
  recompute() {
295
- const next = computeScale(mql.matches);
296
- if (next !== last) {
297
- last = next;
298
- for (const cb of subs) cb(next);
298
+ const next = computeScale(mediaQueryList.matches);
299
+ if (next !== lastComputedScale) {
300
+ lastComputedScale = next;
301
+ for (const listener of subscriptions) listener(next);
299
302
  }
300
303
  },
301
304
  dispose() {
302
- mql.removeEventListener("change", onChange);
303
- subs.clear();
305
+ mediaQueryList.removeEventListener("change", onChange);
306
+ subscriptions.clear();
304
307
  state.watchers.delete(watcher);
305
308
  }
306
309
  };
@@ -321,32 +324,30 @@ function getReducedMotionTimeScale() {
321
324
  return globalScaleUniform;
322
325
  }
323
326
 
324
- // src/primitives/time.ts
325
- var time = import_tsl9.time.mul(getReducedMotionTimeScale());
327
+ // src/primitives/time/time.ts
328
+ var elapsedTime = import_tsl9.time.mul(getReducedMotionTimeScale());
326
329
 
327
- // src/primitives/cursorRipple.ts
330
+ // src/primitives/cursor-ripple/cursor-ripple.ts
328
331
  function cursorRipple(p, center, opts = {}) {
329
332
  const reach = opts.reach ?? 0.4;
330
333
  const frequency = opts.frequency ?? 30;
331
334
  const speed = opts.speed ?? 6;
332
335
  const amplitude = opts.amplitude ?? 0.5;
333
336
  const d = (0, import_tsl10.length)((0, import_tsl10.sub)(p, center));
334
- const wave = (0, import_tsl10.sin)(d.mul(frequency).sub(time.mul(speed)));
337
+ const wave = (0, import_tsl10.sin)(d.mul(frequency).sub(elapsedTime.mul(speed)));
335
338
  const decay = (0, import_tsl10.smoothstep)(reach, 0, d);
336
339
  return wave.mul(amplitude).mul(decay);
337
340
  }
338
341
 
339
- // src/primitives/filmGrain.ts
342
+ // src/primitives/film-grain/film-grain.ts
340
343
  var import_tsl11 = require("three/tsl");
341
- function filmGrain(uvNode, intensity, timeOffset = 0) {
342
- const HASH_C1 = (0, import_tsl11.vec2)(2127.1, 81.17);
343
- const HASH_C2 = (0, import_tsl11.vec2)(1269.5, 283.37);
344
- const base = (0, import_tsl11.vec2)(uvNode.dot(HASH_C1).add(timeOffset), uvNode.dot(HASH_C2).add(timeOffset));
345
- const hash = (0, import_tsl11.fract)((0, import_tsl11.sin)(base).mul(43758.5453));
346
- return (0, import_tsl11.length)(hash).sub(0.765).mul(intensity);
344
+ function filmGrain(intensity, timeOffset = 0) {
345
+ const pixel = import_tsl11.screenCoordinate.xy.floor();
346
+ const seed = pixel.x.toUint().mul(1973).add(pixel.y.toUint().mul(9277)).add((0, import_tsl11.mul)(timeOffset, 26699).toUint());
347
+ return (0, import_tsl11.hash)(seed).sub(0.5).mul(intensity);
347
348
  }
348
349
 
349
- // src/runtime/visibility.ts
350
+ // src/runtime/visibility/visibility.ts
350
351
  function createVisibilityWatcher() {
351
352
  if (typeof document === "undefined") {
352
353
  return {
@@ -357,26 +358,26 @@ function createVisibilityWatcher() {
357
358
  }
358
359
  };
359
360
  }
360
- const subs = /* @__PURE__ */ new Set();
361
+ const subscriptions = /* @__PURE__ */ new Set();
361
362
  const onChange = () => {
362
- const v = document.visibilityState === "visible";
363
- for (const cb of subs) cb(v);
363
+ const isVisible = document.visibilityState === "visible";
364
+ for (const listener of subscriptions) listener(isVisible);
364
365
  };
365
366
  document.addEventListener("visibilitychange", onChange);
366
367
  return {
367
368
  isVisible: () => document.visibilityState === "visible",
368
- subscribe(cb) {
369
- subs.add(cb);
370
- return () => subs.delete(cb);
369
+ subscribe(listener) {
370
+ subscriptions.add(listener);
371
+ return () => subscriptions.delete(listener);
371
372
  },
372
373
  dispose() {
373
374
  document.removeEventListener("visibilitychange", onChange);
374
- subs.clear();
375
+ subscriptions.clear();
375
376
  }
376
377
  };
377
378
  }
378
379
 
379
- // src/runtime/intersection.ts
380
+ // src/runtime/intersection/intersection.ts
380
381
  function createIntersectionWatcher(canvas) {
381
382
  if (typeof IntersectionObserver === "undefined") {
382
383
  return {
@@ -387,41 +388,50 @@ function createIntersectionWatcher(canvas) {
387
388
  }
388
389
  };
389
390
  }
390
- const subs = /* @__PURE__ */ new Set();
391
+ const subscriptions = /* @__PURE__ */ new Set();
391
392
  let inView = true;
392
- const obs = new IntersectionObserver(
393
+ const observer = new IntersectionObserver(
393
394
  (entries) => {
394
- const next = entries.some((e) => e.isIntersecting);
395
+ const next = entries.some((entry) => entry.isIntersecting);
395
396
  if (next === inView) return;
396
397
  inView = next;
397
- for (const cb of subs) cb(inView);
398
+ for (const listener of subscriptions) listener(inView);
398
399
  },
399
400
  { threshold: 0 }
400
401
  );
401
- obs.observe(canvas);
402
+ observer.observe(canvas);
402
403
  return {
403
404
  isInView: () => inView,
404
- subscribe(cb) {
405
- subs.add(cb);
406
- return () => subs.delete(cb);
405
+ subscribe(listener) {
406
+ subscriptions.add(listener);
407
+ return () => subscriptions.delete(listener);
407
408
  },
408
409
  dispose() {
409
- obs.disconnect();
410
- subs.clear();
410
+ observer.disconnect();
411
+ subscriptions.clear();
411
412
  }
412
413
  };
413
414
  }
414
415
 
415
- // src/runtime/frame-scheduler.ts
416
+ // src/runtime/frame-scheduler/frame-scheduler.ts
416
417
  var FrameScheduler = class {
417
418
  clients = /* @__PURE__ */ new Set();
418
419
  rafId = null;
419
420
  running = false;
420
421
  paused = false;
421
- idle = false;
422
422
  flushPending = false;
423
423
  startedAt = 0;
424
424
  lastTickAt = 0;
425
+ // Reference-counted idle voting. The scheduler is idle only when at least
426
+ // one component has voted idle AND no component has voted animated. This
427
+ // prevents a static component (e.g. LinearGradient speed=0) from halting
428
+ // the loop while an animated overlay (e.g. FilmGrain) is still running.
429
+ idleVotes = 0;
430
+ animatedVotes = 0;
431
+ /** True when all participating components prefer idle and none need animation. */
432
+ get idle() {
433
+ return this.idleVotes > 0 && this.animatedVotes === 0;
434
+ }
425
435
  /** Activate the scheduler. The rAF loop starts on the first client added. */
426
436
  start() {
427
437
  this.running = true;
@@ -457,19 +467,39 @@ var FrameScheduler = class {
457
467
  this.clients.clear();
458
468
  }
459
469
  /**
460
- * Mark the scheduler idle. The next tick still fires (a final flush so
461
- * uniform changes that triggered the idle state are rendered), then the
462
- * rAF loop halts. Use `requestRender()` or `setIdle(false)` to wake.
470
+ * Cast a vote on whether the scheduler should be idle.
471
+ *
472
+ * `setIdle(true)` increments the idle-vote count; the returned cleanup
473
+ * decrements it. `setIdle(false)` increments the animated-vote count;
474
+ * its cleanup decrements that. The scheduler halts (after one flush tick)
475
+ * only when `idleVotes > 0 && animatedVotes === 0`.
476
+ *
477
+ * Callers are responsible for calling the returned cleanup on unmount.
478
+ * Use `requestRender()` or cast a `setIdle(false)` vote to wake the loop
479
+ * without permanently registering an animated preference.
463
480
  */
464
481
  setIdle(idle) {
465
- if (this.idle === idle) return;
466
- this.idle = idle;
467
482
  if (idle) {
468
- this.flushPending = true;
469
- this.maybeQueue();
483
+ const wasIdle = this.idle;
484
+ this.idleVotes += 1;
485
+ const nowIdle = this.idle;
486
+ if (!wasIdle && nowIdle) this.onBecameIdle();
487
+ return () => {
488
+ const prevIdle = this.idle;
489
+ this.idleVotes = Math.max(0, this.idleVotes - 1);
490
+ const afterIdle = this.idle;
491
+ if (prevIdle && !afterIdle) this.onBecameAnimated();
492
+ };
470
493
  } else {
471
- this.flushPending = false;
472
- this.maybeQueue();
494
+ const wasIdle = this.idle;
495
+ this.animatedVotes += 1;
496
+ if (wasIdle) this.onBecameAnimated();
497
+ return () => {
498
+ const prevIdle = this.idle;
499
+ this.animatedVotes = Math.max(0, this.animatedVotes - 1);
500
+ const nowIdle = this.idle;
501
+ if (!prevIdle && nowIdle) this.onBecameIdle();
502
+ };
473
503
  }
474
504
  }
475
505
  /** Force a single tick while idle. Useful for prop-change invalidation. */
@@ -478,6 +508,14 @@ var FrameScheduler = class {
478
508
  this.flushPending = true;
479
509
  this.maybeQueue();
480
510
  }
511
+ onBecameIdle() {
512
+ this.flushPending = true;
513
+ this.maybeQueue();
514
+ }
515
+ onBecameAnimated() {
516
+ this.flushPending = false;
517
+ this.maybeQueue();
518
+ }
481
519
  maybeQueue() {
482
520
  if (this.rafId !== null) return;
483
521
  if (!this.running) return;
@@ -520,15 +558,15 @@ var FrameScheduler = class {
520
558
  createVisibilityWatcher,
521
559
  cursorRipple,
522
560
  displace,
523
- fbm,
561
+ elapsedTime,
524
562
  filmGrain,
563
+ fractalNoise,
525
564
  getReducedMotionPolicy,
526
565
  getReducedMotionTimeScale,
527
- noise,
528
566
  quantize,
529
- sdfCircle,
530
567
  setReducedMotionPolicy,
531
- time,
568
+ signedDistanceFieldCircle,
569
+ simplexNoise,
532
570
  voronoi
533
571
  });
534
572
  //# sourceMappingURL=index.cjs.map