@react-three/fiber 8.0.0-beta-01 → 8.0.0-beta-05
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 +48 -0
- package/dist/declarations/src/core/events.d.ts +5 -4
- package/dist/declarations/src/{web → core}/index.d.ts +6 -8
- package/dist/declarations/src/core/loop.d.ts +2 -1
- package/dist/declarations/src/core/renderer.d.ts +5 -5
- package/dist/declarations/src/core/store.d.ts +15 -7
- package/dist/declarations/src/core/utils.d.ts +8 -1
- package/dist/declarations/src/index.d.ts +4 -2
- package/dist/declarations/src/native/Canvas.d.ts +2 -5
- package/dist/declarations/src/native/events.d.ts +0 -1
- package/dist/declarations/src/native.d.ts +4 -2
- package/dist/declarations/src/three-types.d.ts +12 -24
- package/dist/declarations/src/web/Canvas.d.ts +2 -2
- package/dist/declarations/src/web/events.d.ts +0 -1
- package/dist/{hooks-c89a6f88.esm.js → index-3f4e5f46.esm.js} +459 -163
- package/dist/{hooks-e01f12ec.cjs.prod.js → index-95c17855.cjs.dev.js} +478 -175
- package/dist/{hooks-dd693347.cjs.dev.js → index-ff8b5912.cjs.prod.js} +478 -175
- package/dist/react-three-fiber.cjs.dev.js +83 -300
- package/dist/react-three-fiber.cjs.prod.js +83 -300
- package/dist/react-three-fiber.esm.js +56 -273
- package/native/dist/react-three-fiber-native.cjs.dev.js +160 -392
- package/native/dist/react-three-fiber-native.cjs.prod.js +160 -392
- package/native/dist/react-three-fiber-native.esm.js +135 -367
- package/package.json +21 -13
- package/readme.md +10 -10
- package/dist/declarations/src/native/hooks.d.ts +0 -9
- package/dist/declarations/src/native/index.d.ts +0 -37
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var THREE = require('three');
|
|
4
|
-
var Reconciler = require('react-reconciler');
|
|
5
|
-
var constants = require('react-reconciler/constants');
|
|
6
3
|
var React = require('react');
|
|
7
4
|
var suspendReact = require('suspend-react');
|
|
5
|
+
var THREE = require('three');
|
|
6
|
+
var constants = require('react-reconciler/constants');
|
|
8
7
|
var create = require('zustand');
|
|
8
|
+
var Reconciler = require('react-reconciler');
|
|
9
|
+
var scheduler = require('scheduler');
|
|
9
10
|
|
|
10
11
|
function _interopDefault (e) { return e && e.__esModule ? e : { 'default': e }; }
|
|
11
12
|
|
|
@@ -18,19 +19,21 @@ function _interopNamespace(e) {
|
|
|
18
19
|
var d = Object.getOwnPropertyDescriptor(e, k);
|
|
19
20
|
Object.defineProperty(n, k, d.get ? d : {
|
|
20
21
|
enumerable: true,
|
|
21
|
-
get: function () {
|
|
22
|
+
get: function () {
|
|
23
|
+
return e[k];
|
|
24
|
+
}
|
|
22
25
|
});
|
|
23
26
|
}
|
|
24
27
|
});
|
|
25
28
|
}
|
|
26
|
-
n[
|
|
29
|
+
n['default'] = e;
|
|
27
30
|
return Object.freeze(n);
|
|
28
31
|
}
|
|
29
32
|
|
|
30
|
-
var THREE__namespace = /*#__PURE__*/_interopNamespace(THREE);
|
|
31
|
-
var Reconciler__default = /*#__PURE__*/_interopDefault(Reconciler);
|
|
32
33
|
var React__namespace = /*#__PURE__*/_interopNamespace(React);
|
|
34
|
+
var THREE__namespace = /*#__PURE__*/_interopNamespace(THREE);
|
|
33
35
|
var create__default = /*#__PURE__*/_interopDefault(create);
|
|
36
|
+
var Reconciler__default = /*#__PURE__*/_interopDefault(Reconciler);
|
|
34
37
|
|
|
35
38
|
var threeTypes = /*#__PURE__*/Object.freeze({
|
|
36
39
|
__proto__: null
|
|
@@ -40,7 +43,34 @@ const DEFAULT = '__default';
|
|
|
40
43
|
const isDiffSet = def => def && !!def.memoized && !!def.changes;
|
|
41
44
|
function calculateDpr(dpr) {
|
|
42
45
|
return Array.isArray(dpr) ? Math.min(Math.max(dpr[0], window.devicePixelRatio), dpr[1]) : dpr;
|
|
43
|
-
}
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* Picks or omits keys from an object
|
|
49
|
+
* `omit` will filter out keys, and otherwise cherry-pick them.
|
|
50
|
+
*/
|
|
51
|
+
|
|
52
|
+
function filterKeys(obj, omit, ...keys) {
|
|
53
|
+
const keysToSelect = new Set(keys);
|
|
54
|
+
return Object.entries(obj).reduce((acc, [key, value]) => {
|
|
55
|
+
const shouldInclude = !omit;
|
|
56
|
+
|
|
57
|
+
if (keysToSelect.has(key) === shouldInclude) {
|
|
58
|
+
acc[key] = value;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
return acc;
|
|
62
|
+
}, {});
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Clones an object and cherry-picks keys.
|
|
66
|
+
*/
|
|
67
|
+
|
|
68
|
+
const pick = (obj, keys) => filterKeys(obj, false, ...keys);
|
|
69
|
+
/**
|
|
70
|
+
* Clones an object and prunes or omits keys.
|
|
71
|
+
*/
|
|
72
|
+
|
|
73
|
+
const omit = (obj, keys) => filterKeys(obj, true, ...keys); // A collection of compare functions
|
|
44
74
|
|
|
45
75
|
const is = {
|
|
46
76
|
obj: a => a === Object(a) && !is.arr(a) && typeof a !== 'function',
|
|
@@ -89,8 +119,7 @@ function dispose(obj) {
|
|
|
89
119
|
if (obj.dispose && obj.type !== 'Scene') obj.dispose();
|
|
90
120
|
|
|
91
121
|
for (const p in obj) {
|
|
92
|
-
|
|
93
|
-
(_dispose = (_ref = p).dispose) == null ? void 0 : _dispose.call(_ref);
|
|
122
|
+
p.dispose == null ? void 0 : p.dispose();
|
|
94
123
|
delete obj[p];
|
|
95
124
|
}
|
|
96
125
|
} // Each object in the scene carries a small LocalState descriptor
|
|
@@ -111,6 +140,49 @@ function prepare(object, state) {
|
|
|
111
140
|
}
|
|
112
141
|
|
|
113
142
|
return object;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
function resolve(instance, key) {
|
|
146
|
+
let target = instance;
|
|
147
|
+
|
|
148
|
+
if (key.includes('-')) {
|
|
149
|
+
const entries = key.split('-');
|
|
150
|
+
const last = entries.pop();
|
|
151
|
+
target = entries.reduce((acc, key) => acc[key], instance);
|
|
152
|
+
return {
|
|
153
|
+
target,
|
|
154
|
+
key: last
|
|
155
|
+
};
|
|
156
|
+
} else return {
|
|
157
|
+
target,
|
|
158
|
+
key
|
|
159
|
+
};
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
function attach(parent, child, type) {
|
|
163
|
+
if (is.str(type)) {
|
|
164
|
+
const {
|
|
165
|
+
target,
|
|
166
|
+
key
|
|
167
|
+
} = resolve(parent, type);
|
|
168
|
+
parent.__r3f.previousAttach = target[key];
|
|
169
|
+
target[key] = child;
|
|
170
|
+
} else if (is.arr(type)) {
|
|
171
|
+
const [attach] = type;
|
|
172
|
+
if (is.str(attach)) parent[attach](child);else if (is.fun(attach)) attach(parent, child);
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
function detach(parent, child, type) {
|
|
176
|
+
if (is.str(type)) {
|
|
177
|
+
const {
|
|
178
|
+
target,
|
|
179
|
+
key
|
|
180
|
+
} = resolve(parent, type);
|
|
181
|
+
target[key] = parent.__r3f.previousAttach;
|
|
182
|
+
} else if (is.arr(type)) {
|
|
183
|
+
const [, detach] = type;
|
|
184
|
+
if (is.str(detach)) parent[detach](child);else if (is.fun(detach)) detach(parent, child);
|
|
185
|
+
}
|
|
114
186
|
} // Shallow check arrays, but check objects atomically
|
|
115
187
|
|
|
116
188
|
function checkShallow(a, b) {
|
|
@@ -140,7 +212,9 @@ function diffProps(instance, {
|
|
|
140
212
|
if (remove) {
|
|
141
213
|
const previousKeys = Object.keys(previous);
|
|
142
214
|
|
|
143
|
-
for (let i = 0; i < previousKeys.length; i++)
|
|
215
|
+
for (let i = 0; i < previousKeys.length; i++) {
|
|
216
|
+
if (!props.hasOwnProperty(previousKeys[i])) entries.unshift([previousKeys[i], DEFAULT + 'remove']);
|
|
217
|
+
}
|
|
144
218
|
}
|
|
145
219
|
|
|
146
220
|
entries.forEach(([key, value]) => {
|
|
@@ -167,7 +241,7 @@ function diffProps(instance, {
|
|
|
167
241
|
};
|
|
168
242
|
} // This function applies a set of changes to the instance
|
|
169
243
|
|
|
170
|
-
function applyProps(instance, data) {
|
|
244
|
+
function applyProps$1(instance, data) {
|
|
171
245
|
var _instance$__r3f3, _root$getState;
|
|
172
246
|
|
|
173
247
|
// Filter equals, events and reserved props
|
|
@@ -211,7 +285,9 @@ function applyProps(instance, data) {
|
|
|
211
285
|
value = defaultClassCall[targetProp]; // destory the instance
|
|
212
286
|
|
|
213
287
|
if (defaultClassCall.dispose) defaultClassCall.dispose(); // instance does not have constructor, just set it to 0
|
|
214
|
-
} else
|
|
288
|
+
} else {
|
|
289
|
+
value = 0;
|
|
290
|
+
}
|
|
215
291
|
} // Deal with pointer events ...
|
|
216
292
|
|
|
217
293
|
|
|
@@ -220,35 +296,39 @@ function applyProps(instance, data) {
|
|
|
220
296
|
localState.eventCount = Object.keys(localState.handlers).length;
|
|
221
297
|
} // Special treatment for objects with support for set/copy, and layers
|
|
222
298
|
else if (targetProp && targetProp.set && (targetProp.copy || targetProp instanceof THREE__namespace.Layers)) {
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
299
|
+
// If value is an array
|
|
300
|
+
if (Array.isArray(value)) {
|
|
301
|
+
if (targetProp.fromArray) targetProp.fromArray(value);else targetProp.set(...value);
|
|
302
|
+
} // Test again target.copy(class) next ...
|
|
303
|
+
else if (targetProp.copy && value && value.constructor && targetProp.constructor.name === value.constructor.name) {
|
|
304
|
+
targetProp.copy(value);
|
|
305
|
+
} // If nothing else fits, just set the single value, ignore undefined
|
|
306
|
+
// https://github.com/pmndrs/react-three-fiber/issues/274
|
|
307
|
+
else if (value !== undefined) {
|
|
308
|
+
const isColor = targetProp instanceof THREE__namespace.Color; // Allow setting array scalars
|
|
309
|
+
|
|
310
|
+
if (!isColor && targetProp.setScalar) targetProp.setScalar(value); // Layers have no copy function, we must therefore copy the mask property
|
|
311
|
+
else if (targetProp instanceof THREE__namespace.Layers && value instanceof THREE__namespace.Layers) targetProp.mask = value.mask; // Otherwise just set ...
|
|
312
|
+
else targetProp.set(value); // Auto-convert sRGB colors, for now ...
|
|
313
|
+
// https://github.com/pmndrs/react-three-fiber/issues/344
|
|
314
|
+
|
|
315
|
+
if (!rootState.linear && isColor) targetProp.convertSRGBToLinear();
|
|
316
|
+
} // Else, just overwrite the value
|
|
239
317
|
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
318
|
+
} else {
|
|
319
|
+
currentInstance[key] = value; // Auto-convert sRGB textures, for now ...
|
|
320
|
+
// https://github.com/pmndrs/react-three-fiber/issues/344
|
|
243
321
|
|
|
244
|
-
|
|
245
|
-
|
|
322
|
+
if (!rootState.linear && currentInstance[key] instanceof THREE__namespace.Texture) {
|
|
323
|
+
currentInstance[key].encoding = THREE__namespace.sRGBEncoding;
|
|
324
|
+
}
|
|
325
|
+
}
|
|
246
326
|
|
|
247
327
|
invalidateInstance(instance);
|
|
248
328
|
return instance;
|
|
249
329
|
});
|
|
250
330
|
|
|
251
|
-
if (rootState.internal && instance.raycast && prevHandlers !== localState.eventCount) {
|
|
331
|
+
if (localState.parent && rootState.internal && instance.raycast && prevHandlers !== localState.eventCount) {
|
|
252
332
|
// Pre-emptively remove the instance from the interaction manager
|
|
253
333
|
const index = rootState.internal.interaction.indexOf(instance);
|
|
254
334
|
if (index > -1) rootState.internal.interaction.splice(index, 1); // Add the instance to the interaction manager only when it has handlers
|
|
@@ -271,12 +351,41 @@ function updateInstance(instance) {
|
|
|
271
351
|
|
|
272
352
|
function makeId(event) {
|
|
273
353
|
return (event.eventObject || event.object).uuid + '/' + event.index + event.instanceId;
|
|
354
|
+
} // https://github.com/facebook/react/tree/main/packages/react-reconciler#getcurrenteventpriority
|
|
355
|
+
// Gives React a clue as to how import the current interaction is
|
|
356
|
+
|
|
357
|
+
|
|
358
|
+
function getEventPriority() {
|
|
359
|
+
var _window, _window$event;
|
|
360
|
+
|
|
361
|
+
let name = (_window = window) == null ? void 0 : (_window$event = _window.event) == null ? void 0 : _window$event.type;
|
|
362
|
+
|
|
363
|
+
switch (name) {
|
|
364
|
+
case 'click':
|
|
365
|
+
case 'contextmenu':
|
|
366
|
+
case 'dblclick':
|
|
367
|
+
case 'pointercancel':
|
|
368
|
+
case 'pointerdown':
|
|
369
|
+
case 'pointerup':
|
|
370
|
+
return constants.DiscreteEventPriority;
|
|
371
|
+
|
|
372
|
+
case 'pointermove':
|
|
373
|
+
case 'pointerout':
|
|
374
|
+
case 'pointerover':
|
|
375
|
+
case 'pointerenter':
|
|
376
|
+
case 'pointerleave':
|
|
377
|
+
case 'wheel':
|
|
378
|
+
return constants.ContinuousEventPriority;
|
|
379
|
+
|
|
380
|
+
default:
|
|
381
|
+
return constants.DefaultEventPriority;
|
|
382
|
+
}
|
|
274
383
|
}
|
|
275
|
-
/**
|
|
384
|
+
/**
|
|
385
|
+
* Release pointer captures.
|
|
276
386
|
* This is called by releasePointerCapture in the API, and when an object is removed.
|
|
277
387
|
*/
|
|
278
388
|
|
|
279
|
-
|
|
280
389
|
function releaseInternalPointerCapture(capturedMap, obj, captures, pointerId) {
|
|
281
390
|
const captureData = captures.get(obj);
|
|
282
391
|
|
|
@@ -311,7 +420,7 @@ function createEvents(store) {
|
|
|
311
420
|
/** Sets up defaultRaycaster */
|
|
312
421
|
|
|
313
422
|
function prepareRay(event) {
|
|
314
|
-
var
|
|
423
|
+
var _customOffsets$offset, _customOffsets$offset2, _customOffsets$width, _customOffsets$height;
|
|
315
424
|
|
|
316
425
|
const state = store.getState();
|
|
317
426
|
const {
|
|
@@ -322,14 +431,11 @@ function createEvents(store) {
|
|
|
322
431
|
} = state; // https://github.com/pmndrs/react-three-fiber/pull/782
|
|
323
432
|
// Events trigger outside of canvas when moved
|
|
324
433
|
|
|
325
|
-
const
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
const
|
|
330
|
-
width,
|
|
331
|
-
height
|
|
332
|
-
} = size;
|
|
434
|
+
const customOffsets = raycaster.computeOffsets == null ? void 0 : raycaster.computeOffsets(event, state);
|
|
435
|
+
const offsetX = (_customOffsets$offset = customOffsets == null ? void 0 : customOffsets.offsetX) != null ? _customOffsets$offset : event.offsetX;
|
|
436
|
+
const offsetY = (_customOffsets$offset2 = customOffsets == null ? void 0 : customOffsets.offsetY) != null ? _customOffsets$offset2 : event.offsetY;
|
|
437
|
+
const width = (_customOffsets$width = customOffsets == null ? void 0 : customOffsets.width) != null ? _customOffsets$width : size.width;
|
|
438
|
+
const height = (_customOffsets$height = customOffsets == null ? void 0 : customOffsets.height) != null ? _customOffsets$height : size.height;
|
|
333
439
|
mouse.set(offsetX / width * 2 - 1, -(offsetY / height) * 2 + 1);
|
|
334
440
|
raycaster.setFromCamera(mouse, camera);
|
|
335
441
|
}
|
|
@@ -559,13 +665,16 @@ function createEvents(store) {
|
|
|
559
665
|
|
|
560
666
|
case 'onLostPointerCapture':
|
|
561
667
|
return event => {
|
|
562
|
-
|
|
668
|
+
const {
|
|
669
|
+
internal
|
|
670
|
+
} = store.getState();
|
|
671
|
+
|
|
672
|
+
if ('pointerId' in event && !internal.capturedMap.has(event.pointerId)) {
|
|
563
673
|
// If the object event interface had onLostPointerCapture, we'd call it here on every
|
|
564
674
|
// object that's getting removed.
|
|
565
|
-
|
|
675
|
+
internal.capturedMap.delete(event.pointerId);
|
|
676
|
+
cancelPointer([]);
|
|
566
677
|
}
|
|
567
|
-
|
|
568
|
-
cancelPointer([]);
|
|
569
678
|
};
|
|
570
679
|
} // Any other pointer goes here ...
|
|
571
680
|
|
|
@@ -575,7 +684,8 @@ function createEvents(store) {
|
|
|
575
684
|
onPointerMissed,
|
|
576
685
|
internal
|
|
577
686
|
} = store.getState();
|
|
578
|
-
prepareRay(event);
|
|
687
|
+
prepareRay(event);
|
|
688
|
+
internal.lastEvent.current = event; // Get fresh intersects
|
|
579
689
|
|
|
580
690
|
const isPointerMove = name === 'onPointerMove';
|
|
581
691
|
const isClickEvent = name === 'onClick' || name === 'onContextMenu' || name === 'onDoubleClick';
|
|
@@ -633,12 +743,17 @@ function createEvents(store) {
|
|
|
633
743
|
if (handler) {
|
|
634
744
|
// Forward all events back to their respective handlers with the exception of click events,
|
|
635
745
|
// which must use the initial target
|
|
636
|
-
if (
|
|
746
|
+
if (!isClickEvent || internal.initialHits.includes(eventObject)) {
|
|
637
747
|
// Missed events have to come first
|
|
638
748
|
pointerMissed(event, internal.interaction.filter(object => !internal.initialHits.includes(object))); // Now call the handler
|
|
639
749
|
|
|
640
750
|
handler(data);
|
|
641
751
|
}
|
|
752
|
+
} else {
|
|
753
|
+
// Trigger onPointerMissed on all elements that have pointer over/out handlers, but not click and weren't hit
|
|
754
|
+
if (isClickEvent && internal.initialHits.includes(eventObject)) {
|
|
755
|
+
pointerMissed(event, internal.interaction.filter(object => !internal.initialHits.includes(object)));
|
|
756
|
+
}
|
|
642
757
|
}
|
|
643
758
|
}
|
|
644
759
|
});
|
|
@@ -684,6 +799,7 @@ let extend = objects => void (catalogue = { ...catalogue,
|
|
|
684
799
|
function createRenderer(roots, getEventPriority) {
|
|
685
800
|
function createInstance(type, {
|
|
686
801
|
args = [],
|
|
802
|
+
attach,
|
|
687
803
|
...props
|
|
688
804
|
}, root, hostContext, internalInstanceHandle) {
|
|
689
805
|
let name = `${type[0].toUpperCase()}${type.slice(1)}`;
|
|
@@ -700,87 +816,65 @@ function createRenderer(roots, getEventPriority) {
|
|
|
700
816
|
} // Assert that by now we have a valid root
|
|
701
817
|
|
|
702
818
|
|
|
703
|
-
if (!root || !isStore(root)) throw `No valid root for ${name}!`;
|
|
819
|
+
if (!root || !isStore(root)) throw `No valid root for ${name}!`; // Auto-attach geometries and materials
|
|
820
|
+
|
|
821
|
+
if (attach === undefined) {
|
|
822
|
+
if (name.endsWith('Geometry')) attach = 'geometry';else if (name.endsWith('Material')) attach = 'material';
|
|
823
|
+
}
|
|
704
824
|
|
|
705
825
|
if (type === 'primitive') {
|
|
706
826
|
if (props.object === undefined) throw `Primitives without 'object' are invalid!`;
|
|
707
827
|
const object = props.object;
|
|
708
828
|
instance = prepare(object, {
|
|
709
829
|
root,
|
|
830
|
+
attach,
|
|
710
831
|
primitive: true
|
|
711
832
|
});
|
|
712
833
|
} else {
|
|
713
|
-
const target = catalogue[name]
|
|
714
|
-
|
|
834
|
+
const target = catalogue[name];
|
|
835
|
+
|
|
836
|
+
if (!target) {
|
|
837
|
+
throw `${name} is not part of the THREE namespace! Did you forget to extend? See: https://github.com/pmndrs/react-three-fiber/blob/master/markdown/api.md#using-3rd-party-objects-declaratively`;
|
|
838
|
+
} // Throw if an object or literal was passed for args
|
|
839
|
+
|
|
840
|
+
|
|
841
|
+
if (!Array.isArray(args)) throw 'The args prop must be an array!'; // Instanciate new object, link it to the root
|
|
715
842
|
// Append memoized props with args so it's not forgotten
|
|
716
843
|
|
|
717
844
|
instance = prepare(new target(...args), {
|
|
718
845
|
root,
|
|
846
|
+
attach,
|
|
847
|
+
// TODO: Figure out what this is for
|
|
719
848
|
memoizedProps: {
|
|
720
849
|
args: args.length === 0 ? null : args
|
|
721
850
|
}
|
|
722
851
|
});
|
|
723
|
-
} // Auto-attach geometries and materials
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
if (!('attachFns' in props)) {
|
|
727
|
-
if (name.endsWith('Geometry')) {
|
|
728
|
-
props = {
|
|
729
|
-
attach: 'geometry',
|
|
730
|
-
...props
|
|
731
|
-
};
|
|
732
|
-
} else if (name.endsWith('Material')) {
|
|
733
|
-
props = {
|
|
734
|
-
attach: 'material',
|
|
735
|
-
...props
|
|
736
|
-
};
|
|
737
|
-
}
|
|
738
852
|
} // It should NOT call onUpdate on object instanciation, because it hasn't been added to the
|
|
739
853
|
// view yet. If the callback relies on references for instance, they won't be ready yet, this is
|
|
740
854
|
// why it passes "true" here
|
|
741
855
|
|
|
742
856
|
|
|
743
|
-
applyProps(instance, props);
|
|
857
|
+
applyProps$1(instance, props);
|
|
744
858
|
return instance;
|
|
745
859
|
}
|
|
746
860
|
|
|
747
861
|
function appendChild(parentInstance, child) {
|
|
748
|
-
let
|
|
862
|
+
let added = false;
|
|
749
863
|
|
|
750
864
|
if (child) {
|
|
751
865
|
// The attach attribute implies that the object attaches itself on the parent
|
|
752
|
-
if (child.
|
|
753
|
-
|
|
754
|
-
parentInstance[child.attachArray].push(child);
|
|
755
|
-
} else if (child.attachObject) {
|
|
756
|
-
if (!is.obj(parentInstance[child.attachObject[0]])) parentInstance[child.attachObject[0]] = {};
|
|
757
|
-
parentInstance[child.attachObject[0]][child.attachObject[1]] = child;
|
|
758
|
-
} else if (child.attach && !is.fun(child.attach)) {
|
|
759
|
-
parentInstance[child.attach] = child;
|
|
760
|
-
} else if (is.arr(child.attachFns)) {
|
|
761
|
-
const [attachFn] = child.attachFns;
|
|
762
|
-
|
|
763
|
-
if (is.str(attachFn) && is.fun(parentInstance[attachFn])) {
|
|
764
|
-
parentInstance[attachFn](child);
|
|
765
|
-
} else if (is.fun(attachFn)) {
|
|
766
|
-
attachFn(child, parentInstance);
|
|
767
|
-
}
|
|
866
|
+
if (child.__r3f.attach) {
|
|
867
|
+
attach(parentInstance, child, child.__r3f.attach);
|
|
768
868
|
} else if (child.isObject3D && parentInstance.isObject3D) {
|
|
769
869
|
// add in the usual parent-child way
|
|
770
870
|
parentInstance.add(child);
|
|
771
|
-
|
|
772
|
-
}
|
|
773
|
-
|
|
774
|
-
if (!addedAsChild) {
|
|
775
|
-
// This is for anything that used attach, and for non-Object3Ds that don't get attached to props;
|
|
776
|
-
// that is, anything that's a child in React but not a child in the scenegraph.
|
|
777
|
-
parentInstance.__r3f.objects.push(child);
|
|
778
|
-
}
|
|
871
|
+
added = true;
|
|
872
|
+
} // This is for anything that used attach, and for non-Object3Ds that don't get attached to props;
|
|
873
|
+
// that is, anything that's a child in React but not a child in the scenegraph.
|
|
779
874
|
|
|
780
|
-
if (!child.__r3f) {
|
|
781
|
-
prepare(child, {});
|
|
782
|
-
}
|
|
783
875
|
|
|
876
|
+
if (!added) parentInstance.__r3f.objects.push(child);
|
|
877
|
+
if (!child.__r3f) prepare(child, {});
|
|
784
878
|
child.__r3f.parent = parentInstance;
|
|
785
879
|
updateInstance(child);
|
|
786
880
|
invalidateInstance(child);
|
|
@@ -791,13 +885,8 @@ function createRenderer(roots, getEventPriority) {
|
|
|
791
885
|
let added = false;
|
|
792
886
|
|
|
793
887
|
if (child) {
|
|
794
|
-
if (child.
|
|
795
|
-
|
|
796
|
-
if (!is.arr(array)) parentInstance[child.attachArray] = [];
|
|
797
|
-
array.splice(array.indexOf(beforeChild), 0, child);
|
|
798
|
-
} else if (child.attachObject || child.attach && !is.fun(child.attach)) {
|
|
799
|
-
// attach and attachObject don't have an order anyway, so just append
|
|
800
|
-
return appendChild(parentInstance, child);
|
|
888
|
+
if (child.__r3f.attach) {
|
|
889
|
+
attach(parentInstance, child, child.__r3f.attach);
|
|
801
890
|
} else if (child.isObject3D && parentInstance.isObject3D) {
|
|
802
891
|
child.parent = parentInstance;
|
|
803
892
|
child.dispatchEvent({
|
|
@@ -809,14 +898,8 @@ function createRenderer(roots, getEventPriority) {
|
|
|
809
898
|
added = true;
|
|
810
899
|
}
|
|
811
900
|
|
|
812
|
-
if (!added)
|
|
813
|
-
|
|
814
|
-
}
|
|
815
|
-
|
|
816
|
-
if (!child.__r3f) {
|
|
817
|
-
prepare(child, {});
|
|
818
|
-
}
|
|
819
|
-
|
|
901
|
+
if (!added) parentInstance.__r3f.objects.push(child);
|
|
902
|
+
if (!child.__r3f) prepare(child, {});
|
|
820
903
|
child.__r3f.parent = parentInstance;
|
|
821
904
|
updateInstance(child);
|
|
822
905
|
invalidateInstance(child);
|
|
@@ -831,29 +914,13 @@ function createRenderer(roots, getEventPriority) {
|
|
|
831
914
|
if (child) {
|
|
832
915
|
var _parentInstance$__r3f, _child$__r3f2;
|
|
833
916
|
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
}
|
|
917
|
+
// Clear the parent reference
|
|
918
|
+
if (child.__r3f) child.__r3f.parent = null; // Remove child from the parents objects
|
|
837
919
|
|
|
838
|
-
if ((_parentInstance$__r3f = parentInstance.__r3f) != null && _parentInstance$__r3f.objects)
|
|
839
|
-
parentInstance.__r3f.objects = parentInstance.__r3f.objects.filter(x => x !== child);
|
|
840
|
-
} // Remove attachment
|
|
920
|
+
if ((_parentInstance$__r3f = parentInstance.__r3f) != null && _parentInstance$__r3f.objects) parentInstance.__r3f.objects = parentInstance.__r3f.objects.filter(x => x !== child); // Remove attachment
|
|
841
921
|
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
parentInstance[child.attachArray] = parentInstance[child.attachArray].filter(x => x !== child);
|
|
845
|
-
} else if (child.attachObject) {
|
|
846
|
-
delete parentInstance[child.attachObject[0]][child.attachObject[1]];
|
|
847
|
-
} else if (child.attach && !is.fun(child.attach)) {
|
|
848
|
-
parentInstance[child.attach] = null;
|
|
849
|
-
} else if (is.arr(child.attachFns)) {
|
|
850
|
-
const [, detachFn] = child.attachFns;
|
|
851
|
-
|
|
852
|
-
if (is.str(detachFn) && is.fun(parentInstance[detachFn])) {
|
|
853
|
-
parentInstance[detachFn](child);
|
|
854
|
-
} else if (is.fun(detachFn)) {
|
|
855
|
-
detachFn(child, parentInstance);
|
|
856
|
-
}
|
|
922
|
+
if (child.__r3f.attach) {
|
|
923
|
+
detach(parentInstance, child, child.__r3f.attach);
|
|
857
924
|
} else if (child.isObject3D && parentInstance.isObject3D) {
|
|
858
925
|
var _child$__r3f;
|
|
859
926
|
|
|
@@ -895,7 +962,7 @@ function createRenderer(roots, getEventPriority) {
|
|
|
895
962
|
|
|
896
963
|
|
|
897
964
|
if (shouldDispose && child.dispose && child.type !== 'Scene') {
|
|
898
|
-
|
|
965
|
+
scheduler.unstable_scheduleCallback(scheduler.unstable_IdlePriority, () => {
|
|
899
966
|
try {
|
|
900
967
|
child.dispose();
|
|
901
968
|
} catch (e) {
|
|
@@ -927,10 +994,13 @@ function createRenderer(roots, getEventPriority) {
|
|
|
927
994
|
|
|
928
995
|
instance.__r3f.objects = [];
|
|
929
996
|
removeChild(parent, instance);
|
|
930
|
-
appendChild(parent, newInstance) //
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
997
|
+
appendChild(parent, newInstance); // Re-bind event handlers
|
|
998
|
+
|
|
999
|
+
if (newInstance.raycast && newInstance.__r3f.eventCount) {
|
|
1000
|
+
const rootState = newInstance.__r3f.root.getState();
|
|
1001
|
+
|
|
1002
|
+
rootState.internal.interaction.push(newInstance);
|
|
1003
|
+
} // This evil hack switches the react-internal fiber node
|
|
934
1004
|
[fiber, fiber.alternate].forEach(fiber => {
|
|
935
1005
|
if (fiber !== null) {
|
|
936
1006
|
fiber.stateNode = newInstance;
|
|
@@ -942,7 +1012,7 @@ function createRenderer(roots, getEventPriority) {
|
|
|
942
1012
|
});
|
|
943
1013
|
}
|
|
944
1014
|
|
|
945
|
-
const reconciler = Reconciler__default[
|
|
1015
|
+
const reconciler = Reconciler__default['default']({
|
|
946
1016
|
appendChildToContainer: (parentInstance, child) => {
|
|
947
1017
|
const {
|
|
948
1018
|
container,
|
|
@@ -956,7 +1026,9 @@ function createRenderer(roots, getEventPriority) {
|
|
|
956
1026
|
insertInContainerBefore: (parentInstance, child, beforeChild) => insertBefore(getContainer(parentInstance, child).container, child, beforeChild),
|
|
957
1027
|
|
|
958
1028
|
prepareUpdate(instance, type, oldProps, newProps) {
|
|
959
|
-
if (instance.__r3f.primitive && newProps.object && newProps.object !== instance)
|
|
1029
|
+
if (instance.__r3f.primitive && newProps.object && newProps.object !== instance) {
|
|
1030
|
+
return [true];
|
|
1031
|
+
} else {
|
|
960
1032
|
// This is a data object, let's extract critical information about it
|
|
961
1033
|
const {
|
|
962
1034
|
args: argsNew = [],
|
|
@@ -967,7 +1039,9 @@ function createRenderer(roots, getEventPriority) {
|
|
|
967
1039
|
args: argsOld = [],
|
|
968
1040
|
children: cO,
|
|
969
1041
|
...restOld
|
|
970
|
-
} = oldProps; //
|
|
1042
|
+
} = oldProps; // Throw if an object or literal was passed for args
|
|
1043
|
+
|
|
1044
|
+
if (!Array.isArray(argsNew)) throw 'The args prop must be an array!'; // If it has new props or arguments, then it needs to be re-instanciated
|
|
971
1045
|
|
|
972
1046
|
if (argsNew.some((value, index) => value !== argsOld[index])) return [true]; // Create a diff-set, flag if there are any changes
|
|
973
1047
|
|
|
@@ -981,21 +1055,33 @@ function createRenderer(roots, getEventPriority) {
|
|
|
981
1055
|
commitUpdate(instance, [reconstruct, diff], type, oldProps, newProps, fiber) {
|
|
982
1056
|
// Reconstruct when args or <primitive object={...} have changes
|
|
983
1057
|
if (reconstruct) switchInstance(instance, type, newProps, fiber); // Otherwise just overwrite props
|
|
984
|
-
else applyProps(instance, diff);
|
|
1058
|
+
else applyProps$1(instance, diff);
|
|
985
1059
|
},
|
|
986
1060
|
|
|
987
1061
|
hideInstance(instance) {
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
1062
|
+
var _instance$__r3f2;
|
|
1063
|
+
|
|
1064
|
+
// Deatch while the instance is hidden
|
|
1065
|
+
const {
|
|
1066
|
+
attach: type,
|
|
1067
|
+
parent
|
|
1068
|
+
} = (_instance$__r3f2 = instance == null ? void 0 : instance.__r3f) != null ? _instance$__r3f2 : {};
|
|
1069
|
+
if (type && parent) detach(parent, instance, type);
|
|
1070
|
+
if (instance.isObject3D) instance.visible = false;
|
|
1071
|
+
invalidateInstance(instance);
|
|
992
1072
|
},
|
|
993
1073
|
|
|
994
1074
|
unhideInstance(instance, props) {
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
|
|
1075
|
+
var _instance$__r3f3;
|
|
1076
|
+
|
|
1077
|
+
// Re-attach when the instance is unhidden
|
|
1078
|
+
const {
|
|
1079
|
+
attach: type,
|
|
1080
|
+
parent
|
|
1081
|
+
} = (_instance$__r3f3 = instance == null ? void 0 : instance.__r3f) != null ? _instance$__r3f3 : {};
|
|
1082
|
+
if (type && parent) attach(parent, instance, type);
|
|
1083
|
+
if (instance.isObject3D && props.visible == null || props.visible) instance.visible = true;
|
|
1084
|
+
invalidateInstance(instance);
|
|
999
1085
|
},
|
|
1000
1086
|
|
|
1001
1087
|
createInstance,
|
|
@@ -1008,7 +1094,7 @@ function createRenderer(roots, getEventPriority) {
|
|
|
1008
1094
|
isPrimaryRenderer: false,
|
|
1009
1095
|
getCurrentEventPriority: () => getEventPriority ? getEventPriority() : constants.DefaultEventPriority,
|
|
1010
1096
|
// @ts-ignore
|
|
1011
|
-
now: is.fun(performance.now) ? performance.now : is.fun(Date.now) ? Date.now : undefined,
|
|
1097
|
+
now: typeof performance !== 'undefined' && is.fun(performance.now) ? performance.now : is.fun(Date.now) ? Date.now : undefined,
|
|
1012
1098
|
// @ts-ignore
|
|
1013
1099
|
scheduleTimeout: is.fun(setTimeout) ? setTimeout : undefined,
|
|
1014
1100
|
// @ts-ignore
|
|
@@ -1024,8 +1110,30 @@ function createRenderer(roots, getEventPriority) {
|
|
|
1024
1110
|
getRootHostContext: () => null,
|
|
1025
1111
|
getChildHostContext: parentHostContext => parentHostContext,
|
|
1026
1112
|
createTextInstance: () => {},
|
|
1027
|
-
|
|
1028
|
-
|
|
1113
|
+
|
|
1114
|
+
finalizeInitialChildren(instance) {
|
|
1115
|
+
var _instance$__r3f4;
|
|
1116
|
+
|
|
1117
|
+
// https://github.com/facebook/react/issues/20271
|
|
1118
|
+
// Returning true will trigger commitMount
|
|
1119
|
+
const localState = (_instance$__r3f4 = instance == null ? void 0 : instance.__r3f) != null ? _instance$__r3f4 : {};
|
|
1120
|
+
return !!localState.handlers;
|
|
1121
|
+
},
|
|
1122
|
+
|
|
1123
|
+
commitMount(instance)
|
|
1124
|
+
/*, type, props*/
|
|
1125
|
+
{
|
|
1126
|
+
var _instance$__r3f5;
|
|
1127
|
+
|
|
1128
|
+
// https://github.com/facebook/react/issues/20271
|
|
1129
|
+
// This will make sure events are only added once to the central container
|
|
1130
|
+
const localState = (_instance$__r3f5 = instance == null ? void 0 : instance.__r3f) != null ? _instance$__r3f5 : {};
|
|
1131
|
+
|
|
1132
|
+
if (instance.raycast && localState.handlers && localState.eventCount) {
|
|
1133
|
+
instance.__r3f.root.getState().internal.interaction.push(instance);
|
|
1134
|
+
}
|
|
1135
|
+
},
|
|
1136
|
+
|
|
1029
1137
|
shouldDeprioritizeSubtree: () => false,
|
|
1030
1138
|
prepareForCommit: () => null,
|
|
1031
1139
|
preparePortalMount: containerInfo => prepare(containerInfo),
|
|
@@ -1036,7 +1144,7 @@ function createRenderer(roots, getEventPriority) {
|
|
|
1036
1144
|
});
|
|
1037
1145
|
return {
|
|
1038
1146
|
reconciler,
|
|
1039
|
-
applyProps
|
|
1147
|
+
applyProps: applyProps$1
|
|
1040
1148
|
};
|
|
1041
1149
|
}
|
|
1042
1150
|
|
|
@@ -1075,7 +1183,7 @@ const createStore = (applyProps, invalidate, advance, props) => {
|
|
|
1075
1183
|
clock.elapsedTime = 0;
|
|
1076
1184
|
}
|
|
1077
1185
|
|
|
1078
|
-
const rootState = create__default[
|
|
1186
|
+
const rootState = create__default['default']((set, get) => {
|
|
1079
1187
|
// Create custom raycaster
|
|
1080
1188
|
const raycaster = new THREE__namespace.Raycaster();
|
|
1081
1189
|
const {
|
|
@@ -1147,18 +1255,19 @@ const createStore = (applyProps, invalidate, advance, props) => {
|
|
|
1147
1255
|
})); // Handle frame behavior in WebXR
|
|
1148
1256
|
|
|
1149
1257
|
|
|
1150
|
-
const handleXRFrame = timestamp => {
|
|
1258
|
+
const handleXRFrame = (timestamp, frame) => {
|
|
1151
1259
|
const state = get();
|
|
1152
1260
|
if (state.frameloop === 'never') return;
|
|
1153
|
-
advance(timestamp, true);
|
|
1261
|
+
advance(timestamp, true, state, frame);
|
|
1154
1262
|
}; // Toggle render switching on session
|
|
1155
1263
|
|
|
1156
1264
|
|
|
1157
1265
|
const handleSessionChange = () => {
|
|
1158
|
-
gl.xr.enabled = gl.xr.isPresenting;
|
|
1159
|
-
|
|
1266
|
+
gl.xr.enabled = gl.xr.isPresenting; // @ts-expect-error
|
|
1267
|
+
// WebXRManager's signature is incorrect.
|
|
1268
|
+
// See: https://github.com/pmndrs/react-three-fiber/pull/2017#discussion_r790134505
|
|
1160
1269
|
|
|
1161
|
-
|
|
1270
|
+
gl.xr.setAnimationLoop(gl.xr.isPresenting ? handleXRFrame : null);
|
|
1162
1271
|
}; // WebXR session manager
|
|
1163
1272
|
|
|
1164
1273
|
|
|
@@ -1239,6 +1348,9 @@ const createStore = (applyProps, invalidate, advance, props) => {
|
|
|
1239
1348
|
dpr: calculateDpr(dpr)
|
|
1240
1349
|
}
|
|
1241
1350
|
})),
|
|
1351
|
+
setFrameloop: (frameloop = 'always') => set(() => ({
|
|
1352
|
+
frameloop
|
|
1353
|
+
})),
|
|
1242
1354
|
events: {
|
|
1243
1355
|
connected: false
|
|
1244
1356
|
},
|
|
@@ -1247,6 +1359,7 @@ const createStore = (applyProps, invalidate, advance, props) => {
|
|
|
1247
1359
|
priority: 0,
|
|
1248
1360
|
frames: 0,
|
|
1249
1361
|
lastProps: props,
|
|
1362
|
+
lastEvent: /*#__PURE__*/React__namespace.createRef(),
|
|
1250
1363
|
interaction: [],
|
|
1251
1364
|
hovered: new Map(),
|
|
1252
1365
|
subscribers: [],
|
|
@@ -1303,7 +1416,7 @@ const createStore = (applyProps, invalidate, advance, props) => {
|
|
|
1303
1416
|
if (size !== oldSize || viewport.dpr !== oldDpr) {
|
|
1304
1417
|
// https://github.com/pmndrs/react-three-fiber/issues/92
|
|
1305
1418
|
// Do not mess with the camera if it belongs to the user
|
|
1306
|
-
if (!(internal.lastProps.camera instanceof THREE__namespace.Camera)) {
|
|
1419
|
+
if (!camera.manual && !(internal.lastProps.camera instanceof THREE__namespace.Camera)) {
|
|
1307
1420
|
if (isOrthographicCamera(camera)) {
|
|
1308
1421
|
camera.left = size.width / -2;
|
|
1309
1422
|
camera.right = size.width / 2;
|
|
@@ -1352,7 +1465,7 @@ function run(effects, timestamp) {
|
|
|
1352
1465
|
for (i = 0; i < effects.length; i++) effects[i](timestamp);
|
|
1353
1466
|
}
|
|
1354
1467
|
|
|
1355
|
-
function render(timestamp, state) {
|
|
1468
|
+
function render$1(timestamp, state, frame) {
|
|
1356
1469
|
// Run local effects
|
|
1357
1470
|
let delta = state.clock.getDelta(); // In frameloop='never' mode, clock times are updated using the provided timestamp
|
|
1358
1471
|
|
|
@@ -1363,7 +1476,7 @@ function render(timestamp, state) {
|
|
|
1363
1476
|
} // Call subscribers (useFrame)
|
|
1364
1477
|
|
|
1365
1478
|
|
|
1366
|
-
for (i = 0; i < state.internal.subscribers.length; i++) state.internal.subscribers[i].ref.current(state, delta); // Render content
|
|
1479
|
+
for (i = 0; i < state.internal.subscribers.length; i++) state.internal.subscribers[i].ref.current(state, delta, frame); // Render content
|
|
1367
1480
|
|
|
1368
1481
|
|
|
1369
1482
|
if (!state.internal.priority && state.gl.render) state.gl.render(state.scene, state.camera); // Decrease frame count
|
|
@@ -1387,7 +1500,9 @@ function createLoop(roots) {
|
|
|
1387
1500
|
|
|
1388
1501
|
const state = root.store.getState(); // If the frameloop is invalidated, do not run another frame
|
|
1389
1502
|
|
|
1390
|
-
if (state.internal.active && (state.frameloop === 'always' || state.internal.frames > 0) && !((_state$gl$xr = state.gl.xr) != null && _state$gl$xr.isPresenting))
|
|
1503
|
+
if (state.internal.active && (state.frameloop === 'always' || state.internal.frames > 0) && !((_state$gl$xr = state.gl.xr) != null && _state$gl$xr.isPresenting)) {
|
|
1504
|
+
repeat += render$1(timestamp, state);
|
|
1505
|
+
}
|
|
1391
1506
|
}); // Run after-effects
|
|
1392
1507
|
|
|
1393
1508
|
run(globalAfterEffects, timestamp); // Keep on looping if anything invalidates the frameloop
|
|
@@ -1412,9 +1527,9 @@ function createLoop(roots) {
|
|
|
1412
1527
|
}
|
|
1413
1528
|
}
|
|
1414
1529
|
|
|
1415
|
-
function advance(timestamp, runGlobalEffects = true, state) {
|
|
1530
|
+
function advance(timestamp, runGlobalEffects = true, state, frame) {
|
|
1416
1531
|
if (runGlobalEffects) run(globalEffects, timestamp);
|
|
1417
|
-
if (!state) roots.forEach(root => render(timestamp, root.store.getState()));else render(timestamp, state);
|
|
1532
|
+
if (!state) roots.forEach(root => render$1(timestamp, root.store.getState()));else render$1(timestamp, state, frame);
|
|
1418
1533
|
if (runGlobalEffects) run(globalAfterEffects, timestamp);
|
|
1419
1534
|
}
|
|
1420
1535
|
|
|
@@ -1479,21 +1594,209 @@ useLoader.clear = function (Proto, input) {
|
|
|
1479
1594
|
return suspendReact.clear([Proto, ...keys]);
|
|
1480
1595
|
};
|
|
1481
1596
|
|
|
1597
|
+
const roots = new Map();
|
|
1598
|
+
const {
|
|
1599
|
+
invalidate,
|
|
1600
|
+
advance
|
|
1601
|
+
} = createLoop(roots);
|
|
1602
|
+
const {
|
|
1603
|
+
reconciler,
|
|
1604
|
+
applyProps
|
|
1605
|
+
} = createRenderer(roots, getEventPriority);
|
|
1606
|
+
|
|
1607
|
+
const createRendererInstance = (gl, canvas) => {
|
|
1608
|
+
const customRenderer = typeof gl === 'function' ? gl(canvas) : gl;
|
|
1609
|
+
if (isRenderer(customRenderer)) return customRenderer;
|
|
1610
|
+
const renderer = new THREE__namespace.WebGLRenderer({
|
|
1611
|
+
powerPreference: 'high-performance',
|
|
1612
|
+
canvas: canvas,
|
|
1613
|
+
antialias: true,
|
|
1614
|
+
alpha: true,
|
|
1615
|
+
...gl
|
|
1616
|
+
}); // Set color management
|
|
1617
|
+
|
|
1618
|
+
renderer.outputEncoding = THREE__namespace.sRGBEncoding;
|
|
1619
|
+
renderer.toneMapping = THREE__namespace.ACESFilmicToneMapping; // Set gl props
|
|
1620
|
+
|
|
1621
|
+
if (gl) applyProps(renderer, gl);
|
|
1622
|
+
return renderer;
|
|
1623
|
+
};
|
|
1624
|
+
|
|
1625
|
+
function createRoot(canvas, config) {
|
|
1626
|
+
return {
|
|
1627
|
+
render: element => {
|
|
1628
|
+
var _store;
|
|
1629
|
+
|
|
1630
|
+
let {
|
|
1631
|
+
gl,
|
|
1632
|
+
size,
|
|
1633
|
+
events,
|
|
1634
|
+
onCreated,
|
|
1635
|
+
...props
|
|
1636
|
+
} = config || {}; // Allow size to take on container bounds initially
|
|
1637
|
+
|
|
1638
|
+
if (!size) {
|
|
1639
|
+
var _canvas$parentElement, _canvas$parentElement2, _canvas$parentElement3, _canvas$parentElement4;
|
|
1640
|
+
|
|
1641
|
+
size = {
|
|
1642
|
+
width: (_canvas$parentElement = (_canvas$parentElement2 = canvas.parentElement) == null ? void 0 : _canvas$parentElement2.clientWidth) != null ? _canvas$parentElement : 0,
|
|
1643
|
+
height: (_canvas$parentElement3 = (_canvas$parentElement4 = canvas.parentElement) == null ? void 0 : _canvas$parentElement4.clientHeight) != null ? _canvas$parentElement3 : 0
|
|
1644
|
+
};
|
|
1645
|
+
}
|
|
1646
|
+
|
|
1647
|
+
let root = roots.get(canvas);
|
|
1648
|
+
let fiber = root == null ? void 0 : root.fiber;
|
|
1649
|
+
let store = root == null ? void 0 : root.store;
|
|
1650
|
+
let state = (_store = store) == null ? void 0 : _store.getState();
|
|
1651
|
+
|
|
1652
|
+
if (fiber && state) {
|
|
1653
|
+
// When a root was found, see if any fundamental props must be changed or exchanged
|
|
1654
|
+
// Check pixelratio
|
|
1655
|
+
if (props.dpr !== undefined && state.viewport.dpr !== calculateDpr(props.dpr)) state.setDpr(props.dpr); // Check size
|
|
1656
|
+
|
|
1657
|
+
if (state.size.width !== size.width || state.size.height !== size.height) state.setSize(size.width, size.height); // Check frameloop
|
|
1658
|
+
|
|
1659
|
+
if (state.frameloop !== props.frameloop) state.setFrameloop(props.frameloop); // For some props we want to reset the entire root
|
|
1660
|
+
// Changes to the color-space
|
|
1661
|
+
|
|
1662
|
+
const linearChanged = props.linear !== state.internal.lastProps.linear;
|
|
1663
|
+
|
|
1664
|
+
if (linearChanged) {
|
|
1665
|
+
unmountComponentAtNode(canvas);
|
|
1666
|
+
fiber = undefined;
|
|
1667
|
+
}
|
|
1668
|
+
}
|
|
1669
|
+
|
|
1670
|
+
if (!fiber) {
|
|
1671
|
+
// If no root has been found, make one
|
|
1672
|
+
// Create gl
|
|
1673
|
+
const glRenderer = createRendererInstance(gl, canvas); // Create store
|
|
1674
|
+
|
|
1675
|
+
store = createStore(applyProps, invalidate, advance, {
|
|
1676
|
+
gl: glRenderer,
|
|
1677
|
+
size,
|
|
1678
|
+
...props
|
|
1679
|
+
});
|
|
1680
|
+
const state = store.getState(); // Create renderer
|
|
1681
|
+
|
|
1682
|
+
fiber = reconciler.createContainer(store, constants.ConcurrentRoot, false, null); // Map it
|
|
1683
|
+
|
|
1684
|
+
roots.set(canvas, {
|
|
1685
|
+
fiber,
|
|
1686
|
+
store
|
|
1687
|
+
}); // Store events internally
|
|
1688
|
+
|
|
1689
|
+
if (events) state.set({
|
|
1690
|
+
events: events(store)
|
|
1691
|
+
});
|
|
1692
|
+
}
|
|
1693
|
+
|
|
1694
|
+
if (store && fiber) {
|
|
1695
|
+
reconciler.updateContainer( /*#__PURE__*/React__namespace.createElement(Provider, {
|
|
1696
|
+
store: store,
|
|
1697
|
+
element: element,
|
|
1698
|
+
onCreated: onCreated,
|
|
1699
|
+
target: canvas
|
|
1700
|
+
}), fiber, null, () => undefined);
|
|
1701
|
+
return store;
|
|
1702
|
+
} else {
|
|
1703
|
+
throw 'Error creating root!';
|
|
1704
|
+
}
|
|
1705
|
+
},
|
|
1706
|
+
unmount: () => unmountComponentAtNode(canvas)
|
|
1707
|
+
};
|
|
1708
|
+
}
|
|
1709
|
+
|
|
1710
|
+
function render(element, canvas, config = {}) {
|
|
1711
|
+
console.warn('R3F.render is no longer supported in React 18. Use createRoot instead!');
|
|
1712
|
+
return createRoot(canvas, config).render(element);
|
|
1713
|
+
}
|
|
1714
|
+
|
|
1715
|
+
function Provider({
|
|
1716
|
+
store,
|
|
1717
|
+
element,
|
|
1718
|
+
onCreated,
|
|
1719
|
+
target
|
|
1720
|
+
}) {
|
|
1721
|
+
React__namespace.useEffect(() => {
|
|
1722
|
+
const state = store.getState(); // Flag the canvas active, rendering will now begin
|
|
1723
|
+
|
|
1724
|
+
state.set(state => ({
|
|
1725
|
+
internal: { ...state.internal,
|
|
1726
|
+
active: true
|
|
1727
|
+
}
|
|
1728
|
+
})); // Connect events
|
|
1729
|
+
|
|
1730
|
+
state.events.connect == null ? void 0 : state.events.connect(target); // Notifiy that init is completed, the scene graph exists, but nothing has yet rendered
|
|
1731
|
+
|
|
1732
|
+
if (onCreated) onCreated(state); // eslint-disable-next-line react-hooks/exhaustive-deps
|
|
1733
|
+
}, []);
|
|
1734
|
+
return /*#__PURE__*/React__namespace.createElement(context.Provider, {
|
|
1735
|
+
value: store
|
|
1736
|
+
}, element);
|
|
1737
|
+
}
|
|
1738
|
+
|
|
1739
|
+
function unmountComponentAtNode(canvas, callback) {
|
|
1740
|
+
const root = roots.get(canvas);
|
|
1741
|
+
const fiber = root == null ? void 0 : root.fiber;
|
|
1742
|
+
|
|
1743
|
+
if (fiber) {
|
|
1744
|
+
const state = root == null ? void 0 : root.store.getState();
|
|
1745
|
+
if (state) state.internal.active = false;
|
|
1746
|
+
reconciler.updateContainer(null, fiber, null, () => {
|
|
1747
|
+
if (state) {
|
|
1748
|
+
setTimeout(() => {
|
|
1749
|
+
try {
|
|
1750
|
+
var _state$gl, _state$gl$renderLists, _state$gl2, _state$gl3;
|
|
1751
|
+
|
|
1752
|
+
state.events.disconnect == null ? void 0 : state.events.disconnect();
|
|
1753
|
+
(_state$gl = state.gl) == null ? void 0 : (_state$gl$renderLists = _state$gl.renderLists) == null ? void 0 : _state$gl$renderLists.dispose == null ? void 0 : _state$gl$renderLists.dispose();
|
|
1754
|
+
(_state$gl2 = state.gl) == null ? void 0 : _state$gl2.forceContextLoss == null ? void 0 : _state$gl2.forceContextLoss();
|
|
1755
|
+
if ((_state$gl3 = state.gl) != null && _state$gl3.xr) state.internal.xr.disconnect();
|
|
1756
|
+
dispose(state);
|
|
1757
|
+
roots.delete(canvas);
|
|
1758
|
+
if (callback) callback(canvas);
|
|
1759
|
+
} catch (e) {
|
|
1760
|
+
/* ... */
|
|
1761
|
+
}
|
|
1762
|
+
}, 500);
|
|
1763
|
+
}
|
|
1764
|
+
});
|
|
1765
|
+
}
|
|
1766
|
+
}
|
|
1767
|
+
|
|
1768
|
+
const act = React__namespace.unstable_act;
|
|
1769
|
+
|
|
1770
|
+
function createPortal(children, container) {
|
|
1771
|
+
return reconciler.createPortal(children, container, null, null);
|
|
1772
|
+
}
|
|
1773
|
+
|
|
1774
|
+
reconciler.injectIntoDevTools({
|
|
1775
|
+
bundleType: 0 ,
|
|
1776
|
+
rendererPackageName: '@react-three/fiber',
|
|
1777
|
+
version: '18.0.0'
|
|
1778
|
+
});
|
|
1779
|
+
|
|
1780
|
+
exports.act = act;
|
|
1482
1781
|
exports.addAfterEffect = addAfterEffect;
|
|
1483
1782
|
exports.addEffect = addEffect;
|
|
1484
1783
|
exports.addTail = addTail;
|
|
1485
|
-
exports.
|
|
1486
|
-
exports.
|
|
1784
|
+
exports.advance = advance;
|
|
1785
|
+
exports.applyProps = applyProps;
|
|
1487
1786
|
exports.context = context;
|
|
1488
1787
|
exports.createEvents = createEvents;
|
|
1489
|
-
exports.
|
|
1490
|
-
exports.
|
|
1491
|
-
exports.createStore = createStore;
|
|
1788
|
+
exports.createPortal = createPortal;
|
|
1789
|
+
exports.createRoot = createRoot;
|
|
1492
1790
|
exports.dispose = dispose;
|
|
1493
1791
|
exports.extend = extend;
|
|
1494
|
-
exports.
|
|
1495
|
-
exports.
|
|
1792
|
+
exports.invalidate = invalidate;
|
|
1793
|
+
exports.omit = omit;
|
|
1794
|
+
exports.pick = pick;
|
|
1795
|
+
exports.reconciler = reconciler;
|
|
1796
|
+
exports.render = render;
|
|
1797
|
+
exports.roots = roots;
|
|
1496
1798
|
exports.threeTypes = threeTypes;
|
|
1799
|
+
exports.unmountComponentAtNode = unmountComponentAtNode;
|
|
1497
1800
|
exports.useFrame = useFrame;
|
|
1498
1801
|
exports.useGraph = useGraph;
|
|
1499
1802
|
exports.useLoader = useLoader;
|