@react-three/fiber 8.6.2 → 8.7.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,11 @@
1
1
  # @react-three/fiber
2
2
 
3
+ ## 8.7.0
4
+
5
+ ### Minor Changes
6
+
7
+ - f5db1b78: feat: useInstanceHandle, flushGlobalEffects
8
+
3
9
  ## 8.6.2
4
10
 
5
11
  ### Patch Changes
@@ -1,9 +1,11 @@
1
1
  import * as THREE from 'three';
2
+ import * as React from 'react';
2
3
  import { StateSelector, EqualityChecker } from 'zustand';
3
4
  import { GLTF } from 'three/examples/jsm/loaders/GLTFLoader';
4
5
  import { RootState, RenderCallback } from './store';
5
6
  import { ObjectMap } from './utils';
6
7
  import { LoadingManager } from 'three';
8
+ import { LocalState } from './renderer';
7
9
  export interface Loader<T> extends THREE.Loader {
8
10
  load(url: string, onLoad?: (result: T) => void, onProgress?: (event: ProgressEvent) => void, onError?: (event: ErrorEvent) => void): unknown;
9
11
  }
@@ -11,6 +13,7 @@ export declare type Extensions = (loader: THREE.Loader) => void;
11
13
  export declare type LoaderResult<T> = T extends any[] ? Loader<T[number]> : Loader<T>;
12
14
  export declare type ConditionalType<Child, Parent, Truthy, Falsy> = Child extends Parent ? Truthy : Falsy;
13
15
  export declare type BranchingReturn<T, Parent, Coerced> = ConditionalType<T, Parent, Coerced, T>;
16
+ export declare function useInstanceHandle<O>(ref: React.MutableRefObject<O>): React.MutableRefObject<LocalState>;
14
17
  export declare function useStore(): import("zustand").UseBoundStore<RootState, import("zustand").StoreApi<RootState>>;
15
18
  export declare function useThree<T = RootState>(selector?: StateSelector<RootState, T>, equalityFn?: EqualityChecker<T>): T;
16
19
  export declare function useFrame(callback: RenderCallback, renderPriority?: number): null;
@@ -5,6 +5,8 @@ declare type GlobalRenderCallback = (timeStamp: number) => void;
5
5
  export declare const addEffect: (callback: GlobalRenderCallback) => () => void;
6
6
  export declare const addAfterEffect: (callback: GlobalRenderCallback) => () => void;
7
7
  export declare const addTail: (callback: GlobalRenderCallback) => () => void;
8
+ export declare type GlobalEffectType = 'before' | 'after' | 'tail';
9
+ export declare function flushGlobalEffects(type: GlobalEffectType, timestamp: number): void;
8
10
  export declare function createLoop<TCanvas>(roots: Map<TCanvas, Root>): {
9
11
  loop: (timestamp: number) => void;
10
12
  invalidate: (state?: RootState | undefined, frames?: number) => void;
@@ -1468,11 +1468,24 @@ const addAfterEffect = callback => createSubs(callback, globalAfterEffects);
1468
1468
  const addTail = callback => createSubs(callback, globalTailEffects);
1469
1469
 
1470
1470
  function run(effects, timestamp) {
1471
+ if (!effects.size) return;
1471
1472
  effects.forEach(({
1472
1473
  callback
1473
1474
  }) => callback(timestamp));
1474
1475
  }
1475
1476
 
1477
+ function flushGlobalEffects(type, timestamp) {
1478
+ switch (type) {
1479
+ case 'before':
1480
+ return run(globalEffects, timestamp);
1481
+
1482
+ case 'after':
1483
+ return run(globalAfterEffects, timestamp);
1484
+
1485
+ case 'tail':
1486
+ return run(globalTailEffects, timestamp);
1487
+ }
1488
+ }
1476
1489
  let subscribers;
1477
1490
  let subscription;
1478
1491
 
@@ -1512,7 +1525,7 @@ function createLoop(roots) {
1512
1525
  running = true;
1513
1526
  repeat = 0; // Run effects
1514
1527
 
1515
- if (globalEffects.size) run(globalEffects, timestamp); // Render all roots
1528
+ flushGlobalEffects('before', timestamp); // Render all roots
1516
1529
 
1517
1530
  roots.forEach(root => {
1518
1531
  var _state$gl$xr;
@@ -1524,11 +1537,11 @@ function createLoop(roots) {
1524
1537
  }
1525
1538
  }); // Run after-effects
1526
1539
 
1527
- if (globalAfterEffects.size) run(globalAfterEffects, timestamp); // Stop the loop if nothing invalidates it
1540
+ flushGlobalEffects('after', timestamp); // Stop the loop if nothing invalidates it
1528
1541
 
1529
1542
  if (repeat === 0) {
1530
1543
  // Tail call effects, they are called when rendering stops
1531
- if (globalTailEffects.size) run(globalTailEffects, timestamp); // Flag end of operation
1544
+ flushGlobalEffects('tail', timestamp); // Flag end of operation
1532
1545
 
1533
1546
  running = false;
1534
1547
  return cancelAnimationFrame(frame);
@@ -1550,9 +1563,9 @@ function createLoop(roots) {
1550
1563
  }
1551
1564
 
1552
1565
  function advance(timestamp, runGlobalEffects = true, state, frame) {
1553
- if (runGlobalEffects) run(globalEffects, timestamp);
1566
+ if (runGlobalEffects) flushGlobalEffects('before', timestamp);
1554
1567
  if (!state) roots.forEach(root => render$1(timestamp, root.store.getState()));else render$1(timestamp, state, frame);
1555
- if (runGlobalEffects) run(globalAfterEffects, timestamp);
1568
+ if (runGlobalEffects) flushGlobalEffects('after', timestamp);
1556
1569
  }
1557
1570
 
1558
1571
  return {
@@ -1572,6 +1585,17 @@ function createLoop(roots) {
1572
1585
  };
1573
1586
  }
1574
1587
 
1588
+ /**
1589
+ * Exposes an object's {@link LocalState}.
1590
+ * @see https://docs.pmnd.rs/react-three-fiber/api/additional-exports#useInstanceHandle
1591
+ *
1592
+ * **Note**: this is an escape hatch to react-internal fields. Expect this to change significantly between versions.
1593
+ */
1594
+ function useInstanceHandle(ref) {
1595
+ const instance = React.useRef(null);
1596
+ useIsomorphicLayoutEffect(() => void (instance.current = ref.current.__r3f), [ref]);
1597
+ return instance;
1598
+ }
1575
1599
  function useStore() {
1576
1600
  const store = React.useContext(context);
1577
1601
  if (!store) throw new Error('R3F: Hooks can only be used within the Canvas component!');
@@ -2105,4 +2129,4 @@ reconciler.injectIntoDevTools({
2105
2129
  });
2106
2130
  const act = React.unstable_act;
2107
2131
 
2108
- export { Block as B, ErrorBoundary as E, createRoot as a, useIsomorphicLayoutEffect as b, createEvents as c, unmountComponentAtNode as d, extend as e, context as f, createPortal as g, reconciler as h, applyProps as i, dispose as j, invalidate as k, advance as l, addEffect as m, addAfterEffect as n, addTail as o, getRootState as p, act as q, render as r, roots as s, threeTypes as t, useMutableCallback as u, useStore as v, useThree as w, useFrame as x, useGraph as y, useLoader as z };
2132
+ export { useLoader as A, Block as B, ErrorBoundary as E, createRoot as a, useIsomorphicLayoutEffect as b, createEvents as c, unmountComponentAtNode as d, extend as e, context as f, createPortal as g, reconciler as h, applyProps as i, dispose as j, invalidate as k, advance as l, addEffect as m, addAfterEffect as n, addTail as o, getRootState as p, act as q, render as r, roots as s, threeTypes as t, useMutableCallback as u, useInstanceHandle as v, useStore as w, useThree as x, useFrame as y, useGraph as z };
@@ -1495,11 +1495,24 @@ const addAfterEffect = callback => createSubs(callback, globalAfterEffects);
1495
1495
  const addTail = callback => createSubs(callback, globalTailEffects);
1496
1496
 
1497
1497
  function run(effects, timestamp) {
1498
+ if (!effects.size) return;
1498
1499
  effects.forEach(({
1499
1500
  callback
1500
1501
  }) => callback(timestamp));
1501
1502
  }
1502
1503
 
1504
+ function flushGlobalEffects(type, timestamp) {
1505
+ switch (type) {
1506
+ case 'before':
1507
+ return run(globalEffects, timestamp);
1508
+
1509
+ case 'after':
1510
+ return run(globalAfterEffects, timestamp);
1511
+
1512
+ case 'tail':
1513
+ return run(globalTailEffects, timestamp);
1514
+ }
1515
+ }
1503
1516
  let subscribers;
1504
1517
  let subscription;
1505
1518
 
@@ -1539,7 +1552,7 @@ function createLoop(roots) {
1539
1552
  running = true;
1540
1553
  repeat = 0; // Run effects
1541
1554
 
1542
- if (globalEffects.size) run(globalEffects, timestamp); // Render all roots
1555
+ flushGlobalEffects('before', timestamp); // Render all roots
1543
1556
 
1544
1557
  roots.forEach(root => {
1545
1558
  var _state$gl$xr;
@@ -1551,11 +1564,11 @@ function createLoop(roots) {
1551
1564
  }
1552
1565
  }); // Run after-effects
1553
1566
 
1554
- if (globalAfterEffects.size) run(globalAfterEffects, timestamp); // Stop the loop if nothing invalidates it
1567
+ flushGlobalEffects('after', timestamp); // Stop the loop if nothing invalidates it
1555
1568
 
1556
1569
  if (repeat === 0) {
1557
1570
  // Tail call effects, they are called when rendering stops
1558
- if (globalTailEffects.size) run(globalTailEffects, timestamp); // Flag end of operation
1571
+ flushGlobalEffects('tail', timestamp); // Flag end of operation
1559
1572
 
1560
1573
  running = false;
1561
1574
  return cancelAnimationFrame(frame);
@@ -1577,9 +1590,9 @@ function createLoop(roots) {
1577
1590
  }
1578
1591
 
1579
1592
  function advance(timestamp, runGlobalEffects = true, state, frame) {
1580
- if (runGlobalEffects) run(globalEffects, timestamp);
1593
+ if (runGlobalEffects) flushGlobalEffects('before', timestamp);
1581
1594
  if (!state) roots.forEach(root => render$1(timestamp, root.store.getState()));else render$1(timestamp, state, frame);
1582
- if (runGlobalEffects) run(globalAfterEffects, timestamp);
1595
+ if (runGlobalEffects) flushGlobalEffects('after', timestamp);
1583
1596
  }
1584
1597
 
1585
1598
  return {
@@ -1599,6 +1612,17 @@ function createLoop(roots) {
1599
1612
  };
1600
1613
  }
1601
1614
 
1615
+ /**
1616
+ * Exposes an object's {@link LocalState}.
1617
+ * @see https://docs.pmnd.rs/react-three-fiber/api/additional-exports#useInstanceHandle
1618
+ *
1619
+ * **Note**: this is an escape hatch to react-internal fields. Expect this to change significantly between versions.
1620
+ */
1621
+ function useInstanceHandle(ref) {
1622
+ const instance = React__namespace.useRef(null);
1623
+ useIsomorphicLayoutEffect(() => void (instance.current = ref.current.__r3f), [ref]);
1624
+ return instance;
1625
+ }
1602
1626
  function useStore() {
1603
1627
  const store = React__namespace.useContext(context);
1604
1628
  if (!store) throw new Error('R3F: Hooks can only be used within the Canvas component!');
@@ -2155,6 +2179,7 @@ exports.threeTypes = threeTypes;
2155
2179
  exports.unmountComponentAtNode = unmountComponentAtNode;
2156
2180
  exports.useFrame = useFrame;
2157
2181
  exports.useGraph = useGraph;
2182
+ exports.useInstanceHandle = useInstanceHandle;
2158
2183
  exports.useIsomorphicLayoutEffect = useIsomorphicLayoutEffect;
2159
2184
  exports.useLoader = useLoader;
2160
2185
  exports.useMutableCallback = useMutableCallback;
@@ -1495,11 +1495,24 @@ const addAfterEffect = callback => createSubs(callback, globalAfterEffects);
1495
1495
  const addTail = callback => createSubs(callback, globalTailEffects);
1496
1496
 
1497
1497
  function run(effects, timestamp) {
1498
+ if (!effects.size) return;
1498
1499
  effects.forEach(({
1499
1500
  callback
1500
1501
  }) => callback(timestamp));
1501
1502
  }
1502
1503
 
1504
+ function flushGlobalEffects(type, timestamp) {
1505
+ switch (type) {
1506
+ case 'before':
1507
+ return run(globalEffects, timestamp);
1508
+
1509
+ case 'after':
1510
+ return run(globalAfterEffects, timestamp);
1511
+
1512
+ case 'tail':
1513
+ return run(globalTailEffects, timestamp);
1514
+ }
1515
+ }
1503
1516
  let subscribers;
1504
1517
  let subscription;
1505
1518
 
@@ -1539,7 +1552,7 @@ function createLoop(roots) {
1539
1552
  running = true;
1540
1553
  repeat = 0; // Run effects
1541
1554
 
1542
- if (globalEffects.size) run(globalEffects, timestamp); // Render all roots
1555
+ flushGlobalEffects('before', timestamp); // Render all roots
1543
1556
 
1544
1557
  roots.forEach(root => {
1545
1558
  var _state$gl$xr;
@@ -1551,11 +1564,11 @@ function createLoop(roots) {
1551
1564
  }
1552
1565
  }); // Run after-effects
1553
1566
 
1554
- if (globalAfterEffects.size) run(globalAfterEffects, timestamp); // Stop the loop if nothing invalidates it
1567
+ flushGlobalEffects('after', timestamp); // Stop the loop if nothing invalidates it
1555
1568
 
1556
1569
  if (repeat === 0) {
1557
1570
  // Tail call effects, they are called when rendering stops
1558
- if (globalTailEffects.size) run(globalTailEffects, timestamp); // Flag end of operation
1571
+ flushGlobalEffects('tail', timestamp); // Flag end of operation
1559
1572
 
1560
1573
  running = false;
1561
1574
  return cancelAnimationFrame(frame);
@@ -1577,9 +1590,9 @@ function createLoop(roots) {
1577
1590
  }
1578
1591
 
1579
1592
  function advance(timestamp, runGlobalEffects = true, state, frame) {
1580
- if (runGlobalEffects) run(globalEffects, timestamp);
1593
+ if (runGlobalEffects) flushGlobalEffects('before', timestamp);
1581
1594
  if (!state) roots.forEach(root => render$1(timestamp, root.store.getState()));else render$1(timestamp, state, frame);
1582
- if (runGlobalEffects) run(globalAfterEffects, timestamp);
1595
+ if (runGlobalEffects) flushGlobalEffects('after', timestamp);
1583
1596
  }
1584
1597
 
1585
1598
  return {
@@ -1599,6 +1612,17 @@ function createLoop(roots) {
1599
1612
  };
1600
1613
  }
1601
1614
 
1615
+ /**
1616
+ * Exposes an object's {@link LocalState}.
1617
+ * @see https://docs.pmnd.rs/react-three-fiber/api/additional-exports#useInstanceHandle
1618
+ *
1619
+ * **Note**: this is an escape hatch to react-internal fields. Expect this to change significantly between versions.
1620
+ */
1621
+ function useInstanceHandle(ref) {
1622
+ const instance = React__namespace.useRef(null);
1623
+ useIsomorphicLayoutEffect(() => void (instance.current = ref.current.__r3f), [ref]);
1624
+ return instance;
1625
+ }
1602
1626
  function useStore() {
1603
1627
  const store = React__namespace.useContext(context);
1604
1628
  if (!store) throw new Error('R3F: Hooks can only be used within the Canvas component!');
@@ -2155,6 +2179,7 @@ exports.threeTypes = threeTypes;
2155
2179
  exports.unmountComponentAtNode = unmountComponentAtNode;
2156
2180
  exports.useFrame = useFrame;
2157
2181
  exports.useGraph = useGraph;
2182
+ exports.useInstanceHandle = useInstanceHandle;
2158
2183
  exports.useIsomorphicLayoutEffect = useIsomorphicLayoutEffect;
2159
2184
  exports.useLoader = useLoader;
2160
2185
  exports.useMutableCallback = useMutableCallback;
@@ -2,7 +2,7 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var index = require('./index-9a338808.cjs.dev.js');
5
+ var index = require('./index-b3d1f4d2.cjs.dev.js');
6
6
  var _extends = require('@babel/runtime/helpers/extends');
7
7
  var React = require('react');
8
8
  var THREE = require('three');
@@ -263,6 +263,7 @@ exports.render = index.render;
263
263
  exports.unmountComponentAtNode = index.unmountComponentAtNode;
264
264
  exports.useFrame = index.useFrame;
265
265
  exports.useGraph = index.useGraph;
266
+ exports.useInstanceHandle = index.useInstanceHandle;
266
267
  exports.useLoader = index.useLoader;
267
268
  exports.useStore = index.useStore;
268
269
  exports.useThree = index.useThree;
@@ -2,7 +2,7 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var index = require('./index-f368ca4a.cjs.prod.js');
5
+ var index = require('./index-846c69c6.cjs.prod.js');
6
6
  var _extends = require('@babel/runtime/helpers/extends');
7
7
  var React = require('react');
8
8
  var THREE = require('three');
@@ -263,6 +263,7 @@ exports.render = index.render;
263
263
  exports.unmountComponentAtNode = index.unmountComponentAtNode;
264
264
  exports.useFrame = index.useFrame;
265
265
  exports.useGraph = index.useGraph;
266
+ exports.useInstanceHandle = index.useInstanceHandle;
266
267
  exports.useLoader = index.useLoader;
267
268
  exports.useStore = index.useStore;
268
269
  exports.useThree = index.useThree;
@@ -1,5 +1,5 @@
1
- import { c as createEvents, e as extend, u as useMutableCallback, a as createRoot, E as ErrorBoundary, B as Block, b as useIsomorphicLayoutEffect, d as unmountComponentAtNode } from './index-cecf55e8.esm.js';
2
- export { t as ReactThreeFiber, s as _roots, q as act, n as addAfterEffect, m as addEffect, o as addTail, l as advance, i as applyProps, f as context, c as createEvents, g as createPortal, a as createRoot, j as dispose, e as extend, p as getRootState, k as invalidate, h as reconciler, r as render, d as unmountComponentAtNode, x as useFrame, y as useGraph, z as useLoader, v as useStore, w as useThree } from './index-cecf55e8.esm.js';
1
+ import { c as createEvents, e as extend, u as useMutableCallback, a as createRoot, E as ErrorBoundary, B as Block, b as useIsomorphicLayoutEffect, d as unmountComponentAtNode } from './index-3b3bed95.esm.js';
2
+ export { t as ReactThreeFiber, s as _roots, q as act, n as addAfterEffect, m as addEffect, o as addTail, l as advance, i as applyProps, f as context, c as createEvents, g as createPortal, a as createRoot, j as dispose, e as extend, p as getRootState, k as invalidate, h as reconciler, r as render, d as unmountComponentAtNode, y as useFrame, z as useGraph, v as useInstanceHandle, A as useLoader, w as useStore, x as useThree } from './index-3b3bed95.esm.js';
3
3
  import _extends from '@babel/runtime/helpers/esm/extends';
4
4
  import * as React from 'react';
5
5
  import * as THREE from 'three';
@@ -2,7 +2,7 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var index = require('../../dist/index-9a338808.cjs.dev.js');
5
+ var index = require('../../dist/index-b3d1f4d2.cjs.dev.js');
6
6
  var _extends = require('@babel/runtime/helpers/extends');
7
7
  var React = require('react');
8
8
  var THREE = require('three');
@@ -401,6 +401,7 @@ exports.render = index.render;
401
401
  exports.unmountComponentAtNode = index.unmountComponentAtNode;
402
402
  exports.useFrame = index.useFrame;
403
403
  exports.useGraph = index.useGraph;
404
+ exports.useInstanceHandle = index.useInstanceHandle;
404
405
  exports.useLoader = index.useLoader;
405
406
  exports.useStore = index.useStore;
406
407
  exports.useThree = index.useThree;
@@ -2,7 +2,7 @@
2
2
 
3
3
  Object.defineProperty(exports, '__esModule', { value: true });
4
4
 
5
- var index = require('../../dist/index-f368ca4a.cjs.prod.js');
5
+ var index = require('../../dist/index-846c69c6.cjs.prod.js');
6
6
  var _extends = require('@babel/runtime/helpers/extends');
7
7
  var React = require('react');
8
8
  var THREE = require('three');
@@ -401,6 +401,7 @@ exports.render = index.render;
401
401
  exports.unmountComponentAtNode = index.unmountComponentAtNode;
402
402
  exports.useFrame = index.useFrame;
403
403
  exports.useGraph = index.useGraph;
404
+ exports.useInstanceHandle = index.useInstanceHandle;
404
405
  exports.useLoader = index.useLoader;
405
406
  exports.useStore = index.useStore;
406
407
  exports.useThree = index.useThree;
@@ -1,5 +1,5 @@
1
- import { c as createEvents, e as extend, u as useMutableCallback, a as createRoot, E as ErrorBoundary, B as Block, d as unmountComponentAtNode } from '../../dist/index-cecf55e8.esm.js';
2
- export { t as ReactThreeFiber, s as _roots, q as act, n as addAfterEffect, m as addEffect, o as addTail, l as advance, i as applyProps, f as context, g as createPortal, a as createRoot, j as dispose, e as extend, p as getRootState, k as invalidate, h as reconciler, r as render, d as unmountComponentAtNode, x as useFrame, y as useGraph, z as useLoader, v as useStore, w as useThree } from '../../dist/index-cecf55e8.esm.js';
1
+ import { c as createEvents, e as extend, u as useMutableCallback, a as createRoot, E as ErrorBoundary, B as Block, d as unmountComponentAtNode } from '../../dist/index-3b3bed95.esm.js';
2
+ export { t as ReactThreeFiber, s as _roots, q as act, n as addAfterEffect, m as addEffect, o as addTail, l as advance, i as applyProps, f as context, g as createPortal, a as createRoot, j as dispose, e as extend, p as getRootState, k as invalidate, h as reconciler, r as render, d as unmountComponentAtNode, y as useFrame, z as useGraph, v as useInstanceHandle, A as useLoader, w as useStore, x as useThree } from '../../dist/index-3b3bed95.esm.js';
3
3
  import _extends from '@babel/runtime/helpers/esm/extends';
4
4
  import * as React from 'react';
5
5
  import * as THREE from 'three';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@react-three/fiber",
3
- "version": "8.6.2",
3
+ "version": "8.7.0",
4
4
  "description": "A React renderer for Threejs",
5
5
  "keywords": [
6
6
  "react",