iwer 0.0.1
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/build/iwer.js +4628 -0
- package/build/iwer.min.js +1 -0
- package/build/iwer.module.js +4591 -0
- package/build/iwer.module.min.js +1 -0
- package/lib/action/ActionPlayer.d.ts +75 -0
- package/lib/action/ActionPlayer.d.ts.map +1 -0
- package/lib/action/ActionPlayer.js +206 -0
- package/lib/action/ActionPlayer.js.map +1 -0
- package/lib/action/ActionRecorder.d.ts +59 -0
- package/lib/action/ActionRecorder.d.ts.map +1 -0
- package/lib/action/ActionRecorder.js +162 -0
- package/lib/action/ActionRecorder.js.map +1 -0
- package/lib/action/Capture.d.ts +3 -0
- package/lib/action/Capture.d.ts.map +1 -0
- package/lib/action/Capture.js +26907 -0
- package/lib/action/Capture.js.map +1 -0
- package/lib/device/XRController.d.ts +24 -0
- package/lib/device/XRController.d.ts.map +1 -0
- package/lib/device/XRController.js +82 -0
- package/lib/device/XRController.js.map +1 -0
- package/lib/device/XRDevice.d.ts +142 -0
- package/lib/device/XRDevice.d.ts.map +1 -0
- package/lib/device/XRDevice.js +370 -0
- package/lib/device/XRDevice.js.map +1 -0
- package/lib/device/XRHandInput.d.ts +44 -0
- package/lib/device/XRHandInput.d.ts.map +1 -0
- package/lib/device/XRHandInput.js +133 -0
- package/lib/device/XRHandInput.js.map +1 -0
- package/lib/device/XRTrackedInput.d.ts +22 -0
- package/lib/device/XRTrackedInput.d.ts.map +1 -0
- package/lib/device/XRTrackedInput.js +89 -0
- package/lib/device/XRTrackedInput.js.map +1 -0
- package/lib/device/configs/controller/meta.d.ts +6 -0
- package/lib/device/configs/controller/meta.d.ts.map +1 -0
- package/lib/device/configs/controller/meta.js +152 -0
- package/lib/device/configs/controller/meta.js.map +1 -0
- package/lib/device/configs/hand/pinch.d.ts +3 -0
- package/lib/device/configs/hand/pinch.d.ts.map +1 -0
- package/lib/device/configs/hand/pinch.js +237 -0
- package/lib/device/configs/hand/pinch.js.map +1 -0
- package/lib/device/configs/hand/point.d.ts +3 -0
- package/lib/device/configs/hand/point.d.ts.map +1 -0
- package/lib/device/configs/hand/point.js +236 -0
- package/lib/device/configs/hand/point.js.map +1 -0
- package/lib/device/configs/hand/relaxed.d.ts +3 -0
- package/lib/device/configs/hand/relaxed.d.ts.map +1 -0
- package/lib/device/configs/hand/relaxed.js +236 -0
- package/lib/device/configs/hand/relaxed.js.map +1 -0
- package/lib/device/configs/headset/meta.d.ts +6 -0
- package/lib/device/configs/headset/meta.d.ts.map +1 -0
- package/lib/device/configs/headset/meta.js +99 -0
- package/lib/device/configs/headset/meta.js.map +1 -0
- package/lib/device/controllers.d.ts +31 -0
- package/lib/device/controllers.d.ts.map +1 -0
- package/lib/device/controllers.js +8 -0
- package/lib/device/controllers.js.map +1 -0
- package/lib/events/XRInputSourceEvent.d.ts +16 -0
- package/lib/events/XRInputSourceEvent.d.ts.map +1 -0
- package/lib/events/XRInputSourceEvent.js +14 -0
- package/lib/events/XRInputSourceEvent.js.map +1 -0
- package/lib/events/XRInputSourcesChangeEvent.d.ts +18 -0
- package/lib/events/XRInputSourcesChangeEvent.d.ts.map +1 -0
- package/lib/events/XRInputSourcesChangeEvent.js +18 -0
- package/lib/events/XRInputSourcesChangeEvent.js.map +1 -0
- package/lib/events/XRReferenceSpaceEvent.d.ts +16 -0
- package/lib/events/XRReferenceSpaceEvent.d.ts.map +1 -0
- package/lib/events/XRReferenceSpaceEvent.js +11 -0
- package/lib/events/XRReferenceSpaceEvent.js.map +1 -0
- package/lib/events/XRSessionEvent.d.ts +13 -0
- package/lib/events/XRSessionEvent.d.ts.map +1 -0
- package/lib/events/XRSessionEvent.js +10 -0
- package/lib/events/XRSessionEvent.js.map +1 -0
- package/lib/frameloop/XRFrame.d.ts +28 -0
- package/lib/frameloop/XRFrame.d.ts.map +1 -0
- package/lib/frameloop/XRFrame.js +117 -0
- package/lib/frameloop/XRFrame.js.map +1 -0
- package/lib/gamepad/Gamepad.d.ts +72 -0
- package/lib/gamepad/Gamepad.d.ts.map +1 -0
- package/lib/gamepad/Gamepad.js +126 -0
- package/lib/gamepad/Gamepad.js.map +1 -0
- package/lib/index.d.ts +24 -0
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +36 -0
- package/lib/index.js.map +1 -0
- package/lib/initialization/XRSystem.d.ts +13 -0
- package/lib/initialization/XRSystem.d.ts.map +1 -0
- package/lib/initialization/XRSystem.js +65 -0
- package/lib/initialization/XRSystem.js.map +1 -0
- package/lib/input/XRHand.d.ts +31 -0
- package/lib/input/XRHand.d.ts.map +1 -0
- package/lib/input/XRHand.js +31 -0
- package/lib/input/XRHand.js.map +1 -0
- package/lib/input/XRInputSource.d.ts +37 -0
- package/lib/input/XRInputSource.d.ts.map +1 -0
- package/lib/input/XRInputSource.js +51 -0
- package/lib/input/XRInputSource.js.map +1 -0
- package/lib/input/XRInputSourceArray.d.ts +11 -0
- package/lib/input/XRInputSourceArray.d.ts.map +1 -0
- package/lib/input/XRInputSourceArray.js +17 -0
- package/lib/input/XRInputSourceArray.js.map +1 -0
- package/lib/layers/XRWebGLLayer.d.ts +31 -0
- package/lib/layers/XRWebGLLayer.d.ts.map +1 -0
- package/lib/layers/XRWebGLLayer.js +67 -0
- package/lib/layers/XRWebGLLayer.js.map +1 -0
- package/lib/pose/XRJointPose.d.ts +11 -0
- package/lib/pose/XRJointPose.d.ts.map +1 -0
- package/lib/pose/XRJointPose.js +12 -0
- package/lib/pose/XRJointPose.js.map +1 -0
- package/lib/pose/XRPose.d.ts +16 -0
- package/lib/pose/XRPose.d.ts.map +1 -0
- package/lib/pose/XRPose.js +24 -0
- package/lib/pose/XRPose.js.map +1 -0
- package/lib/pose/XRViewerPose.d.ts +12 -0
- package/lib/pose/XRViewerPose.d.ts.map +1 -0
- package/lib/pose/XRViewerPose.js +14 -0
- package/lib/pose/XRViewerPose.js.map +1 -0
- package/lib/primitives/XRRigidTransform.d.ts +17 -0
- package/lib/primitives/XRRigidTransform.d.ts.map +1 -0
- package/lib/primitives/XRRigidTransform.js +54 -0
- package/lib/primitives/XRRigidTransform.js.map +1 -0
- package/lib/session/XRRenderState.d.ts +22 -0
- package/lib/session/XRRenderState.d.ts.map +1 -0
- package/lib/session/XRRenderState.js +26 -0
- package/lib/session/XRRenderState.js.map +1 -0
- package/lib/session/XRSession.d.ts +103 -0
- package/lib/session/XRSession.d.ts.map +1 -0
- package/lib/session/XRSession.js +459 -0
- package/lib/session/XRSession.js.map +1 -0
- package/lib/spaces/XRJointSpace.d.ts +13 -0
- package/lib/spaces/XRJointSpace.d.ts.map +1 -0
- package/lib/spaces/XRJointSpace.js +12 -0
- package/lib/spaces/XRJointSpace.js.map +1 -0
- package/lib/spaces/XRReferenceSpace.d.ts +22 -0
- package/lib/spaces/XRReferenceSpace.d.ts.map +1 -0
- package/lib/spaces/XRReferenceSpace.js +42 -0
- package/lib/spaces/XRReferenceSpace.js.map +1 -0
- package/lib/spaces/XRSpace.d.ts +20 -0
- package/lib/spaces/XRSpace.d.ts.map +1 -0
- package/lib/spaces/XRSpace.js +45 -0
- package/lib/spaces/XRSpace.js.map +1 -0
- package/lib/utils/DOMPointReadOnly.d.ts +17 -0
- package/lib/utils/DOMPointReadOnly.d.ts.map +1 -0
- package/lib/utils/DOMPointReadOnly.js +26 -0
- package/lib/utils/DOMPointReadOnly.js.map +1 -0
- package/lib/utils/Math.d.ts +49 -0
- package/lib/utils/Math.d.ts.map +1 -0
- package/lib/utils/Math.js +129 -0
- package/lib/utils/Math.js.map +1 -0
- package/lib/version.d.ts +2 -0
- package/lib/version.d.ts.map +1 -0
- package/lib/version.js +2 -0
- package/lib/version.js.map +1 -0
- package/lib/views/XRView.d.ts +25 -0
- package/lib/views/XRView.d.ts.map +1 -0
- package/lib/views/XRView.js +39 -0
- package/lib/views/XRView.js.map +1 -0
- package/lib/views/XRViewport.d.ts +15 -0
- package/lib/views/XRViewport.d.ts.map +1 -0
- package/lib/views/XRViewport.js +19 -0
- package/lib/views/XRViewport.js.map +1 -0
- package/package.json +63 -0
package/build/iwer.js
ADDED
|
@@ -0,0 +1,4628 @@
|
|
|
1
|
+
(function (global, factory) {
|
|
2
|
+
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) :
|
|
3
|
+
typeof define === 'function' && define.amd ? define(['exports'], factory) :
|
|
4
|
+
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.IWER = {}));
|
|
5
|
+
})(this, (function (exports) { 'use strict';
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Common utilities
|
|
9
|
+
* @module glMatrix
|
|
10
|
+
*/
|
|
11
|
+
// Configuration Constants
|
|
12
|
+
var EPSILON = 0.000001;
|
|
13
|
+
var ARRAY_TYPE = typeof Float32Array !== 'undefined' ? Float32Array : Array;
|
|
14
|
+
if (!Math.hypot) Math.hypot = function () {
|
|
15
|
+
var y = 0,
|
|
16
|
+
i = arguments.length;
|
|
17
|
+
|
|
18
|
+
while (i--) {
|
|
19
|
+
y += arguments[i] * arguments[i];
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
return Math.sqrt(y);
|
|
23
|
+
};
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* 3x3 Matrix
|
|
27
|
+
* @module mat3
|
|
28
|
+
*/
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* Creates a new identity mat3
|
|
32
|
+
*
|
|
33
|
+
* @returns {mat3} a new 3x3 matrix
|
|
34
|
+
*/
|
|
35
|
+
|
|
36
|
+
function create$4() {
|
|
37
|
+
var out = new ARRAY_TYPE(9);
|
|
38
|
+
|
|
39
|
+
if (ARRAY_TYPE != Float32Array) {
|
|
40
|
+
out[1] = 0;
|
|
41
|
+
out[2] = 0;
|
|
42
|
+
out[3] = 0;
|
|
43
|
+
out[5] = 0;
|
|
44
|
+
out[6] = 0;
|
|
45
|
+
out[7] = 0;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
out[0] = 1;
|
|
49
|
+
out[4] = 1;
|
|
50
|
+
out[8] = 1;
|
|
51
|
+
return out;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* 4x4 Matrix<br>Format: column-major, when typed out it looks like row-major<br>The matrices are being post multiplied.
|
|
56
|
+
* @module mat4
|
|
57
|
+
*/
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* Creates a new identity mat4
|
|
61
|
+
*
|
|
62
|
+
* @returns {mat4} a new 4x4 matrix
|
|
63
|
+
*/
|
|
64
|
+
|
|
65
|
+
function create$3() {
|
|
66
|
+
var out = new ARRAY_TYPE(16);
|
|
67
|
+
|
|
68
|
+
if (ARRAY_TYPE != Float32Array) {
|
|
69
|
+
out[1] = 0;
|
|
70
|
+
out[2] = 0;
|
|
71
|
+
out[3] = 0;
|
|
72
|
+
out[4] = 0;
|
|
73
|
+
out[6] = 0;
|
|
74
|
+
out[7] = 0;
|
|
75
|
+
out[8] = 0;
|
|
76
|
+
out[9] = 0;
|
|
77
|
+
out[11] = 0;
|
|
78
|
+
out[12] = 0;
|
|
79
|
+
out[13] = 0;
|
|
80
|
+
out[14] = 0;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
out[0] = 1;
|
|
84
|
+
out[5] = 1;
|
|
85
|
+
out[10] = 1;
|
|
86
|
+
out[15] = 1;
|
|
87
|
+
return out;
|
|
88
|
+
}
|
|
89
|
+
/**
|
|
90
|
+
* Creates a new mat4 initialized with values from an existing matrix
|
|
91
|
+
*
|
|
92
|
+
* @param {ReadonlyMat4} a matrix to clone
|
|
93
|
+
* @returns {mat4} a new 4x4 matrix
|
|
94
|
+
*/
|
|
95
|
+
|
|
96
|
+
function clone(a) {
|
|
97
|
+
var out = new ARRAY_TYPE(16);
|
|
98
|
+
out[0] = a[0];
|
|
99
|
+
out[1] = a[1];
|
|
100
|
+
out[2] = a[2];
|
|
101
|
+
out[3] = a[3];
|
|
102
|
+
out[4] = a[4];
|
|
103
|
+
out[5] = a[5];
|
|
104
|
+
out[6] = a[6];
|
|
105
|
+
out[7] = a[7];
|
|
106
|
+
out[8] = a[8];
|
|
107
|
+
out[9] = a[9];
|
|
108
|
+
out[10] = a[10];
|
|
109
|
+
out[11] = a[11];
|
|
110
|
+
out[12] = a[12];
|
|
111
|
+
out[13] = a[13];
|
|
112
|
+
out[14] = a[14];
|
|
113
|
+
out[15] = a[15];
|
|
114
|
+
return out;
|
|
115
|
+
}
|
|
116
|
+
/**
|
|
117
|
+
* Copy the values from one mat4 to another
|
|
118
|
+
*
|
|
119
|
+
* @param {mat4} out the receiving matrix
|
|
120
|
+
* @param {ReadonlyMat4} a the source matrix
|
|
121
|
+
* @returns {mat4} out
|
|
122
|
+
*/
|
|
123
|
+
|
|
124
|
+
function copy$3(out, a) {
|
|
125
|
+
out[0] = a[0];
|
|
126
|
+
out[1] = a[1];
|
|
127
|
+
out[2] = a[2];
|
|
128
|
+
out[3] = a[3];
|
|
129
|
+
out[4] = a[4];
|
|
130
|
+
out[5] = a[5];
|
|
131
|
+
out[6] = a[6];
|
|
132
|
+
out[7] = a[7];
|
|
133
|
+
out[8] = a[8];
|
|
134
|
+
out[9] = a[9];
|
|
135
|
+
out[10] = a[10];
|
|
136
|
+
out[11] = a[11];
|
|
137
|
+
out[12] = a[12];
|
|
138
|
+
out[13] = a[13];
|
|
139
|
+
out[14] = a[14];
|
|
140
|
+
out[15] = a[15];
|
|
141
|
+
return out;
|
|
142
|
+
}
|
|
143
|
+
/**
|
|
144
|
+
* Inverts a mat4
|
|
145
|
+
*
|
|
146
|
+
* @param {mat4} out the receiving matrix
|
|
147
|
+
* @param {ReadonlyMat4} a the source matrix
|
|
148
|
+
* @returns {mat4} out
|
|
149
|
+
*/
|
|
150
|
+
|
|
151
|
+
function invert(out, a) {
|
|
152
|
+
var a00 = a[0],
|
|
153
|
+
a01 = a[1],
|
|
154
|
+
a02 = a[2],
|
|
155
|
+
a03 = a[3];
|
|
156
|
+
var a10 = a[4],
|
|
157
|
+
a11 = a[5],
|
|
158
|
+
a12 = a[6],
|
|
159
|
+
a13 = a[7];
|
|
160
|
+
var a20 = a[8],
|
|
161
|
+
a21 = a[9],
|
|
162
|
+
a22 = a[10],
|
|
163
|
+
a23 = a[11];
|
|
164
|
+
var a30 = a[12],
|
|
165
|
+
a31 = a[13],
|
|
166
|
+
a32 = a[14],
|
|
167
|
+
a33 = a[15];
|
|
168
|
+
var b00 = a00 * a11 - a01 * a10;
|
|
169
|
+
var b01 = a00 * a12 - a02 * a10;
|
|
170
|
+
var b02 = a00 * a13 - a03 * a10;
|
|
171
|
+
var b03 = a01 * a12 - a02 * a11;
|
|
172
|
+
var b04 = a01 * a13 - a03 * a11;
|
|
173
|
+
var b05 = a02 * a13 - a03 * a12;
|
|
174
|
+
var b06 = a20 * a31 - a21 * a30;
|
|
175
|
+
var b07 = a20 * a32 - a22 * a30;
|
|
176
|
+
var b08 = a20 * a33 - a23 * a30;
|
|
177
|
+
var b09 = a21 * a32 - a22 * a31;
|
|
178
|
+
var b10 = a21 * a33 - a23 * a31;
|
|
179
|
+
var b11 = a22 * a33 - a23 * a32; // Calculate the determinant
|
|
180
|
+
|
|
181
|
+
var det = b00 * b11 - b01 * b10 + b02 * b09 + b03 * b08 - b04 * b07 + b05 * b06;
|
|
182
|
+
|
|
183
|
+
if (!det) {
|
|
184
|
+
return null;
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
det = 1.0 / det;
|
|
188
|
+
out[0] = (a11 * b11 - a12 * b10 + a13 * b09) * det;
|
|
189
|
+
out[1] = (a02 * b10 - a01 * b11 - a03 * b09) * det;
|
|
190
|
+
out[2] = (a31 * b05 - a32 * b04 + a33 * b03) * det;
|
|
191
|
+
out[3] = (a22 * b04 - a21 * b05 - a23 * b03) * det;
|
|
192
|
+
out[4] = (a12 * b08 - a10 * b11 - a13 * b07) * det;
|
|
193
|
+
out[5] = (a00 * b11 - a02 * b08 + a03 * b07) * det;
|
|
194
|
+
out[6] = (a32 * b02 - a30 * b05 - a33 * b01) * det;
|
|
195
|
+
out[7] = (a20 * b05 - a22 * b02 + a23 * b01) * det;
|
|
196
|
+
out[8] = (a10 * b10 - a11 * b08 + a13 * b06) * det;
|
|
197
|
+
out[9] = (a01 * b08 - a00 * b10 - a03 * b06) * det;
|
|
198
|
+
out[10] = (a30 * b04 - a31 * b02 + a33 * b00) * det;
|
|
199
|
+
out[11] = (a21 * b02 - a20 * b04 - a23 * b00) * det;
|
|
200
|
+
out[12] = (a11 * b07 - a10 * b09 - a12 * b06) * det;
|
|
201
|
+
out[13] = (a00 * b09 - a01 * b07 + a02 * b06) * det;
|
|
202
|
+
out[14] = (a31 * b01 - a30 * b03 - a32 * b00) * det;
|
|
203
|
+
out[15] = (a20 * b03 - a21 * b01 + a22 * b00) * det;
|
|
204
|
+
return out;
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Multiplies two mat4s
|
|
208
|
+
*
|
|
209
|
+
* @param {mat4} out the receiving matrix
|
|
210
|
+
* @param {ReadonlyMat4} a the first operand
|
|
211
|
+
* @param {ReadonlyMat4} b the second operand
|
|
212
|
+
* @returns {mat4} out
|
|
213
|
+
*/
|
|
214
|
+
|
|
215
|
+
function multiply$1(out, a, b) {
|
|
216
|
+
var a00 = a[0],
|
|
217
|
+
a01 = a[1],
|
|
218
|
+
a02 = a[2],
|
|
219
|
+
a03 = a[3];
|
|
220
|
+
var a10 = a[4],
|
|
221
|
+
a11 = a[5],
|
|
222
|
+
a12 = a[6],
|
|
223
|
+
a13 = a[7];
|
|
224
|
+
var a20 = a[8],
|
|
225
|
+
a21 = a[9],
|
|
226
|
+
a22 = a[10],
|
|
227
|
+
a23 = a[11];
|
|
228
|
+
var a30 = a[12],
|
|
229
|
+
a31 = a[13],
|
|
230
|
+
a32 = a[14],
|
|
231
|
+
a33 = a[15]; // Cache only the current line of the second matrix
|
|
232
|
+
|
|
233
|
+
var b0 = b[0],
|
|
234
|
+
b1 = b[1],
|
|
235
|
+
b2 = b[2],
|
|
236
|
+
b3 = b[3];
|
|
237
|
+
out[0] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
|
|
238
|
+
out[1] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
|
|
239
|
+
out[2] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
|
|
240
|
+
out[3] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
|
|
241
|
+
b0 = b[4];
|
|
242
|
+
b1 = b[5];
|
|
243
|
+
b2 = b[6];
|
|
244
|
+
b3 = b[7];
|
|
245
|
+
out[4] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
|
|
246
|
+
out[5] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
|
|
247
|
+
out[6] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
|
|
248
|
+
out[7] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
|
|
249
|
+
b0 = b[8];
|
|
250
|
+
b1 = b[9];
|
|
251
|
+
b2 = b[10];
|
|
252
|
+
b3 = b[11];
|
|
253
|
+
out[8] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
|
|
254
|
+
out[9] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
|
|
255
|
+
out[10] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
|
|
256
|
+
out[11] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
|
|
257
|
+
b0 = b[12];
|
|
258
|
+
b1 = b[13];
|
|
259
|
+
b2 = b[14];
|
|
260
|
+
b3 = b[15];
|
|
261
|
+
out[12] = b0 * a00 + b1 * a10 + b2 * a20 + b3 * a30;
|
|
262
|
+
out[13] = b0 * a01 + b1 * a11 + b2 * a21 + b3 * a31;
|
|
263
|
+
out[14] = b0 * a02 + b1 * a12 + b2 * a22 + b3 * a32;
|
|
264
|
+
out[15] = b0 * a03 + b1 * a13 + b2 * a23 + b3 * a33;
|
|
265
|
+
return out;
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Creates a matrix from a vector translation
|
|
269
|
+
* This is equivalent to (but much faster than):
|
|
270
|
+
*
|
|
271
|
+
* mat4.identity(dest);
|
|
272
|
+
* mat4.translate(dest, dest, vec);
|
|
273
|
+
*
|
|
274
|
+
* @param {mat4} out mat4 receiving operation result
|
|
275
|
+
* @param {ReadonlyVec3} v Translation vector
|
|
276
|
+
* @returns {mat4} out
|
|
277
|
+
*/
|
|
278
|
+
|
|
279
|
+
function fromTranslation(out, v) {
|
|
280
|
+
out[0] = 1;
|
|
281
|
+
out[1] = 0;
|
|
282
|
+
out[2] = 0;
|
|
283
|
+
out[3] = 0;
|
|
284
|
+
out[4] = 0;
|
|
285
|
+
out[5] = 1;
|
|
286
|
+
out[6] = 0;
|
|
287
|
+
out[7] = 0;
|
|
288
|
+
out[8] = 0;
|
|
289
|
+
out[9] = 0;
|
|
290
|
+
out[10] = 1;
|
|
291
|
+
out[11] = 0;
|
|
292
|
+
out[12] = v[0];
|
|
293
|
+
out[13] = v[1];
|
|
294
|
+
out[14] = v[2];
|
|
295
|
+
out[15] = 1;
|
|
296
|
+
return out;
|
|
297
|
+
}
|
|
298
|
+
/**
|
|
299
|
+
* Creates a matrix from a quaternion rotation and vector translation
|
|
300
|
+
* This is equivalent to (but much faster than):
|
|
301
|
+
*
|
|
302
|
+
* mat4.identity(dest);
|
|
303
|
+
* mat4.translate(dest, vec);
|
|
304
|
+
* let quatMat = mat4.create();
|
|
305
|
+
* quat4.toMat4(quat, quatMat);
|
|
306
|
+
* mat4.multiply(dest, quatMat);
|
|
307
|
+
*
|
|
308
|
+
* @param {mat4} out mat4 receiving operation result
|
|
309
|
+
* @param {quat4} q Rotation quaternion
|
|
310
|
+
* @param {ReadonlyVec3} v Translation vector
|
|
311
|
+
* @returns {mat4} out
|
|
312
|
+
*/
|
|
313
|
+
|
|
314
|
+
function fromRotationTranslation(out, q, v) {
|
|
315
|
+
// Quaternion math
|
|
316
|
+
var x = q[0],
|
|
317
|
+
y = q[1],
|
|
318
|
+
z = q[2],
|
|
319
|
+
w = q[3];
|
|
320
|
+
var x2 = x + x;
|
|
321
|
+
var y2 = y + y;
|
|
322
|
+
var z2 = z + z;
|
|
323
|
+
var xx = x * x2;
|
|
324
|
+
var xy = x * y2;
|
|
325
|
+
var xz = x * z2;
|
|
326
|
+
var yy = y * y2;
|
|
327
|
+
var yz = y * z2;
|
|
328
|
+
var zz = z * z2;
|
|
329
|
+
var wx = w * x2;
|
|
330
|
+
var wy = w * y2;
|
|
331
|
+
var wz = w * z2;
|
|
332
|
+
out[0] = 1 - (yy + zz);
|
|
333
|
+
out[1] = xy + wz;
|
|
334
|
+
out[2] = xz - wy;
|
|
335
|
+
out[3] = 0;
|
|
336
|
+
out[4] = xy - wz;
|
|
337
|
+
out[5] = 1 - (xx + zz);
|
|
338
|
+
out[6] = yz + wx;
|
|
339
|
+
out[7] = 0;
|
|
340
|
+
out[8] = xz + wy;
|
|
341
|
+
out[9] = yz - wx;
|
|
342
|
+
out[10] = 1 - (xx + yy);
|
|
343
|
+
out[11] = 0;
|
|
344
|
+
out[12] = v[0];
|
|
345
|
+
out[13] = v[1];
|
|
346
|
+
out[14] = v[2];
|
|
347
|
+
out[15] = 1;
|
|
348
|
+
return out;
|
|
349
|
+
}
|
|
350
|
+
/**
|
|
351
|
+
* Returns the translation vector component of a transformation
|
|
352
|
+
* matrix. If a matrix is built with fromRotationTranslation,
|
|
353
|
+
* the returned vector will be the same as the translation vector
|
|
354
|
+
* originally supplied.
|
|
355
|
+
* @param {vec3} out Vector to receive translation component
|
|
356
|
+
* @param {ReadonlyMat4} mat Matrix to be decomposed (input)
|
|
357
|
+
* @return {vec3} out
|
|
358
|
+
*/
|
|
359
|
+
|
|
360
|
+
function getTranslation(out, mat) {
|
|
361
|
+
out[0] = mat[12];
|
|
362
|
+
out[1] = mat[13];
|
|
363
|
+
out[2] = mat[14];
|
|
364
|
+
return out;
|
|
365
|
+
}
|
|
366
|
+
/**
|
|
367
|
+
* Returns the scaling factor component of a transformation
|
|
368
|
+
* matrix. If a matrix is built with fromRotationTranslationScale
|
|
369
|
+
* with a normalized Quaternion paramter, the returned vector will be
|
|
370
|
+
* the same as the scaling vector
|
|
371
|
+
* originally supplied.
|
|
372
|
+
* @param {vec3} out Vector to receive scaling factor component
|
|
373
|
+
* @param {ReadonlyMat4} mat Matrix to be decomposed (input)
|
|
374
|
+
* @return {vec3} out
|
|
375
|
+
*/
|
|
376
|
+
|
|
377
|
+
function getScaling(out, mat) {
|
|
378
|
+
var m11 = mat[0];
|
|
379
|
+
var m12 = mat[1];
|
|
380
|
+
var m13 = mat[2];
|
|
381
|
+
var m21 = mat[4];
|
|
382
|
+
var m22 = mat[5];
|
|
383
|
+
var m23 = mat[6];
|
|
384
|
+
var m31 = mat[8];
|
|
385
|
+
var m32 = mat[9];
|
|
386
|
+
var m33 = mat[10];
|
|
387
|
+
out[0] = Math.hypot(m11, m12, m13);
|
|
388
|
+
out[1] = Math.hypot(m21, m22, m23);
|
|
389
|
+
out[2] = Math.hypot(m31, m32, m33);
|
|
390
|
+
return out;
|
|
391
|
+
}
|
|
392
|
+
/**
|
|
393
|
+
* Returns a quaternion representing the rotational component
|
|
394
|
+
* of a transformation matrix. If a matrix is built with
|
|
395
|
+
* fromRotationTranslation, the returned quaternion will be the
|
|
396
|
+
* same as the quaternion originally supplied.
|
|
397
|
+
* @param {quat} out Quaternion to receive the rotation component
|
|
398
|
+
* @param {ReadonlyMat4} mat Matrix to be decomposed (input)
|
|
399
|
+
* @return {quat} out
|
|
400
|
+
*/
|
|
401
|
+
|
|
402
|
+
function getRotation(out, mat) {
|
|
403
|
+
var scaling = new ARRAY_TYPE(3);
|
|
404
|
+
getScaling(scaling, mat);
|
|
405
|
+
var is1 = 1 / scaling[0];
|
|
406
|
+
var is2 = 1 / scaling[1];
|
|
407
|
+
var is3 = 1 / scaling[2];
|
|
408
|
+
var sm11 = mat[0] * is1;
|
|
409
|
+
var sm12 = mat[1] * is2;
|
|
410
|
+
var sm13 = mat[2] * is3;
|
|
411
|
+
var sm21 = mat[4] * is1;
|
|
412
|
+
var sm22 = mat[5] * is2;
|
|
413
|
+
var sm23 = mat[6] * is3;
|
|
414
|
+
var sm31 = mat[8] * is1;
|
|
415
|
+
var sm32 = mat[9] * is2;
|
|
416
|
+
var sm33 = mat[10] * is3;
|
|
417
|
+
var trace = sm11 + sm22 + sm33;
|
|
418
|
+
var S = 0;
|
|
419
|
+
|
|
420
|
+
if (trace > 0) {
|
|
421
|
+
S = Math.sqrt(trace + 1.0) * 2;
|
|
422
|
+
out[3] = 0.25 * S;
|
|
423
|
+
out[0] = (sm23 - sm32) / S;
|
|
424
|
+
out[1] = (sm31 - sm13) / S;
|
|
425
|
+
out[2] = (sm12 - sm21) / S;
|
|
426
|
+
} else if (sm11 > sm22 && sm11 > sm33) {
|
|
427
|
+
S = Math.sqrt(1.0 + sm11 - sm22 - sm33) * 2;
|
|
428
|
+
out[3] = (sm23 - sm32) / S;
|
|
429
|
+
out[0] = 0.25 * S;
|
|
430
|
+
out[1] = (sm12 + sm21) / S;
|
|
431
|
+
out[2] = (sm31 + sm13) / S;
|
|
432
|
+
} else if (sm22 > sm33) {
|
|
433
|
+
S = Math.sqrt(1.0 + sm22 - sm11 - sm33) * 2;
|
|
434
|
+
out[3] = (sm31 - sm13) / S;
|
|
435
|
+
out[0] = (sm12 + sm21) / S;
|
|
436
|
+
out[1] = 0.25 * S;
|
|
437
|
+
out[2] = (sm23 + sm32) / S;
|
|
438
|
+
} else {
|
|
439
|
+
S = Math.sqrt(1.0 + sm33 - sm11 - sm22) * 2;
|
|
440
|
+
out[3] = (sm12 - sm21) / S;
|
|
441
|
+
out[0] = (sm31 + sm13) / S;
|
|
442
|
+
out[1] = (sm23 + sm32) / S;
|
|
443
|
+
out[2] = 0.25 * S;
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
return out;
|
|
447
|
+
}
|
|
448
|
+
/**
|
|
449
|
+
* Creates a matrix from a quaternion rotation, vector translation and vector scale
|
|
450
|
+
* This is equivalent to (but much faster than):
|
|
451
|
+
*
|
|
452
|
+
* mat4.identity(dest);
|
|
453
|
+
* mat4.translate(dest, vec);
|
|
454
|
+
* let quatMat = mat4.create();
|
|
455
|
+
* quat4.toMat4(quat, quatMat);
|
|
456
|
+
* mat4.multiply(dest, quatMat);
|
|
457
|
+
* mat4.scale(dest, scale)
|
|
458
|
+
*
|
|
459
|
+
* @param {mat4} out mat4 receiving operation result
|
|
460
|
+
* @param {quat4} q Rotation quaternion
|
|
461
|
+
* @param {ReadonlyVec3} v Translation vector
|
|
462
|
+
* @param {ReadonlyVec3} s Scaling vector
|
|
463
|
+
* @returns {mat4} out
|
|
464
|
+
*/
|
|
465
|
+
|
|
466
|
+
function fromRotationTranslationScale(out, q, v, s) {
|
|
467
|
+
// Quaternion math
|
|
468
|
+
var x = q[0],
|
|
469
|
+
y = q[1],
|
|
470
|
+
z = q[2],
|
|
471
|
+
w = q[3];
|
|
472
|
+
var x2 = x + x;
|
|
473
|
+
var y2 = y + y;
|
|
474
|
+
var z2 = z + z;
|
|
475
|
+
var xx = x * x2;
|
|
476
|
+
var xy = x * y2;
|
|
477
|
+
var xz = x * z2;
|
|
478
|
+
var yy = y * y2;
|
|
479
|
+
var yz = y * z2;
|
|
480
|
+
var zz = z * z2;
|
|
481
|
+
var wx = w * x2;
|
|
482
|
+
var wy = w * y2;
|
|
483
|
+
var wz = w * z2;
|
|
484
|
+
var sx = s[0];
|
|
485
|
+
var sy = s[1];
|
|
486
|
+
var sz = s[2];
|
|
487
|
+
out[0] = (1 - (yy + zz)) * sx;
|
|
488
|
+
out[1] = (xy + wz) * sx;
|
|
489
|
+
out[2] = (xz - wy) * sx;
|
|
490
|
+
out[3] = 0;
|
|
491
|
+
out[4] = (xy - wz) * sy;
|
|
492
|
+
out[5] = (1 - (xx + zz)) * sy;
|
|
493
|
+
out[6] = (yz + wx) * sy;
|
|
494
|
+
out[7] = 0;
|
|
495
|
+
out[8] = (xz + wy) * sz;
|
|
496
|
+
out[9] = (yz - wx) * sz;
|
|
497
|
+
out[10] = (1 - (xx + yy)) * sz;
|
|
498
|
+
out[11] = 0;
|
|
499
|
+
out[12] = v[0];
|
|
500
|
+
out[13] = v[1];
|
|
501
|
+
out[14] = v[2];
|
|
502
|
+
out[15] = 1;
|
|
503
|
+
return out;
|
|
504
|
+
}
|
|
505
|
+
/**
|
|
506
|
+
* Generates a perspective projection matrix with the given bounds.
|
|
507
|
+
* The near/far clip planes correspond to a normalized device coordinate Z range of [-1, 1],
|
|
508
|
+
* which matches WebGL/OpenGL's clip volume.
|
|
509
|
+
* Passing null/undefined/no value for far will generate infinite projection matrix.
|
|
510
|
+
*
|
|
511
|
+
* @param {mat4} out mat4 frustum matrix will be written into
|
|
512
|
+
* @param {number} fovy Vertical field of view in radians
|
|
513
|
+
* @param {number} aspect Aspect ratio. typically viewport width/height
|
|
514
|
+
* @param {number} near Near bound of the frustum
|
|
515
|
+
* @param {number} far Far bound of the frustum, can be null or Infinity
|
|
516
|
+
* @returns {mat4} out
|
|
517
|
+
*/
|
|
518
|
+
|
|
519
|
+
function perspectiveNO(out, fovy, aspect, near, far) {
|
|
520
|
+
var f = 1.0 / Math.tan(fovy / 2),
|
|
521
|
+
nf;
|
|
522
|
+
out[0] = f / aspect;
|
|
523
|
+
out[1] = 0;
|
|
524
|
+
out[2] = 0;
|
|
525
|
+
out[3] = 0;
|
|
526
|
+
out[4] = 0;
|
|
527
|
+
out[5] = f;
|
|
528
|
+
out[6] = 0;
|
|
529
|
+
out[7] = 0;
|
|
530
|
+
out[8] = 0;
|
|
531
|
+
out[9] = 0;
|
|
532
|
+
out[11] = -1;
|
|
533
|
+
out[12] = 0;
|
|
534
|
+
out[13] = 0;
|
|
535
|
+
out[15] = 0;
|
|
536
|
+
|
|
537
|
+
if (far != null && far !== Infinity) {
|
|
538
|
+
nf = 1 / (near - far);
|
|
539
|
+
out[10] = (far + near) * nf;
|
|
540
|
+
out[14] = 2 * far * near * nf;
|
|
541
|
+
} else {
|
|
542
|
+
out[10] = -1;
|
|
543
|
+
out[14] = -2 * near;
|
|
544
|
+
}
|
|
545
|
+
|
|
546
|
+
return out;
|
|
547
|
+
}
|
|
548
|
+
/**
|
|
549
|
+
* Alias for {@link mat4.perspectiveNO}
|
|
550
|
+
* @function
|
|
551
|
+
*/
|
|
552
|
+
|
|
553
|
+
var perspective = perspectiveNO;
|
|
554
|
+
|
|
555
|
+
/**
|
|
556
|
+
* 3 Dimensional Vector
|
|
557
|
+
* @module vec3
|
|
558
|
+
*/
|
|
559
|
+
|
|
560
|
+
/**
|
|
561
|
+
* Creates a new, empty vec3
|
|
562
|
+
*
|
|
563
|
+
* @returns {vec3} a new 3D vector
|
|
564
|
+
*/
|
|
565
|
+
|
|
566
|
+
function create$2() {
|
|
567
|
+
var out = new ARRAY_TYPE(3);
|
|
568
|
+
|
|
569
|
+
if (ARRAY_TYPE != Float32Array) {
|
|
570
|
+
out[0] = 0;
|
|
571
|
+
out[1] = 0;
|
|
572
|
+
out[2] = 0;
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
return out;
|
|
576
|
+
}
|
|
577
|
+
/**
|
|
578
|
+
* Calculates the length of a vec3
|
|
579
|
+
*
|
|
580
|
+
* @param {ReadonlyVec3} a vector to calculate length of
|
|
581
|
+
* @returns {Number} length of a
|
|
582
|
+
*/
|
|
583
|
+
|
|
584
|
+
function length(a) {
|
|
585
|
+
var x = a[0];
|
|
586
|
+
var y = a[1];
|
|
587
|
+
var z = a[2];
|
|
588
|
+
return Math.hypot(x, y, z);
|
|
589
|
+
}
|
|
590
|
+
/**
|
|
591
|
+
* Creates a new vec3 initialized with the given values
|
|
592
|
+
*
|
|
593
|
+
* @param {Number} x X component
|
|
594
|
+
* @param {Number} y Y component
|
|
595
|
+
* @param {Number} z Z component
|
|
596
|
+
* @returns {vec3} a new 3D vector
|
|
597
|
+
*/
|
|
598
|
+
|
|
599
|
+
function fromValues$2(x, y, z) {
|
|
600
|
+
var out = new ARRAY_TYPE(3);
|
|
601
|
+
out[0] = x;
|
|
602
|
+
out[1] = y;
|
|
603
|
+
out[2] = z;
|
|
604
|
+
return out;
|
|
605
|
+
}
|
|
606
|
+
/**
|
|
607
|
+
* Copy the values from one vec3 to another
|
|
608
|
+
*
|
|
609
|
+
* @param {vec3} out the receiving vector
|
|
610
|
+
* @param {ReadonlyVec3} a the source vector
|
|
611
|
+
* @returns {vec3} out
|
|
612
|
+
*/
|
|
613
|
+
|
|
614
|
+
function copy$2(out, a) {
|
|
615
|
+
out[0] = a[0];
|
|
616
|
+
out[1] = a[1];
|
|
617
|
+
out[2] = a[2];
|
|
618
|
+
return out;
|
|
619
|
+
}
|
|
620
|
+
/**
|
|
621
|
+
* Set the components of a vec3 to the given values
|
|
622
|
+
*
|
|
623
|
+
* @param {vec3} out the receiving vector
|
|
624
|
+
* @param {Number} x X component
|
|
625
|
+
* @param {Number} y Y component
|
|
626
|
+
* @param {Number} z Z component
|
|
627
|
+
* @returns {vec3} out
|
|
628
|
+
*/
|
|
629
|
+
|
|
630
|
+
function set$2(out, x, y, z) {
|
|
631
|
+
out[0] = x;
|
|
632
|
+
out[1] = y;
|
|
633
|
+
out[2] = z;
|
|
634
|
+
return out;
|
|
635
|
+
}
|
|
636
|
+
/**
|
|
637
|
+
* Adds two vec3's
|
|
638
|
+
*
|
|
639
|
+
* @param {vec3} out the receiving vector
|
|
640
|
+
* @param {ReadonlyVec3} a the first operand
|
|
641
|
+
* @param {ReadonlyVec3} b the second operand
|
|
642
|
+
* @returns {vec3} out
|
|
643
|
+
*/
|
|
644
|
+
|
|
645
|
+
function add(out, a, b) {
|
|
646
|
+
out[0] = a[0] + b[0];
|
|
647
|
+
out[1] = a[1] + b[1];
|
|
648
|
+
out[2] = a[2] + b[2];
|
|
649
|
+
return out;
|
|
650
|
+
}
|
|
651
|
+
/**
|
|
652
|
+
* Normalize a vec3
|
|
653
|
+
*
|
|
654
|
+
* @param {vec3} out the receiving vector
|
|
655
|
+
* @param {ReadonlyVec3} a vector to normalize
|
|
656
|
+
* @returns {vec3} out
|
|
657
|
+
*/
|
|
658
|
+
|
|
659
|
+
function normalize$2(out, a) {
|
|
660
|
+
var x = a[0];
|
|
661
|
+
var y = a[1];
|
|
662
|
+
var z = a[2];
|
|
663
|
+
var len = x * x + y * y + z * z;
|
|
664
|
+
|
|
665
|
+
if (len > 0) {
|
|
666
|
+
//TODO: evaluate use of glm_invsqrt here?
|
|
667
|
+
len = 1 / Math.sqrt(len);
|
|
668
|
+
}
|
|
669
|
+
|
|
670
|
+
out[0] = a[0] * len;
|
|
671
|
+
out[1] = a[1] * len;
|
|
672
|
+
out[2] = a[2] * len;
|
|
673
|
+
return out;
|
|
674
|
+
}
|
|
675
|
+
/**
|
|
676
|
+
* Calculates the dot product of two vec3's
|
|
677
|
+
*
|
|
678
|
+
* @param {ReadonlyVec3} a the first operand
|
|
679
|
+
* @param {ReadonlyVec3} b the second operand
|
|
680
|
+
* @returns {Number} dot product of a and b
|
|
681
|
+
*/
|
|
682
|
+
|
|
683
|
+
function dot(a, b) {
|
|
684
|
+
return a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
|
|
685
|
+
}
|
|
686
|
+
/**
|
|
687
|
+
* Computes the cross product of two vec3's
|
|
688
|
+
*
|
|
689
|
+
* @param {vec3} out the receiving vector
|
|
690
|
+
* @param {ReadonlyVec3} a the first operand
|
|
691
|
+
* @param {ReadonlyVec3} b the second operand
|
|
692
|
+
* @returns {vec3} out
|
|
693
|
+
*/
|
|
694
|
+
|
|
695
|
+
function cross(out, a, b) {
|
|
696
|
+
var ax = a[0],
|
|
697
|
+
ay = a[1],
|
|
698
|
+
az = a[2];
|
|
699
|
+
var bx = b[0],
|
|
700
|
+
by = b[1],
|
|
701
|
+
bz = b[2];
|
|
702
|
+
out[0] = ay * bz - az * by;
|
|
703
|
+
out[1] = az * bx - ax * bz;
|
|
704
|
+
out[2] = ax * by - ay * bx;
|
|
705
|
+
return out;
|
|
706
|
+
}
|
|
707
|
+
/**
|
|
708
|
+
* Performs a linear interpolation between two vec3's
|
|
709
|
+
*
|
|
710
|
+
* @param {vec3} out the receiving vector
|
|
711
|
+
* @param {ReadonlyVec3} a the first operand
|
|
712
|
+
* @param {ReadonlyVec3} b the second operand
|
|
713
|
+
* @param {Number} t interpolation amount, in the range [0-1], between the two inputs
|
|
714
|
+
* @returns {vec3} out
|
|
715
|
+
*/
|
|
716
|
+
|
|
717
|
+
function lerp(out, a, b, t) {
|
|
718
|
+
var ax = a[0];
|
|
719
|
+
var ay = a[1];
|
|
720
|
+
var az = a[2];
|
|
721
|
+
out[0] = ax + t * (b[0] - ax);
|
|
722
|
+
out[1] = ay + t * (b[1] - ay);
|
|
723
|
+
out[2] = az + t * (b[2] - az);
|
|
724
|
+
return out;
|
|
725
|
+
}
|
|
726
|
+
/**
|
|
727
|
+
* Transforms the vec3 with a quat
|
|
728
|
+
* Can also be used for dual quaternions. (Multiply it with the real part)
|
|
729
|
+
*
|
|
730
|
+
* @param {vec3} out the receiving vector
|
|
731
|
+
* @param {ReadonlyVec3} a the vector to transform
|
|
732
|
+
* @param {ReadonlyQuat} q quaternion to transform with
|
|
733
|
+
* @returns {vec3} out
|
|
734
|
+
*/
|
|
735
|
+
|
|
736
|
+
function transformQuat(out, a, q) {
|
|
737
|
+
// benchmarks: https://jsperf.com/quaternion-transform-vec3-implementations-fixed
|
|
738
|
+
var qx = q[0],
|
|
739
|
+
qy = q[1],
|
|
740
|
+
qz = q[2],
|
|
741
|
+
qw = q[3];
|
|
742
|
+
var x = a[0],
|
|
743
|
+
y = a[1],
|
|
744
|
+
z = a[2]; // var qvec = [qx, qy, qz];
|
|
745
|
+
// var uv = vec3.cross([], qvec, a);
|
|
746
|
+
|
|
747
|
+
var uvx = qy * z - qz * y,
|
|
748
|
+
uvy = qz * x - qx * z,
|
|
749
|
+
uvz = qx * y - qy * x; // var uuv = vec3.cross([], qvec, uv);
|
|
750
|
+
|
|
751
|
+
var uuvx = qy * uvz - qz * uvy,
|
|
752
|
+
uuvy = qz * uvx - qx * uvz,
|
|
753
|
+
uuvz = qx * uvy - qy * uvx; // vec3.scale(uv, uv, 2 * w);
|
|
754
|
+
|
|
755
|
+
var w2 = qw * 2;
|
|
756
|
+
uvx *= w2;
|
|
757
|
+
uvy *= w2;
|
|
758
|
+
uvz *= w2; // vec3.scale(uuv, uuv, 2);
|
|
759
|
+
|
|
760
|
+
uuvx *= 2;
|
|
761
|
+
uuvy *= 2;
|
|
762
|
+
uuvz *= 2; // return vec3.add(out, a, vec3.add(out, uv, uuv));
|
|
763
|
+
|
|
764
|
+
out[0] = x + uvx + uuvx;
|
|
765
|
+
out[1] = y + uvy + uuvy;
|
|
766
|
+
out[2] = z + uvz + uuvz;
|
|
767
|
+
return out;
|
|
768
|
+
}
|
|
769
|
+
/**
|
|
770
|
+
* Alias for {@link vec3.length}
|
|
771
|
+
* @function
|
|
772
|
+
*/
|
|
773
|
+
|
|
774
|
+
var len = length;
|
|
775
|
+
/**
|
|
776
|
+
* Perform some operation over an array of vec3s.
|
|
777
|
+
*
|
|
778
|
+
* @param {Array} a the array of vectors to iterate over
|
|
779
|
+
* @param {Number} stride Number of elements between the start of each vec3. If 0 assumes tightly packed
|
|
780
|
+
* @param {Number} offset Number of elements to skip at the beginning of the array
|
|
781
|
+
* @param {Number} count Number of vec3s to iterate over. If 0 iterates over entire array
|
|
782
|
+
* @param {Function} fn Function to call for each vector in the array
|
|
783
|
+
* @param {Object} [arg] additional argument to pass to fn
|
|
784
|
+
* @returns {Array} a
|
|
785
|
+
* @function
|
|
786
|
+
*/
|
|
787
|
+
|
|
788
|
+
(function () {
|
|
789
|
+
var vec = create$2();
|
|
790
|
+
return function (a, stride, offset, count, fn, arg) {
|
|
791
|
+
var i, l;
|
|
792
|
+
|
|
793
|
+
if (!stride) {
|
|
794
|
+
stride = 3;
|
|
795
|
+
}
|
|
796
|
+
|
|
797
|
+
if (!offset) {
|
|
798
|
+
offset = 0;
|
|
799
|
+
}
|
|
800
|
+
|
|
801
|
+
if (count) {
|
|
802
|
+
l = Math.min(count * stride + offset, a.length);
|
|
803
|
+
} else {
|
|
804
|
+
l = a.length;
|
|
805
|
+
}
|
|
806
|
+
|
|
807
|
+
for (i = offset; i < l; i += stride) {
|
|
808
|
+
vec[0] = a[i];
|
|
809
|
+
vec[1] = a[i + 1];
|
|
810
|
+
vec[2] = a[i + 2];
|
|
811
|
+
fn(vec, vec, arg);
|
|
812
|
+
a[i] = vec[0];
|
|
813
|
+
a[i + 1] = vec[1];
|
|
814
|
+
a[i + 2] = vec[2];
|
|
815
|
+
}
|
|
816
|
+
|
|
817
|
+
return a;
|
|
818
|
+
};
|
|
819
|
+
})();
|
|
820
|
+
|
|
821
|
+
/**
|
|
822
|
+
* 4 Dimensional Vector
|
|
823
|
+
* @module vec4
|
|
824
|
+
*/
|
|
825
|
+
|
|
826
|
+
/**
|
|
827
|
+
* Creates a new, empty vec4
|
|
828
|
+
*
|
|
829
|
+
* @returns {vec4} a new 4D vector
|
|
830
|
+
*/
|
|
831
|
+
|
|
832
|
+
function create$1() {
|
|
833
|
+
var out = new ARRAY_TYPE(4);
|
|
834
|
+
|
|
835
|
+
if (ARRAY_TYPE != Float32Array) {
|
|
836
|
+
out[0] = 0;
|
|
837
|
+
out[1] = 0;
|
|
838
|
+
out[2] = 0;
|
|
839
|
+
out[3] = 0;
|
|
840
|
+
}
|
|
841
|
+
|
|
842
|
+
return out;
|
|
843
|
+
}
|
|
844
|
+
/**
|
|
845
|
+
* Creates a new vec4 initialized with the given values
|
|
846
|
+
*
|
|
847
|
+
* @param {Number} x X component
|
|
848
|
+
* @param {Number} y Y component
|
|
849
|
+
* @param {Number} z Z component
|
|
850
|
+
* @param {Number} w W component
|
|
851
|
+
* @returns {vec4} a new 4D vector
|
|
852
|
+
*/
|
|
853
|
+
|
|
854
|
+
function fromValues$1(x, y, z, w) {
|
|
855
|
+
var out = new ARRAY_TYPE(4);
|
|
856
|
+
out[0] = x;
|
|
857
|
+
out[1] = y;
|
|
858
|
+
out[2] = z;
|
|
859
|
+
out[3] = w;
|
|
860
|
+
return out;
|
|
861
|
+
}
|
|
862
|
+
/**
|
|
863
|
+
* Copy the values from one vec4 to another
|
|
864
|
+
*
|
|
865
|
+
* @param {vec4} out the receiving vector
|
|
866
|
+
* @param {ReadonlyVec4} a the source vector
|
|
867
|
+
* @returns {vec4} out
|
|
868
|
+
*/
|
|
869
|
+
|
|
870
|
+
function copy$1(out, a) {
|
|
871
|
+
out[0] = a[0];
|
|
872
|
+
out[1] = a[1];
|
|
873
|
+
out[2] = a[2];
|
|
874
|
+
out[3] = a[3];
|
|
875
|
+
return out;
|
|
876
|
+
}
|
|
877
|
+
/**
|
|
878
|
+
* Set the components of a vec4 to the given values
|
|
879
|
+
*
|
|
880
|
+
* @param {vec4} out the receiving vector
|
|
881
|
+
* @param {Number} x X component
|
|
882
|
+
* @param {Number} y Y component
|
|
883
|
+
* @param {Number} z Z component
|
|
884
|
+
* @param {Number} w W component
|
|
885
|
+
* @returns {vec4} out
|
|
886
|
+
*/
|
|
887
|
+
|
|
888
|
+
function set$1(out, x, y, z, w) {
|
|
889
|
+
out[0] = x;
|
|
890
|
+
out[1] = y;
|
|
891
|
+
out[2] = z;
|
|
892
|
+
out[3] = w;
|
|
893
|
+
return out;
|
|
894
|
+
}
|
|
895
|
+
/**
|
|
896
|
+
* Normalize a vec4
|
|
897
|
+
*
|
|
898
|
+
* @param {vec4} out the receiving vector
|
|
899
|
+
* @param {ReadonlyVec4} a vector to normalize
|
|
900
|
+
* @returns {vec4} out
|
|
901
|
+
*/
|
|
902
|
+
|
|
903
|
+
function normalize$1(out, a) {
|
|
904
|
+
var x = a[0];
|
|
905
|
+
var y = a[1];
|
|
906
|
+
var z = a[2];
|
|
907
|
+
var w = a[3];
|
|
908
|
+
var len = x * x + y * y + z * z + w * w;
|
|
909
|
+
|
|
910
|
+
if (len > 0) {
|
|
911
|
+
len = 1 / Math.sqrt(len);
|
|
912
|
+
}
|
|
913
|
+
|
|
914
|
+
out[0] = x * len;
|
|
915
|
+
out[1] = y * len;
|
|
916
|
+
out[2] = z * len;
|
|
917
|
+
out[3] = w * len;
|
|
918
|
+
return out;
|
|
919
|
+
}
|
|
920
|
+
/**
|
|
921
|
+
* Perform some operation over an array of vec4s.
|
|
922
|
+
*
|
|
923
|
+
* @param {Array} a the array of vectors to iterate over
|
|
924
|
+
* @param {Number} stride Number of elements between the start of each vec4. If 0 assumes tightly packed
|
|
925
|
+
* @param {Number} offset Number of elements to skip at the beginning of the array
|
|
926
|
+
* @param {Number} count Number of vec4s to iterate over. If 0 iterates over entire array
|
|
927
|
+
* @param {Function} fn Function to call for each vector in the array
|
|
928
|
+
* @param {Object} [arg] additional argument to pass to fn
|
|
929
|
+
* @returns {Array} a
|
|
930
|
+
* @function
|
|
931
|
+
*/
|
|
932
|
+
|
|
933
|
+
(function () {
|
|
934
|
+
var vec = create$1();
|
|
935
|
+
return function (a, stride, offset, count, fn, arg) {
|
|
936
|
+
var i, l;
|
|
937
|
+
|
|
938
|
+
if (!stride) {
|
|
939
|
+
stride = 4;
|
|
940
|
+
}
|
|
941
|
+
|
|
942
|
+
if (!offset) {
|
|
943
|
+
offset = 0;
|
|
944
|
+
}
|
|
945
|
+
|
|
946
|
+
if (count) {
|
|
947
|
+
l = Math.min(count * stride + offset, a.length);
|
|
948
|
+
} else {
|
|
949
|
+
l = a.length;
|
|
950
|
+
}
|
|
951
|
+
|
|
952
|
+
for (i = offset; i < l; i += stride) {
|
|
953
|
+
vec[0] = a[i];
|
|
954
|
+
vec[1] = a[i + 1];
|
|
955
|
+
vec[2] = a[i + 2];
|
|
956
|
+
vec[3] = a[i + 3];
|
|
957
|
+
fn(vec, vec, arg);
|
|
958
|
+
a[i] = vec[0];
|
|
959
|
+
a[i + 1] = vec[1];
|
|
960
|
+
a[i + 2] = vec[2];
|
|
961
|
+
a[i + 3] = vec[3];
|
|
962
|
+
}
|
|
963
|
+
|
|
964
|
+
return a;
|
|
965
|
+
};
|
|
966
|
+
})();
|
|
967
|
+
|
|
968
|
+
/**
|
|
969
|
+
* Quaternion
|
|
970
|
+
* @module quat
|
|
971
|
+
*/
|
|
972
|
+
|
|
973
|
+
/**
|
|
974
|
+
* Creates a new identity quat
|
|
975
|
+
*
|
|
976
|
+
* @returns {quat} a new quaternion
|
|
977
|
+
*/
|
|
978
|
+
|
|
979
|
+
function create() {
|
|
980
|
+
var out = new ARRAY_TYPE(4);
|
|
981
|
+
|
|
982
|
+
if (ARRAY_TYPE != Float32Array) {
|
|
983
|
+
out[0] = 0;
|
|
984
|
+
out[1] = 0;
|
|
985
|
+
out[2] = 0;
|
|
986
|
+
}
|
|
987
|
+
|
|
988
|
+
out[3] = 1;
|
|
989
|
+
return out;
|
|
990
|
+
}
|
|
991
|
+
/**
|
|
992
|
+
* Sets a quat from the given angle and rotation axis,
|
|
993
|
+
* then returns it.
|
|
994
|
+
*
|
|
995
|
+
* @param {quat} out the receiving quaternion
|
|
996
|
+
* @param {ReadonlyVec3} axis the axis around which to rotate
|
|
997
|
+
* @param {Number} rad the angle in radians
|
|
998
|
+
* @returns {quat} out
|
|
999
|
+
**/
|
|
1000
|
+
|
|
1001
|
+
function setAxisAngle(out, axis, rad) {
|
|
1002
|
+
rad = rad * 0.5;
|
|
1003
|
+
var s = Math.sin(rad);
|
|
1004
|
+
out[0] = s * axis[0];
|
|
1005
|
+
out[1] = s * axis[1];
|
|
1006
|
+
out[2] = s * axis[2];
|
|
1007
|
+
out[3] = Math.cos(rad);
|
|
1008
|
+
return out;
|
|
1009
|
+
}
|
|
1010
|
+
/**
|
|
1011
|
+
* Multiplies two quat's
|
|
1012
|
+
*
|
|
1013
|
+
* @param {quat} out the receiving quaternion
|
|
1014
|
+
* @param {ReadonlyQuat} a the first operand
|
|
1015
|
+
* @param {ReadonlyQuat} b the second operand
|
|
1016
|
+
* @returns {quat} out
|
|
1017
|
+
*/
|
|
1018
|
+
|
|
1019
|
+
function multiply(out, a, b) {
|
|
1020
|
+
var ax = a[0],
|
|
1021
|
+
ay = a[1],
|
|
1022
|
+
az = a[2],
|
|
1023
|
+
aw = a[3];
|
|
1024
|
+
var bx = b[0],
|
|
1025
|
+
by = b[1],
|
|
1026
|
+
bz = b[2],
|
|
1027
|
+
bw = b[3];
|
|
1028
|
+
out[0] = ax * bw + aw * bx + ay * bz - az * by;
|
|
1029
|
+
out[1] = ay * bw + aw * by + az * bx - ax * bz;
|
|
1030
|
+
out[2] = az * bw + aw * bz + ax * by - ay * bx;
|
|
1031
|
+
out[3] = aw * bw - ax * bx - ay * by - az * bz;
|
|
1032
|
+
return out;
|
|
1033
|
+
}
|
|
1034
|
+
/**
|
|
1035
|
+
* Performs a spherical linear interpolation between two quat
|
|
1036
|
+
*
|
|
1037
|
+
* @param {quat} out the receiving quaternion
|
|
1038
|
+
* @param {ReadonlyQuat} a the first operand
|
|
1039
|
+
* @param {ReadonlyQuat} b the second operand
|
|
1040
|
+
* @param {Number} t interpolation amount, in the range [0-1], between the two inputs
|
|
1041
|
+
* @returns {quat} out
|
|
1042
|
+
*/
|
|
1043
|
+
|
|
1044
|
+
function slerp(out, a, b, t) {
|
|
1045
|
+
// benchmarks:
|
|
1046
|
+
// http://jsperf.com/quaternion-slerp-implementations
|
|
1047
|
+
var ax = a[0],
|
|
1048
|
+
ay = a[1],
|
|
1049
|
+
az = a[2],
|
|
1050
|
+
aw = a[3];
|
|
1051
|
+
var bx = b[0],
|
|
1052
|
+
by = b[1],
|
|
1053
|
+
bz = b[2],
|
|
1054
|
+
bw = b[3];
|
|
1055
|
+
var omega, cosom, sinom, scale0, scale1; // calc cosine
|
|
1056
|
+
|
|
1057
|
+
cosom = ax * bx + ay * by + az * bz + aw * bw; // adjust signs (if necessary)
|
|
1058
|
+
|
|
1059
|
+
if (cosom < 0.0) {
|
|
1060
|
+
cosom = -cosom;
|
|
1061
|
+
bx = -bx;
|
|
1062
|
+
by = -by;
|
|
1063
|
+
bz = -bz;
|
|
1064
|
+
bw = -bw;
|
|
1065
|
+
} // calculate coefficients
|
|
1066
|
+
|
|
1067
|
+
|
|
1068
|
+
if (1.0 - cosom > EPSILON) {
|
|
1069
|
+
// standard case (slerp)
|
|
1070
|
+
omega = Math.acos(cosom);
|
|
1071
|
+
sinom = Math.sin(omega);
|
|
1072
|
+
scale0 = Math.sin((1.0 - t) * omega) / sinom;
|
|
1073
|
+
scale1 = Math.sin(t * omega) / sinom;
|
|
1074
|
+
} else {
|
|
1075
|
+
// "from" and "to" quaternions are very close
|
|
1076
|
+
// ... so we can do a linear interpolation
|
|
1077
|
+
scale0 = 1.0 - t;
|
|
1078
|
+
scale1 = t;
|
|
1079
|
+
} // calculate final values
|
|
1080
|
+
|
|
1081
|
+
|
|
1082
|
+
out[0] = scale0 * ax + scale1 * bx;
|
|
1083
|
+
out[1] = scale0 * ay + scale1 * by;
|
|
1084
|
+
out[2] = scale0 * az + scale1 * bz;
|
|
1085
|
+
out[3] = scale0 * aw + scale1 * bw;
|
|
1086
|
+
return out;
|
|
1087
|
+
}
|
|
1088
|
+
/**
|
|
1089
|
+
* Calculates the conjugate of a quat
|
|
1090
|
+
* If the quaternion is normalized, this function is faster than quat.inverse and produces the same result.
|
|
1091
|
+
*
|
|
1092
|
+
* @param {quat} out the receiving quaternion
|
|
1093
|
+
* @param {ReadonlyQuat} a quat to calculate conjugate of
|
|
1094
|
+
* @returns {quat} out
|
|
1095
|
+
*/
|
|
1096
|
+
|
|
1097
|
+
function conjugate(out, a) {
|
|
1098
|
+
out[0] = -a[0];
|
|
1099
|
+
out[1] = -a[1];
|
|
1100
|
+
out[2] = -a[2];
|
|
1101
|
+
out[3] = a[3];
|
|
1102
|
+
return out;
|
|
1103
|
+
}
|
|
1104
|
+
/**
|
|
1105
|
+
* Creates a quaternion from the given 3x3 rotation matrix.
|
|
1106
|
+
*
|
|
1107
|
+
* NOTE: The resultant quaternion is not normalized, so you should be sure
|
|
1108
|
+
* to renormalize the quaternion yourself where necessary.
|
|
1109
|
+
*
|
|
1110
|
+
* @param {quat} out the receiving quaternion
|
|
1111
|
+
* @param {ReadonlyMat3} m rotation matrix
|
|
1112
|
+
* @returns {quat} out
|
|
1113
|
+
* @function
|
|
1114
|
+
*/
|
|
1115
|
+
|
|
1116
|
+
function fromMat3(out, m) {
|
|
1117
|
+
// Algorithm in Ken Shoemake's article in 1987 SIGGRAPH course notes
|
|
1118
|
+
// article "Quaternion Calculus and Fast Animation".
|
|
1119
|
+
var fTrace = m[0] + m[4] + m[8];
|
|
1120
|
+
var fRoot;
|
|
1121
|
+
|
|
1122
|
+
if (fTrace > 0.0) {
|
|
1123
|
+
// |w| > 1/2, may as well choose w > 1/2
|
|
1124
|
+
fRoot = Math.sqrt(fTrace + 1.0); // 2w
|
|
1125
|
+
|
|
1126
|
+
out[3] = 0.5 * fRoot;
|
|
1127
|
+
fRoot = 0.5 / fRoot; // 1/(4w)
|
|
1128
|
+
|
|
1129
|
+
out[0] = (m[5] - m[7]) * fRoot;
|
|
1130
|
+
out[1] = (m[6] - m[2]) * fRoot;
|
|
1131
|
+
out[2] = (m[1] - m[3]) * fRoot;
|
|
1132
|
+
} else {
|
|
1133
|
+
// |w| <= 1/2
|
|
1134
|
+
var i = 0;
|
|
1135
|
+
if (m[4] > m[0]) i = 1;
|
|
1136
|
+
if (m[8] > m[i * 3 + i]) i = 2;
|
|
1137
|
+
var j = (i + 1) % 3;
|
|
1138
|
+
var k = (i + 2) % 3;
|
|
1139
|
+
fRoot = Math.sqrt(m[i * 3 + i] - m[j * 3 + j] - m[k * 3 + k] + 1.0);
|
|
1140
|
+
out[i] = 0.5 * fRoot;
|
|
1141
|
+
fRoot = 0.5 / fRoot;
|
|
1142
|
+
out[3] = (m[j * 3 + k] - m[k * 3 + j]) * fRoot;
|
|
1143
|
+
out[j] = (m[j * 3 + i] + m[i * 3 + j]) * fRoot;
|
|
1144
|
+
out[k] = (m[k * 3 + i] + m[i * 3 + k]) * fRoot;
|
|
1145
|
+
}
|
|
1146
|
+
|
|
1147
|
+
return out;
|
|
1148
|
+
}
|
|
1149
|
+
/**
|
|
1150
|
+
* Creates a new quat initialized with the given values
|
|
1151
|
+
*
|
|
1152
|
+
* @param {Number} x X component
|
|
1153
|
+
* @param {Number} y Y component
|
|
1154
|
+
* @param {Number} z Z component
|
|
1155
|
+
* @param {Number} w W component
|
|
1156
|
+
* @returns {quat} a new quaternion
|
|
1157
|
+
* @function
|
|
1158
|
+
*/
|
|
1159
|
+
|
|
1160
|
+
var fromValues = fromValues$1;
|
|
1161
|
+
/**
|
|
1162
|
+
* Copy the values from one quat to another
|
|
1163
|
+
*
|
|
1164
|
+
* @param {quat} out the receiving quaternion
|
|
1165
|
+
* @param {ReadonlyQuat} a the source quaternion
|
|
1166
|
+
* @returns {quat} out
|
|
1167
|
+
* @function
|
|
1168
|
+
*/
|
|
1169
|
+
|
|
1170
|
+
var copy = copy$1;
|
|
1171
|
+
/**
|
|
1172
|
+
* Set the components of a quat to the given values
|
|
1173
|
+
*
|
|
1174
|
+
* @param {quat} out the receiving quaternion
|
|
1175
|
+
* @param {Number} x X component
|
|
1176
|
+
* @param {Number} y Y component
|
|
1177
|
+
* @param {Number} z Z component
|
|
1178
|
+
* @param {Number} w W component
|
|
1179
|
+
* @returns {quat} out
|
|
1180
|
+
* @function
|
|
1181
|
+
*/
|
|
1182
|
+
|
|
1183
|
+
var set = set$1;
|
|
1184
|
+
/**
|
|
1185
|
+
* Normalize a quat
|
|
1186
|
+
*
|
|
1187
|
+
* @param {quat} out the receiving quaternion
|
|
1188
|
+
* @param {ReadonlyQuat} a quaternion to normalize
|
|
1189
|
+
* @returns {quat} out
|
|
1190
|
+
* @function
|
|
1191
|
+
*/
|
|
1192
|
+
|
|
1193
|
+
var normalize = normalize$1;
|
|
1194
|
+
/**
|
|
1195
|
+
* Sets a quaternion to represent the shortest rotation from one
|
|
1196
|
+
* vector to another.
|
|
1197
|
+
*
|
|
1198
|
+
* Both vectors are assumed to be unit length.
|
|
1199
|
+
*
|
|
1200
|
+
* @param {quat} out the receiving quaternion.
|
|
1201
|
+
* @param {ReadonlyVec3} a the initial vector
|
|
1202
|
+
* @param {ReadonlyVec3} b the destination vector
|
|
1203
|
+
* @returns {quat} out
|
|
1204
|
+
*/
|
|
1205
|
+
|
|
1206
|
+
(function () {
|
|
1207
|
+
var tmpvec3 = create$2();
|
|
1208
|
+
var xUnitVec3 = fromValues$2(1, 0, 0);
|
|
1209
|
+
var yUnitVec3 = fromValues$2(0, 1, 0);
|
|
1210
|
+
return function (out, a, b) {
|
|
1211
|
+
var dot$1 = dot(a, b);
|
|
1212
|
+
|
|
1213
|
+
if (dot$1 < -0.999999) {
|
|
1214
|
+
cross(tmpvec3, xUnitVec3, a);
|
|
1215
|
+
if (len(tmpvec3) < 0.000001) cross(tmpvec3, yUnitVec3, a);
|
|
1216
|
+
normalize$2(tmpvec3, tmpvec3);
|
|
1217
|
+
setAxisAngle(out, tmpvec3, Math.PI);
|
|
1218
|
+
return out;
|
|
1219
|
+
} else if (dot$1 > 0.999999) {
|
|
1220
|
+
out[0] = 0;
|
|
1221
|
+
out[1] = 0;
|
|
1222
|
+
out[2] = 0;
|
|
1223
|
+
out[3] = 1;
|
|
1224
|
+
return out;
|
|
1225
|
+
} else {
|
|
1226
|
+
cross(tmpvec3, a, b);
|
|
1227
|
+
out[0] = tmpvec3[0];
|
|
1228
|
+
out[1] = tmpvec3[1];
|
|
1229
|
+
out[2] = tmpvec3[2];
|
|
1230
|
+
out[3] = 1 + dot$1;
|
|
1231
|
+
return normalize(out, out);
|
|
1232
|
+
}
|
|
1233
|
+
};
|
|
1234
|
+
})();
|
|
1235
|
+
/**
|
|
1236
|
+
* Performs a spherical linear interpolation with two control points
|
|
1237
|
+
*
|
|
1238
|
+
* @param {quat} out the receiving quaternion
|
|
1239
|
+
* @param {ReadonlyQuat} a the first operand
|
|
1240
|
+
* @param {ReadonlyQuat} b the second operand
|
|
1241
|
+
* @param {ReadonlyQuat} c the third operand
|
|
1242
|
+
* @param {ReadonlyQuat} d the fourth operand
|
|
1243
|
+
* @param {Number} t interpolation amount, in the range [0-1], between the two inputs
|
|
1244
|
+
* @returns {quat} out
|
|
1245
|
+
*/
|
|
1246
|
+
|
|
1247
|
+
(function () {
|
|
1248
|
+
var temp1 = create();
|
|
1249
|
+
var temp2 = create();
|
|
1250
|
+
return function (out, a, b, c, d, t) {
|
|
1251
|
+
slerp(temp1, a, d, t);
|
|
1252
|
+
slerp(temp2, b, c, t);
|
|
1253
|
+
slerp(out, temp1, temp2, 2 * t * (1 - t));
|
|
1254
|
+
return out;
|
|
1255
|
+
};
|
|
1256
|
+
})();
|
|
1257
|
+
/**
|
|
1258
|
+
* Sets the specified quaternion with values corresponding to the given
|
|
1259
|
+
* axes. Each axis is a vec3 and is expected to be unit length and
|
|
1260
|
+
* perpendicular to all other specified axes.
|
|
1261
|
+
*
|
|
1262
|
+
* @param {ReadonlyVec3} view the vector representing the viewing direction
|
|
1263
|
+
* @param {ReadonlyVec3} right the vector representing the local "right" direction
|
|
1264
|
+
* @param {ReadonlyVec3} up the vector representing the local "up" direction
|
|
1265
|
+
* @returns {quat} out
|
|
1266
|
+
*/
|
|
1267
|
+
|
|
1268
|
+
(function () {
|
|
1269
|
+
var matr = create$4();
|
|
1270
|
+
return function (out, view, right, up) {
|
|
1271
|
+
matr[0] = right[0];
|
|
1272
|
+
matr[3] = right[1];
|
|
1273
|
+
matr[6] = right[2];
|
|
1274
|
+
matr[1] = up[0];
|
|
1275
|
+
matr[4] = up[1];
|
|
1276
|
+
matr[7] = up[2];
|
|
1277
|
+
matr[2] = -view[0];
|
|
1278
|
+
matr[5] = -view[1];
|
|
1279
|
+
matr[8] = -view[2];
|
|
1280
|
+
return normalize(out, fromMat3(out, matr));
|
|
1281
|
+
};
|
|
1282
|
+
})();
|
|
1283
|
+
|
|
1284
|
+
const PRIVATE$k = Symbol('@immersive-web-emulation-runtime/xr-space');
|
|
1285
|
+
class XRSpace extends EventTarget {
|
|
1286
|
+
constructor(parentSpace, offsetMatrix) {
|
|
1287
|
+
super();
|
|
1288
|
+
this[PRIVATE$k] = {
|
|
1289
|
+
parentSpace,
|
|
1290
|
+
offsetMatrix: offsetMatrix ? clone(offsetMatrix) : create$3(),
|
|
1291
|
+
emulated: true,
|
|
1292
|
+
};
|
|
1293
|
+
}
|
|
1294
|
+
}
|
|
1295
|
+
class GlobalSpace extends XRSpace {
|
|
1296
|
+
constructor() {
|
|
1297
|
+
super(undefined, create$3()); // GlobalSpace has no parent
|
|
1298
|
+
}
|
|
1299
|
+
}
|
|
1300
|
+
class XRSpaceUtils {
|
|
1301
|
+
// Update the position component of the offsetMatrix of a given XRSpace
|
|
1302
|
+
static updateOffsetPosition(space, position) {
|
|
1303
|
+
const offsetMatrix = space[PRIVATE$k].offsetMatrix;
|
|
1304
|
+
fromTranslation(offsetMatrix, position);
|
|
1305
|
+
}
|
|
1306
|
+
// Update the rotation component of the offsetMatrix of a given XRSpace using a quaternion
|
|
1307
|
+
static updateOffsetQuaternion(space, quaternion) {
|
|
1308
|
+
const offsetMatrix = space[PRIVATE$k].offsetMatrix;
|
|
1309
|
+
const translation = create$2();
|
|
1310
|
+
getTranslation(translation, offsetMatrix);
|
|
1311
|
+
fromRotationTranslation(offsetMatrix, quaternion, translation);
|
|
1312
|
+
}
|
|
1313
|
+
// Update the offsetMatrix of a given XRSpace directly
|
|
1314
|
+
static updateOffsetMatrix(space, matrix) {
|
|
1315
|
+
const offsetMatrix = space[PRIVATE$k].offsetMatrix;
|
|
1316
|
+
copy$3(offsetMatrix, matrix);
|
|
1317
|
+
}
|
|
1318
|
+
// Calculate the global offset matrix for a given XRSpace
|
|
1319
|
+
static calculateGlobalOffsetMatrix(space, globalOffset = create$3()) {
|
|
1320
|
+
const parentOffset = space[PRIVATE$k].parentSpace
|
|
1321
|
+
? XRSpaceUtils.calculateGlobalOffsetMatrix(space[PRIVATE$k].parentSpace)
|
|
1322
|
+
: create$3(); // Identity matrix for GlobalSpace
|
|
1323
|
+
multiply$1(globalOffset, parentOffset, space[PRIVATE$k].offsetMatrix);
|
|
1324
|
+
return globalOffset;
|
|
1325
|
+
}
|
|
1326
|
+
}
|
|
1327
|
+
|
|
1328
|
+
/**
|
|
1329
|
+
* Wrapper class for gl-matrix vec3
|
|
1330
|
+
* Minimal interoperable interface to Vector3 in Three.js and Babylon.js
|
|
1331
|
+
*/
|
|
1332
|
+
class Vector3 {
|
|
1333
|
+
constructor(x = 0, y = 0, z = 0) {
|
|
1334
|
+
this.vec3 = fromValues$2(x, y, z);
|
|
1335
|
+
this.tempVec3 = create$2();
|
|
1336
|
+
}
|
|
1337
|
+
get x() {
|
|
1338
|
+
return this.vec3[0];
|
|
1339
|
+
}
|
|
1340
|
+
set x(value) {
|
|
1341
|
+
this.vec3[0] = value;
|
|
1342
|
+
}
|
|
1343
|
+
get y() {
|
|
1344
|
+
return this.vec3[1];
|
|
1345
|
+
}
|
|
1346
|
+
set y(value) {
|
|
1347
|
+
this.vec3[1] = value;
|
|
1348
|
+
}
|
|
1349
|
+
get z() {
|
|
1350
|
+
return this.vec3[2];
|
|
1351
|
+
}
|
|
1352
|
+
set z(value) {
|
|
1353
|
+
this.vec3[2] = value;
|
|
1354
|
+
}
|
|
1355
|
+
set(x, y, z) {
|
|
1356
|
+
set$2(this.vec3, x, y, z);
|
|
1357
|
+
return this;
|
|
1358
|
+
}
|
|
1359
|
+
clone() {
|
|
1360
|
+
return new Vector3(this.x, this.y, this.z);
|
|
1361
|
+
}
|
|
1362
|
+
copy(v) {
|
|
1363
|
+
this.x = v.x;
|
|
1364
|
+
this.y = v.y;
|
|
1365
|
+
this.z = v.z;
|
|
1366
|
+
return this;
|
|
1367
|
+
}
|
|
1368
|
+
round() {
|
|
1369
|
+
this.x = Math.round(this.x);
|
|
1370
|
+
this.y = Math.round(this.y);
|
|
1371
|
+
this.z = Math.round(this.z);
|
|
1372
|
+
return this;
|
|
1373
|
+
}
|
|
1374
|
+
normalize() {
|
|
1375
|
+
copy$2(this.tempVec3, this.vec3);
|
|
1376
|
+
normalize$2(this.vec3, this.tempVec3);
|
|
1377
|
+
return this;
|
|
1378
|
+
}
|
|
1379
|
+
add(v) {
|
|
1380
|
+
copy$2(this.tempVec3, this.vec3);
|
|
1381
|
+
add(this.vec3, this.tempVec3, v.vec3);
|
|
1382
|
+
return this;
|
|
1383
|
+
}
|
|
1384
|
+
applyQuaternion(q) {
|
|
1385
|
+
copy$2(this.tempVec3, this.vec3);
|
|
1386
|
+
transformQuat(this.vec3, this.tempVec3, q.quat);
|
|
1387
|
+
return this;
|
|
1388
|
+
}
|
|
1389
|
+
}
|
|
1390
|
+
/**
|
|
1391
|
+
* Wrapper class for gl-matrix quat4
|
|
1392
|
+
* Minimal interoperable interface to Vector3 in Three.js and Babylon.js
|
|
1393
|
+
*/
|
|
1394
|
+
class Quaternion {
|
|
1395
|
+
constructor(x = 0, y = 0, z = 0, w = 1) {
|
|
1396
|
+
this.quat = fromValues(x, y, z, w);
|
|
1397
|
+
this.tempQuat = create();
|
|
1398
|
+
}
|
|
1399
|
+
get x() {
|
|
1400
|
+
return this.quat[0];
|
|
1401
|
+
}
|
|
1402
|
+
set x(value) {
|
|
1403
|
+
this.quat[0] = value;
|
|
1404
|
+
}
|
|
1405
|
+
get y() {
|
|
1406
|
+
return this.quat[1];
|
|
1407
|
+
}
|
|
1408
|
+
set y(value) {
|
|
1409
|
+
this.quat[1] = value;
|
|
1410
|
+
}
|
|
1411
|
+
get z() {
|
|
1412
|
+
return this.quat[2];
|
|
1413
|
+
}
|
|
1414
|
+
set z(value) {
|
|
1415
|
+
this.quat[2] = value;
|
|
1416
|
+
}
|
|
1417
|
+
get w() {
|
|
1418
|
+
return this.quat[3];
|
|
1419
|
+
}
|
|
1420
|
+
set w(value) {
|
|
1421
|
+
this.quat[3] = value;
|
|
1422
|
+
}
|
|
1423
|
+
set(x, y, z, w) {
|
|
1424
|
+
set(this.quat, x, y, z, w);
|
|
1425
|
+
return this;
|
|
1426
|
+
}
|
|
1427
|
+
clone() {
|
|
1428
|
+
return new Quaternion(this.x, this.y, this.z, this.w);
|
|
1429
|
+
}
|
|
1430
|
+
copy(q) {
|
|
1431
|
+
set(this.quat, q.x, q.y, q.z, q.w);
|
|
1432
|
+
return this;
|
|
1433
|
+
}
|
|
1434
|
+
normalize() {
|
|
1435
|
+
copy(this.tempQuat, this.quat);
|
|
1436
|
+
normalize(this.quat, this.tempQuat);
|
|
1437
|
+
return this;
|
|
1438
|
+
}
|
|
1439
|
+
invert() {
|
|
1440
|
+
copy(this.tempQuat, this.quat);
|
|
1441
|
+
conjugate(this.quat, this.tempQuat);
|
|
1442
|
+
return this;
|
|
1443
|
+
}
|
|
1444
|
+
multiply(q) {
|
|
1445
|
+
copy(this.tempQuat, this.quat);
|
|
1446
|
+
multiply(this.quat, this.tempQuat, q.quat);
|
|
1447
|
+
return this;
|
|
1448
|
+
}
|
|
1449
|
+
setFromAxisAngle(axis, angle) {
|
|
1450
|
+
setAxisAngle(this.quat, axis.vec3, angle);
|
|
1451
|
+
return this;
|
|
1452
|
+
}
|
|
1453
|
+
}
|
|
1454
|
+
|
|
1455
|
+
const PRIVATE$j = Symbol('@immersive-web-emulation-runtime/gamepad');
|
|
1456
|
+
var GamepadMappingType;
|
|
1457
|
+
(function (GamepadMappingType) {
|
|
1458
|
+
GamepadMappingType["None"] = "";
|
|
1459
|
+
GamepadMappingType["Standard"] = "standard";
|
|
1460
|
+
GamepadMappingType["XRStandard"] = "xr-standard";
|
|
1461
|
+
})(GamepadMappingType || (GamepadMappingType = {}));
|
|
1462
|
+
class GamepadButton {
|
|
1463
|
+
constructor(type, eventTrigger) {
|
|
1464
|
+
this[PRIVATE$j] = {
|
|
1465
|
+
type,
|
|
1466
|
+
eventTrigger,
|
|
1467
|
+
pressed: false,
|
|
1468
|
+
touched: false,
|
|
1469
|
+
value: 0,
|
|
1470
|
+
lastFrameValue: 0,
|
|
1471
|
+
pendingValue: null,
|
|
1472
|
+
};
|
|
1473
|
+
}
|
|
1474
|
+
get pressed() {
|
|
1475
|
+
if (this[PRIVATE$j].type === 'manual') {
|
|
1476
|
+
return this[PRIVATE$j].pressed;
|
|
1477
|
+
}
|
|
1478
|
+
else {
|
|
1479
|
+
return this[PRIVATE$j].value > 0;
|
|
1480
|
+
}
|
|
1481
|
+
}
|
|
1482
|
+
get touched() {
|
|
1483
|
+
if (this[PRIVATE$j].type === 'manual') {
|
|
1484
|
+
return this[PRIVATE$j].touched;
|
|
1485
|
+
}
|
|
1486
|
+
else {
|
|
1487
|
+
return this[PRIVATE$j].touched || this.pressed;
|
|
1488
|
+
}
|
|
1489
|
+
}
|
|
1490
|
+
get value() {
|
|
1491
|
+
return this[PRIVATE$j].value;
|
|
1492
|
+
}
|
|
1493
|
+
}
|
|
1494
|
+
class EmptyGamepadButton {
|
|
1495
|
+
constructor() {
|
|
1496
|
+
this.pressed = false;
|
|
1497
|
+
this.touched = false;
|
|
1498
|
+
this.value = 0;
|
|
1499
|
+
}
|
|
1500
|
+
}
|
|
1501
|
+
class Gamepad {
|
|
1502
|
+
constructor(gamepadConfig, id = '', index = -1) {
|
|
1503
|
+
this[PRIVATE$j] = {
|
|
1504
|
+
id,
|
|
1505
|
+
index,
|
|
1506
|
+
connected: false,
|
|
1507
|
+
timestamp: performance.now(),
|
|
1508
|
+
mapping: gamepadConfig.mapping,
|
|
1509
|
+
buttonsMap: {},
|
|
1510
|
+
buttonsSequence: [],
|
|
1511
|
+
axesMap: {},
|
|
1512
|
+
axesSequence: [],
|
|
1513
|
+
hapticActuators: [],
|
|
1514
|
+
};
|
|
1515
|
+
gamepadConfig.buttons.forEach((buttonConfig) => {
|
|
1516
|
+
var _a;
|
|
1517
|
+
if (buttonConfig === null) {
|
|
1518
|
+
this[PRIVATE$j].buttonsSequence.push(null);
|
|
1519
|
+
}
|
|
1520
|
+
else {
|
|
1521
|
+
this[PRIVATE$j].buttonsSequence.push(buttonConfig.id);
|
|
1522
|
+
this[PRIVATE$j].buttonsMap[buttonConfig.id] = new GamepadButton(buttonConfig.type, (_a = buttonConfig.eventTrigger) !== null && _a !== void 0 ? _a : null);
|
|
1523
|
+
}
|
|
1524
|
+
});
|
|
1525
|
+
gamepadConfig.axes.forEach((axisConfig) => {
|
|
1526
|
+
if (axisConfig === null) {
|
|
1527
|
+
this[PRIVATE$j].axesSequence.push(null);
|
|
1528
|
+
}
|
|
1529
|
+
else {
|
|
1530
|
+
this[PRIVATE$j].axesSequence.push(axisConfig.id + axisConfig.type);
|
|
1531
|
+
if (!this[PRIVATE$j].axesMap[axisConfig.id]) {
|
|
1532
|
+
this[PRIVATE$j].axesMap[axisConfig.id] = { x: 0, y: 0 };
|
|
1533
|
+
}
|
|
1534
|
+
}
|
|
1535
|
+
});
|
|
1536
|
+
}
|
|
1537
|
+
get id() {
|
|
1538
|
+
return this[PRIVATE$j].id;
|
|
1539
|
+
}
|
|
1540
|
+
get index() {
|
|
1541
|
+
return this[PRIVATE$j].index;
|
|
1542
|
+
}
|
|
1543
|
+
get connected() {
|
|
1544
|
+
return this[PRIVATE$j].connected;
|
|
1545
|
+
}
|
|
1546
|
+
get timestamp() {
|
|
1547
|
+
return this[PRIVATE$j].timestamp;
|
|
1548
|
+
}
|
|
1549
|
+
get mapping() {
|
|
1550
|
+
return this[PRIVATE$j].mapping;
|
|
1551
|
+
}
|
|
1552
|
+
get axes() {
|
|
1553
|
+
const axes = [];
|
|
1554
|
+
this[PRIVATE$j].axesSequence.forEach((id) => {
|
|
1555
|
+
if (id === null) {
|
|
1556
|
+
axes.push(null);
|
|
1557
|
+
}
|
|
1558
|
+
else {
|
|
1559
|
+
const axisId = id.substring(0, id.length - 6);
|
|
1560
|
+
const axisType = id.substring(id.length - 6);
|
|
1561
|
+
axes.push(
|
|
1562
|
+
// if axis type is manual, then return the x value
|
|
1563
|
+
axisType === 'y-axis'
|
|
1564
|
+
? this[PRIVATE$j].axesMap[axisId].y
|
|
1565
|
+
: this[PRIVATE$j].axesMap[axisId].x);
|
|
1566
|
+
}
|
|
1567
|
+
});
|
|
1568
|
+
return axes;
|
|
1569
|
+
}
|
|
1570
|
+
get buttons() {
|
|
1571
|
+
return this[PRIVATE$j].buttonsSequence.map((id) => id === null ? new EmptyGamepadButton() : this[PRIVATE$j].buttonsMap[id]);
|
|
1572
|
+
}
|
|
1573
|
+
get hapticActuators() {
|
|
1574
|
+
return this[PRIVATE$j].hapticActuators;
|
|
1575
|
+
}
|
|
1576
|
+
get vibrationActuator() {
|
|
1577
|
+
return null;
|
|
1578
|
+
}
|
|
1579
|
+
}
|
|
1580
|
+
|
|
1581
|
+
var XRHandedness;
|
|
1582
|
+
(function (XRHandedness) {
|
|
1583
|
+
XRHandedness["None"] = "none";
|
|
1584
|
+
XRHandedness["Left"] = "left";
|
|
1585
|
+
XRHandedness["Right"] = "right";
|
|
1586
|
+
})(XRHandedness || (XRHandedness = {}));
|
|
1587
|
+
var XRTargetRayMode;
|
|
1588
|
+
(function (XRTargetRayMode) {
|
|
1589
|
+
XRTargetRayMode["Gaze"] = "gaze";
|
|
1590
|
+
XRTargetRayMode["TrackedPointer"] = "tracked-pointer";
|
|
1591
|
+
XRTargetRayMode["Screen"] = "screen";
|
|
1592
|
+
XRTargetRayMode["TransientPointer"] = "transient-pointer";
|
|
1593
|
+
})(XRTargetRayMode || (XRTargetRayMode = {}));
|
|
1594
|
+
class XRInputSourceArray extends Array {
|
|
1595
|
+
}
|
|
1596
|
+
const PRIVATE$i = Symbol('@immersive-web-emulation-runtime/xr-input-source');
|
|
1597
|
+
class XRInputSource {
|
|
1598
|
+
constructor(handedness, targetRayMode, profiles, targetRaySpace, gamepad, gripSpace, hand) {
|
|
1599
|
+
this[PRIVATE$i] = {
|
|
1600
|
+
handedness,
|
|
1601
|
+
targetRayMode,
|
|
1602
|
+
targetRaySpace,
|
|
1603
|
+
gripSpace,
|
|
1604
|
+
profiles,
|
|
1605
|
+
gamepad,
|
|
1606
|
+
hand,
|
|
1607
|
+
};
|
|
1608
|
+
}
|
|
1609
|
+
get handedness() {
|
|
1610
|
+
return this[PRIVATE$i].handedness;
|
|
1611
|
+
}
|
|
1612
|
+
get targetRayMode() {
|
|
1613
|
+
return this[PRIVATE$i].targetRayMode;
|
|
1614
|
+
}
|
|
1615
|
+
get targetRaySpace() {
|
|
1616
|
+
return this[PRIVATE$i].targetRaySpace;
|
|
1617
|
+
}
|
|
1618
|
+
get gripSpace() {
|
|
1619
|
+
return this[PRIVATE$i].gripSpace;
|
|
1620
|
+
}
|
|
1621
|
+
get profiles() {
|
|
1622
|
+
return this[PRIVATE$i].profiles;
|
|
1623
|
+
}
|
|
1624
|
+
get gamepad() {
|
|
1625
|
+
return this[PRIVATE$i].gamepad;
|
|
1626
|
+
}
|
|
1627
|
+
get hand() {
|
|
1628
|
+
return this[PRIVATE$i].hand;
|
|
1629
|
+
}
|
|
1630
|
+
}
|
|
1631
|
+
|
|
1632
|
+
class XRInputSourceEvent extends Event {
|
|
1633
|
+
constructor(type, eventInitDict) {
|
|
1634
|
+
super(type, eventInitDict);
|
|
1635
|
+
if (!eventInitDict.frame) {
|
|
1636
|
+
throw new Error('XRInputSourceEventInit.frame is required');
|
|
1637
|
+
}
|
|
1638
|
+
if (!eventInitDict.inputSource) {
|
|
1639
|
+
throw new Error('XRInputSourceEventInit.inputSource is required');
|
|
1640
|
+
}
|
|
1641
|
+
this.frame = eventInitDict.frame;
|
|
1642
|
+
this.inputSource = eventInitDict.inputSource;
|
|
1643
|
+
}
|
|
1644
|
+
}
|
|
1645
|
+
|
|
1646
|
+
const PRIVATE$h = Symbol('@immersive-web-emulation-runtime/xr-tracked-input');
|
|
1647
|
+
const DEFAULT_TRANSFORM = {
|
|
1648
|
+
[XRHandedness.Left]: {
|
|
1649
|
+
position: new Vector3(-0.25, 1.5, -0.4),
|
|
1650
|
+
quaternion: new Quaternion(),
|
|
1651
|
+
},
|
|
1652
|
+
[XRHandedness.Right]: {
|
|
1653
|
+
position: new Vector3(0.25, 1.5, -0.4),
|
|
1654
|
+
quaternion: new Quaternion(),
|
|
1655
|
+
},
|
|
1656
|
+
[XRHandedness.None]: {
|
|
1657
|
+
position: new Vector3(0.25, 1.5, -0.4),
|
|
1658
|
+
quaternion: new Quaternion(),
|
|
1659
|
+
},
|
|
1660
|
+
};
|
|
1661
|
+
class XRTrackedInput {
|
|
1662
|
+
constructor(inputSource) {
|
|
1663
|
+
this[PRIVATE$h] = {
|
|
1664
|
+
inputSource,
|
|
1665
|
+
position: DEFAULT_TRANSFORM[inputSource.handedness].position.clone(),
|
|
1666
|
+
quaternion: DEFAULT_TRANSFORM[inputSource.handedness].quaternion.clone(),
|
|
1667
|
+
connected: true,
|
|
1668
|
+
lastFrameConnected: false,
|
|
1669
|
+
inputSourceChanged: true,
|
|
1670
|
+
};
|
|
1671
|
+
}
|
|
1672
|
+
get position() {
|
|
1673
|
+
return this[PRIVATE$h].position;
|
|
1674
|
+
}
|
|
1675
|
+
get quaternion() {
|
|
1676
|
+
return this[PRIVATE$h].quaternion;
|
|
1677
|
+
}
|
|
1678
|
+
get inputSource() {
|
|
1679
|
+
return this[PRIVATE$h].inputSource;
|
|
1680
|
+
}
|
|
1681
|
+
get connected() {
|
|
1682
|
+
return this[PRIVATE$h].connected;
|
|
1683
|
+
}
|
|
1684
|
+
set connected(value) {
|
|
1685
|
+
this[PRIVATE$h].connected = value;
|
|
1686
|
+
this[PRIVATE$h].inputSource.gamepad[PRIVATE$j].connected = value;
|
|
1687
|
+
}
|
|
1688
|
+
onFrameStart(frame) {
|
|
1689
|
+
const targetRaySpace = this[PRIVATE$h].inputSource.targetRaySpace;
|
|
1690
|
+
fromRotationTranslation(targetRaySpace[PRIVATE$k].offsetMatrix, this[PRIVATE$h].quaternion.quat, this[PRIVATE$h].position.vec3);
|
|
1691
|
+
const session = frame.session;
|
|
1692
|
+
this[PRIVATE$h].inputSource.gamepad.buttons.forEach((button) => {
|
|
1693
|
+
if (button instanceof GamepadButton) {
|
|
1694
|
+
// apply pending values and record last frame values
|
|
1695
|
+
button[PRIVATE$j].lastFrameValue = button[PRIVATE$j].value;
|
|
1696
|
+
if (button[PRIVATE$j].pendingValue != null) {
|
|
1697
|
+
button[PRIVATE$j].value = button[PRIVATE$j].pendingValue;
|
|
1698
|
+
button[PRIVATE$j].pendingValue = null;
|
|
1699
|
+
}
|
|
1700
|
+
// trigger input source events
|
|
1701
|
+
if (button[PRIVATE$j].eventTrigger != null) {
|
|
1702
|
+
if (button[PRIVATE$j].lastFrameValue === 0 &&
|
|
1703
|
+
button[PRIVATE$j].value > 0) {
|
|
1704
|
+
session.dispatchEvent(new XRInputSourceEvent(button[PRIVATE$j].eventTrigger, {
|
|
1705
|
+
frame,
|
|
1706
|
+
inputSource: this[PRIVATE$h].inputSource,
|
|
1707
|
+
}));
|
|
1708
|
+
session.dispatchEvent(new XRInputSourceEvent(button[PRIVATE$j].eventTrigger + 'start', {
|
|
1709
|
+
frame,
|
|
1710
|
+
inputSource: this[PRIVATE$h].inputSource,
|
|
1711
|
+
}));
|
|
1712
|
+
}
|
|
1713
|
+
else if (button[PRIVATE$j].lastFrameValue > 0 &&
|
|
1714
|
+
button[PRIVATE$j].value === 0) {
|
|
1715
|
+
session.dispatchEvent(new XRInputSourceEvent(button[PRIVATE$j].eventTrigger + 'end', {
|
|
1716
|
+
frame,
|
|
1717
|
+
inputSource: this[PRIVATE$h].inputSource,
|
|
1718
|
+
}));
|
|
1719
|
+
}
|
|
1720
|
+
}
|
|
1721
|
+
}
|
|
1722
|
+
});
|
|
1723
|
+
this[PRIVATE$h].inputSourceChanged =
|
|
1724
|
+
this.connected !== this[PRIVATE$h].lastFrameConnected;
|
|
1725
|
+
this[PRIVATE$h].lastFrameConnected = this.connected;
|
|
1726
|
+
}
|
|
1727
|
+
}
|
|
1728
|
+
|
|
1729
|
+
class XRController extends XRTrackedInput {
|
|
1730
|
+
constructor(controllerConfig, handedness, globalSpace) {
|
|
1731
|
+
if (!controllerConfig.layout[handedness]) {
|
|
1732
|
+
throw new DOMException('Handedness not supported', 'InvalidStateError');
|
|
1733
|
+
}
|
|
1734
|
+
const targetRaySpace = new XRSpace(globalSpace);
|
|
1735
|
+
const gripSpace = controllerConfig.layout[handedness].gripOffsetMatrix
|
|
1736
|
+
? new XRSpace(targetRaySpace, controllerConfig.layout[handedness].gripOffsetMatrix)
|
|
1737
|
+
: undefined;
|
|
1738
|
+
const profiles = [
|
|
1739
|
+
controllerConfig.profileId,
|
|
1740
|
+
...controllerConfig.fallbackProfileIds,
|
|
1741
|
+
];
|
|
1742
|
+
const inputSource = new XRInputSource(handedness, XRTargetRayMode.TrackedPointer, profiles, targetRaySpace, new Gamepad(controllerConfig.layout[handedness].gamepad), gripSpace);
|
|
1743
|
+
super(inputSource);
|
|
1744
|
+
}
|
|
1745
|
+
updateButtonValue(id, value) {
|
|
1746
|
+
if (value > 1 || value < 0) {
|
|
1747
|
+
console.warn(`Out-of-range value ${value} provided for button ${id}.`);
|
|
1748
|
+
return;
|
|
1749
|
+
}
|
|
1750
|
+
const gamepadButton = this[PRIVATE$h].inputSource.gamepad[PRIVATE$j].buttonsMap[id];
|
|
1751
|
+
if (gamepadButton) {
|
|
1752
|
+
if (gamepadButton[PRIVATE$j].type === 'binary' &&
|
|
1753
|
+
value != 1 &&
|
|
1754
|
+
value != 0) {
|
|
1755
|
+
console.warn(`Non-binary value ${value} provided for binary button ${id}.`);
|
|
1756
|
+
return;
|
|
1757
|
+
}
|
|
1758
|
+
gamepadButton[PRIVATE$j].pendingValue = value;
|
|
1759
|
+
}
|
|
1760
|
+
else {
|
|
1761
|
+
console.warn(`Current controller does not have button ${id}.`);
|
|
1762
|
+
}
|
|
1763
|
+
}
|
|
1764
|
+
updateButtonTouch(id, touched) {
|
|
1765
|
+
const gamepadButton = this[PRIVATE$h].inputSource.gamepad[PRIVATE$j].buttonsMap[id];
|
|
1766
|
+
if (gamepadButton) {
|
|
1767
|
+
gamepadButton[PRIVATE$j].touched = touched;
|
|
1768
|
+
}
|
|
1769
|
+
else {
|
|
1770
|
+
console.warn(`Current controller does not have button ${id}.`);
|
|
1771
|
+
}
|
|
1772
|
+
}
|
|
1773
|
+
updateAxis(id, type, value) {
|
|
1774
|
+
if (value > 1 || value < -1) {
|
|
1775
|
+
console.warn(`Out-of-range value ${value} provided for ${id} axes.`);
|
|
1776
|
+
return;
|
|
1777
|
+
}
|
|
1778
|
+
const axesById = this[PRIVATE$h].inputSource.gamepad[PRIVATE$j].axesMap[id];
|
|
1779
|
+
if (axesById) {
|
|
1780
|
+
if (type === 'x-axis') {
|
|
1781
|
+
axesById.x = value;
|
|
1782
|
+
}
|
|
1783
|
+
else if (type === 'y-axis') {
|
|
1784
|
+
axesById.y = value;
|
|
1785
|
+
}
|
|
1786
|
+
}
|
|
1787
|
+
else {
|
|
1788
|
+
console.warn(`Current controller does not have ${id} axes.`);
|
|
1789
|
+
}
|
|
1790
|
+
}
|
|
1791
|
+
updateAxes(id, x, y) {
|
|
1792
|
+
if (x > 1 || x < -1 || y > 1 || y < -1) {
|
|
1793
|
+
console.warn(`Out-of-range value x:${x}, y:${y} provided for ${id} axes.`);
|
|
1794
|
+
return;
|
|
1795
|
+
}
|
|
1796
|
+
const axesById = this[PRIVATE$h].inputSource.gamepad[PRIVATE$j].axesMap[id];
|
|
1797
|
+
if (axesById) {
|
|
1798
|
+
axesById.x = x;
|
|
1799
|
+
axesById.y = y;
|
|
1800
|
+
}
|
|
1801
|
+
else {
|
|
1802
|
+
console.warn(`Current controller does not have ${id} axes.`);
|
|
1803
|
+
}
|
|
1804
|
+
}
|
|
1805
|
+
}
|
|
1806
|
+
|
|
1807
|
+
const PRIVATE$g = Symbol('@immersive-web-emulation-runtime/xr-view');
|
|
1808
|
+
var XREye;
|
|
1809
|
+
(function (XREye) {
|
|
1810
|
+
XREye["None"] = "none";
|
|
1811
|
+
XREye["Left"] = "left";
|
|
1812
|
+
XREye["Right"] = "right";
|
|
1813
|
+
})(XREye || (XREye = {}));
|
|
1814
|
+
class XRView {
|
|
1815
|
+
constructor(eye, projectionMatrix, transform, session) {
|
|
1816
|
+
this[PRIVATE$g] = {
|
|
1817
|
+
eye,
|
|
1818
|
+
projectionMatrix,
|
|
1819
|
+
transform,
|
|
1820
|
+
recommendedViewportScale: null,
|
|
1821
|
+
requestedViewportScale: 1.0,
|
|
1822
|
+
session,
|
|
1823
|
+
};
|
|
1824
|
+
}
|
|
1825
|
+
get eye() {
|
|
1826
|
+
return this[PRIVATE$g].eye;
|
|
1827
|
+
}
|
|
1828
|
+
get projectionMatrix() {
|
|
1829
|
+
return this[PRIVATE$g].projectionMatrix;
|
|
1830
|
+
}
|
|
1831
|
+
get transform() {
|
|
1832
|
+
return this[PRIVATE$g].transform;
|
|
1833
|
+
}
|
|
1834
|
+
get recommendedViewportScale() {
|
|
1835
|
+
return this[PRIVATE$g].recommendedViewportScale;
|
|
1836
|
+
}
|
|
1837
|
+
requestViewportScale(scale) {
|
|
1838
|
+
if (scale === null || scale <= 0 || scale > 1) {
|
|
1839
|
+
console.warn('Invalid scale value. Scale must be > 0 and <= 1.');
|
|
1840
|
+
return;
|
|
1841
|
+
}
|
|
1842
|
+
this[PRIVATE$g].requestedViewportScale = scale;
|
|
1843
|
+
}
|
|
1844
|
+
}
|
|
1845
|
+
|
|
1846
|
+
var XRHandJoint;
|
|
1847
|
+
(function (XRHandJoint) {
|
|
1848
|
+
XRHandJoint["Wrist"] = "wrist";
|
|
1849
|
+
XRHandJoint["ThumbMetacarpal"] = "thumb-metacarpal";
|
|
1850
|
+
XRHandJoint["ThumbPhalanxProximal"] = "thumb-phalanx-proximal";
|
|
1851
|
+
XRHandJoint["ThumbPhalanxDistal"] = "thumb-phalanx-distal";
|
|
1852
|
+
XRHandJoint["ThumbTip"] = "thumb-tip";
|
|
1853
|
+
XRHandJoint["IndexFingerMetacarpal"] = "index-finger-metacarpal";
|
|
1854
|
+
XRHandJoint["IndexFingerPhalanxProximal"] = "index-finger-phalanx-proximal";
|
|
1855
|
+
XRHandJoint["IndexFingerPhalanxIntermediate"] = "index-finger-phalanx-intermediate";
|
|
1856
|
+
XRHandJoint["IndexFingerPhalanxDistal"] = "index-finger-phalanx-distal";
|
|
1857
|
+
XRHandJoint["IndexFingerTip"] = "index-finger-tip";
|
|
1858
|
+
XRHandJoint["MiddleFingerMetacarpal"] = "middle-finger-metacarpal";
|
|
1859
|
+
XRHandJoint["MiddleFingerPhalanxProximal"] = "middle-finger-phalanx-proximal";
|
|
1860
|
+
XRHandJoint["MiddleFingerPhalanxIntermediate"] = "middle-finger-phalanx-intermediate";
|
|
1861
|
+
XRHandJoint["MiddleFingerPhalanxDistal"] = "middle-finger-phalanx-distal";
|
|
1862
|
+
XRHandJoint["MiddleFingerTip"] = "middle-finger-tip";
|
|
1863
|
+
XRHandJoint["RingFingerMetacarpal"] = "ring-finger-metacarpal";
|
|
1864
|
+
XRHandJoint["RingFingerPhalanxProximal"] = "ring-finger-phalanx-proximal";
|
|
1865
|
+
XRHandJoint["RingFingerPhalanxIntermediate"] = "ring-finger-phalanx-intermediate";
|
|
1866
|
+
XRHandJoint["RingFingerPhalanxDistal"] = "ring-finger-phalanx-distal";
|
|
1867
|
+
XRHandJoint["RingFingerTip"] = "ring-finger-tip";
|
|
1868
|
+
XRHandJoint["PinkyFingerMetacarpal"] = "pinky-finger-metacarpal";
|
|
1869
|
+
XRHandJoint["PinkyFingerPhalanxProximal"] = "pinky-finger-phalanx-proximal";
|
|
1870
|
+
XRHandJoint["PinkyFingerPhalanxIntermediate"] = "pinky-finger-phalanx-intermediate";
|
|
1871
|
+
XRHandJoint["PinkyFingerPhalanxDistal"] = "pinky-finger-phalanx-distal";
|
|
1872
|
+
XRHandJoint["PinkyFingerTip"] = "pinky-finger-tip";
|
|
1873
|
+
})(XRHandJoint || (XRHandJoint = {}));
|
|
1874
|
+
class XRHand extends Map {
|
|
1875
|
+
}
|
|
1876
|
+
|
|
1877
|
+
const PRIVATE$f = Symbol('@immersive-web-emulation-runtime/xr-joint-space');
|
|
1878
|
+
class XRJointSpace extends XRSpace {
|
|
1879
|
+
constructor(jointName, parentSpace, offsetMatrix) {
|
|
1880
|
+
super(parentSpace, offsetMatrix);
|
|
1881
|
+
this[PRIVATE$f] = { jointName, radius: 0 };
|
|
1882
|
+
}
|
|
1883
|
+
get jointName() {
|
|
1884
|
+
return this[PRIVATE$f].jointName;
|
|
1885
|
+
}
|
|
1886
|
+
}
|
|
1887
|
+
|
|
1888
|
+
const pinchHandPose = {
|
|
1889
|
+
jointTransforms: {
|
|
1890
|
+
wrist: {
|
|
1891
|
+
offsetMatrix: [
|
|
1892
|
+
0.9060805439949036, -0.1844543218612671, 0.3807799518108368, 0,
|
|
1893
|
+
-0.08027800172567368, 0.8086723685264587, 0.5827555656433105, 0,
|
|
1894
|
+
-0.4154181182384491, -0.5585917234420776, 0.7179155349731445, 0,
|
|
1895
|
+
-0.06867414712905884, -0.009423808194696903, 0.10627774149179459, 1,
|
|
1896
|
+
],
|
|
1897
|
+
radius: 0.021460847929120064,
|
|
1898
|
+
},
|
|
1899
|
+
'thumb-metacarpal': {
|
|
1900
|
+
offsetMatrix: [
|
|
1901
|
+
-0.5012241005897522, -0.8650535345077515, -0.0213695727288723, 0,
|
|
1902
|
+
0.7415963411331177, -0.4421543478965759, 0.5045139193534851, 0,
|
|
1903
|
+
-0.44587990641593933, 0.23702676594257355, 0.8631392121315002, 0,
|
|
1904
|
+
-0.032122574746608734, -0.01196830440312624, 0.07194234430789948, 1,
|
|
1905
|
+
],
|
|
1906
|
+
radius: 0.019382517784833908,
|
|
1907
|
+
},
|
|
1908
|
+
'thumb-phalanx-proximal': {
|
|
1909
|
+
offsetMatrix: [
|
|
1910
|
+
-0.3175753057003021, -0.9460570216178894, -0.06419729441404343, 0,
|
|
1911
|
+
0.8958902955055237, -0.32153913378715515, 0.30658137798309326, 0,
|
|
1912
|
+
-0.3106854259967804, 0.03984907269477844, 0.9496771097183228, 0,
|
|
1913
|
+
-0.017625702545046806, -0.01967475935816765, 0.04387917369604111, 1,
|
|
1914
|
+
],
|
|
1915
|
+
radius: 0.01228295173496008,
|
|
1916
|
+
},
|
|
1917
|
+
'thumb-phalanx-distal': {
|
|
1918
|
+
offsetMatrix: [
|
|
1919
|
+
-0.4944636821746826, -0.8691971898078918, 0.001086252392269671, 0,
|
|
1920
|
+
0.8307800889015198, -0.4722411036491394, 0.2946045398712158, 0,
|
|
1921
|
+
-0.25555649399757385, 0.14657381176948547, 0.9556186199188232, 0,
|
|
1922
|
+
-0.007126678712666035, -0.021021386608481407, 0.011786630377173424, 1,
|
|
1923
|
+
],
|
|
1924
|
+
radius: 0.009768804535269737,
|
|
1925
|
+
},
|
|
1926
|
+
'thumb-tip': {
|
|
1927
|
+
offsetMatrix: [
|
|
1928
|
+
-0.4944636821746826, -0.8691971898078918, 0.001086252392269671, 0,
|
|
1929
|
+
0.8307800889015198, -0.4722411036491394, 0.2946045398712158, 0,
|
|
1930
|
+
-0.25555649399757385, 0.14657381176948547, 0.9556186199188232, 0,
|
|
1931
|
+
0.0003423091256991029, -0.024528030306100845, -0.011410919018089771, 1,
|
|
1932
|
+
],
|
|
1933
|
+
radius: 0.008768804371356964,
|
|
1934
|
+
},
|
|
1935
|
+
'index-finger-metacarpal': {
|
|
1936
|
+
offsetMatrix: [
|
|
1937
|
+
0.9060805439949036, -0.1844543218612671, 0.3807799518108368, 0,
|
|
1938
|
+
-0.08027800172567368, 0.8086723685264587, 0.5827555656433105, 0,
|
|
1939
|
+
-0.4154181182384491, -0.5585917234420776, 0.7179155349731445, 0,
|
|
1940
|
+
-0.038037415593862534, -0.0020236473064869642, 0.07626739144325256, 1,
|
|
1941
|
+
],
|
|
1942
|
+
radius: 0.021228281781077385,
|
|
1943
|
+
},
|
|
1944
|
+
'index-finger-phalanx-proximal': {
|
|
1945
|
+
offsetMatrix: [
|
|
1946
|
+
0.7986818552017212, -0.35985732078552246, 0.48229536414146423, 0,
|
|
1947
|
+
0.538311243057251, 0.7854709625244141, -0.30537736415863037, 0,
|
|
1948
|
+
-0.2689369022846222, 0.5035246014595032, 0.8210577368736267, 0,
|
|
1949
|
+
-0.006869405973702669, 0.033938243985176086, 0.04206443578004837, 1,
|
|
1950
|
+
],
|
|
1951
|
+
radius: 0.010295259766280651,
|
|
1952
|
+
},
|
|
1953
|
+
'index-finger-phalanx-intermediate': {
|
|
1954
|
+
offsetMatrix: [
|
|
1955
|
+
0.8285930156707764, -0.32672837376594543, 0.4546217918395996, 0,
|
|
1956
|
+
0.5577570199966431, 0.4116027057170868, -0.7207564115524292, 0,
|
|
1957
|
+
0.04836784675717354, 0.8507823944091797, 0.5232869386672974, 0,
|
|
1958
|
+
0.0033306588884443045, 0.014840902760624886, 0.010923954658210278, 1,
|
|
1959
|
+
],
|
|
1960
|
+
radius: 0.00853810179978609,
|
|
1961
|
+
},
|
|
1962
|
+
'index-finger-phalanx-distal': {
|
|
1963
|
+
offsetMatrix: [
|
|
1964
|
+
0.8412464261054993, -0.35794928669929504, 0.4051857888698578, 0,
|
|
1965
|
+
0.5139996409416199, 0.29711154103279114, -0.8046918511390686, 0,
|
|
1966
|
+
0.16765329241752625, 0.8852096796035767, 0.4339304566383362, 0,
|
|
1967
|
+
0.0021551470272243023, -0.0058362227864563465, -0.0017938464879989624,
|
|
1968
|
+
1,
|
|
1969
|
+
],
|
|
1970
|
+
radius: 0.007636196445673704,
|
|
1971
|
+
},
|
|
1972
|
+
'index-finger-tip': {
|
|
1973
|
+
offsetMatrix: [
|
|
1974
|
+
0.8412464261054993, -0.35794928669929504, 0.4051857888698578, 0,
|
|
1975
|
+
0.5139996409416199, 0.29711154103279114, -0.8046918511390686, 0,
|
|
1976
|
+
0.16765329241752625, 0.8852096796035767, 0.4339304566383362, 0,
|
|
1977
|
+
-0.00131594471167773, -0.025222131982445717, -0.012442642822861671, 1,
|
|
1978
|
+
],
|
|
1979
|
+
radius: 0.006636196281760931,
|
|
1980
|
+
},
|
|
1981
|
+
'middle-finger-metacarpal': {
|
|
1982
|
+
offsetMatrix: [
|
|
1983
|
+
0.9060805439949036, -0.1844543218612671, 0.3807799518108368, 0,
|
|
1984
|
+
-0.08027800172567368, 0.8086723685264587, 0.5827555656433105, 0,
|
|
1985
|
+
-0.4154181182384491, -0.5585917234420776, 0.7179155349731445, 0,
|
|
1986
|
+
-0.05395089089870453, 0.003063359996303916, 0.07402937114238739, 1,
|
|
1987
|
+
],
|
|
1988
|
+
radius: 0.021231964230537415,
|
|
1989
|
+
},
|
|
1990
|
+
'middle-finger-phalanx-proximal': {
|
|
1991
|
+
offsetMatrix: [
|
|
1992
|
+
0.9187911748886108, -0.1530158370733261, 0.36387869715690613, 0,
|
|
1993
|
+
0.038666240870952606, 0.9522662162780762, 0.302808940410614, 0,
|
|
1994
|
+
-0.3928440511226654, -0.26414817571640015, 0.8808513283729553, 0,
|
|
1995
|
+
-0.02717282809317112, 0.04162866622209549, 0.03678669035434723, 1,
|
|
1996
|
+
],
|
|
1997
|
+
radius: 0.01117393933236599,
|
|
1998
|
+
},
|
|
1999
|
+
'middle-finger-phalanx-intermediate': {
|
|
2000
|
+
offsetMatrix: [
|
|
2001
|
+
0.9228746294975281, -0.12856416404247284, 0.36300456523895264, 0,
|
|
2002
|
+
0.14524033665657043, 0.9892153143882751, -0.01890045404434204, 0,
|
|
2003
|
+
-0.3566599190235138, 0.07016586512327194, 0.9315956234931946, 0,
|
|
2004
|
+
-0.01030921470373869, 0.05296773463487625, -0.0010256498353555799, 1,
|
|
2005
|
+
],
|
|
2006
|
+
radius: 0.008030958473682404,
|
|
2007
|
+
},
|
|
2008
|
+
'middle-finger-phalanx-distal': {
|
|
2009
|
+
offsetMatrix: [
|
|
2010
|
+
0.9325166344642639, -0.040404170751571655, 0.35885775089263916, 0,
|
|
2011
|
+
0.06836572289466858, 0.995502769947052, -0.0655682161450386, 0,
|
|
2012
|
+
-0.3545948565006256, 0.08567725121974945, 0.9310863614082336, 0,
|
|
2013
|
+
-0.0004833847051486373, 0.05103470757603645, -0.026690717786550522, 1,
|
|
2014
|
+
],
|
|
2015
|
+
radius: 0.007629410829395056,
|
|
2016
|
+
},
|
|
2017
|
+
'middle-finger-tip': {
|
|
2018
|
+
offsetMatrix: [
|
|
2019
|
+
0.9325166344642639, -0.040404170751571655, 0.35885775089263916, 0,
|
|
2020
|
+
0.06836572289466858, 0.995502769947052, -0.0655682161450386, 0,
|
|
2021
|
+
-0.3545948565006256, 0.08567725121974945, 0.9310863614082336, 0,
|
|
2022
|
+
0.008158999495208263, 0.05004044249653816, -0.050120558589696884, 1,
|
|
2023
|
+
],
|
|
2024
|
+
radius: 0.006629410665482283,
|
|
2025
|
+
},
|
|
2026
|
+
'ring-finger-metacarpal': {
|
|
2027
|
+
offsetMatrix: [
|
|
2028
|
+
0.9060805439949036, -0.1844543218612671, 0.3807799518108368, 0,
|
|
2029
|
+
-0.08027800172567368, 0.8086723685264587, 0.5827555656433105, 0,
|
|
2030
|
+
-0.4154181182384491, -0.5585917234420776, 0.7179155349731445, 0,
|
|
2031
|
+
-0.06732909381389618, 0.007902119308710098, 0.07209732383489609, 1,
|
|
2032
|
+
],
|
|
2033
|
+
radius: 0.019088275730609894,
|
|
2034
|
+
},
|
|
2035
|
+
'ring-finger-phalanx-proximal': {
|
|
2036
|
+
offsetMatrix: [
|
|
2037
|
+
0.9391821026802063, -0.027994679287075996, 0.34227466583251953, 0,
|
|
2038
|
+
-0.18282271921634674, 0.8029410243034363, 0.5673282742500305, 0,
|
|
2039
|
+
-0.2907087206840515, -0.5954000353813171, 0.7489906549453735, 0,
|
|
2040
|
+
-0.047129884362220764, 0.03806127607822418, 0.032147664576768875, 1,
|
|
2041
|
+
],
|
|
2042
|
+
radius: 0.00992213748395443,
|
|
2043
|
+
},
|
|
2044
|
+
'ring-finger-phalanx-intermediate': {
|
|
2045
|
+
offsetMatrix: [
|
|
2046
|
+
0.9249380826950073, 0.03699534013867378, 0.3783116042613983, 0,
|
|
2047
|
+
-0.12898847460746765, 0.9667453765869141, 0.2208271026611328, 0,
|
|
2048
|
+
-0.3575615882873535, -0.25304901599884033, 0.8989526629447937, 0,
|
|
2049
|
+
-0.03579339757561684, 0.06127955764532089, 0.002939916681498289, 1,
|
|
2050
|
+
],
|
|
2051
|
+
radius: 0.007611672393977642,
|
|
2052
|
+
},
|
|
2053
|
+
'ring-finger-phalanx-distal': {
|
|
2054
|
+
offsetMatrix: [
|
|
2055
|
+
0.9001164436340332, 0.03983335196971893, 0.4338230490684509, 0,
|
|
2056
|
+
-0.09662467986345291, 0.9892624020576477, 0.10964841395616531, 0,
|
|
2057
|
+
-0.4247973561286926, -0.14061418175697327, 0.8943013548851013, 0,
|
|
2058
|
+
-0.026291755959391594, 0.06800390034914017, -0.02094830758869648, 1,
|
|
2059
|
+
],
|
|
2060
|
+
radius: 0.007231088820844889,
|
|
2061
|
+
},
|
|
2062
|
+
'ring-finger-tip': {
|
|
2063
|
+
offsetMatrix: [
|
|
2064
|
+
0.9001164436340332, 0.03983335196971893, 0.4338230490684509, 0,
|
|
2065
|
+
-0.09662467986345291, 0.9892624020576477, 0.10964841395616531, 0,
|
|
2066
|
+
-0.4247973561286926, -0.14061418175697327, 0.8943013548851013, 0,
|
|
2067
|
+
-0.016345610842108727, 0.07300511747598648, -0.04263874143362045, 1,
|
|
2068
|
+
],
|
|
2069
|
+
radius: 0.0062310886569321156,
|
|
2070
|
+
},
|
|
2071
|
+
'pinky-finger-metacarpal': {
|
|
2072
|
+
offsetMatrix: [
|
|
2073
|
+
0.8769711852073669, 0.31462907791137695, 0.36322021484375, 0,
|
|
2074
|
+
-0.4506046175956726, 0.801031768321991, 0.39408499002456665, 0,
|
|
2075
|
+
-0.16696058213710785, -0.5092697143554688, 0.8442559838294983, 0,
|
|
2076
|
+
-0.07460174709558487, 0.0062340241856873035, 0.06756893545389175, 1,
|
|
2077
|
+
],
|
|
2078
|
+
radius: 0.01808827556669712,
|
|
2079
|
+
},
|
|
2080
|
+
'pinky-finger-phalanx-proximal': {
|
|
2081
|
+
offsetMatrix: [
|
|
2082
|
+
0.9498357176780701, 0.1553308218717575, 0.2714462876319885, 0,
|
|
2083
|
+
-0.3019258379936218, 0.6817675232887268, 0.6663586497306824, 0,
|
|
2084
|
+
-0.08155745267868042, -0.7148879170417786, 0.694466233253479, 0,
|
|
2085
|
+
-0.06697750836610794, 0.029482364654541016, 0.02902858518064022, 1,
|
|
2086
|
+
],
|
|
2087
|
+
radius: 0.008483353070914745,
|
|
2088
|
+
},
|
|
2089
|
+
'pinky-finger-phalanx-intermediate': {
|
|
2090
|
+
offsetMatrix: [
|
|
2091
|
+
0.9214097261428833, 0.27928245067596436, 0.2701927423477173, 0,
|
|
2092
|
+
-0.3670244514942169, 0.8538867831230164, 0.36901235580444336, 0,
|
|
2093
|
+
-0.12765564024448395, -0.43917882442474365, 0.8892839550971985, 0,
|
|
2094
|
+
-0.06447203457355499, 0.05144399777054787, 0.0076942890882492065, 1,
|
|
2095
|
+
],
|
|
2096
|
+
radius: 0.0067641944624483585,
|
|
2097
|
+
},
|
|
2098
|
+
'pinky-finger-phalanx-distal': {
|
|
2099
|
+
offsetMatrix: [
|
|
2100
|
+
0.9038633704185486, 0.23618005216121674, 0.3567195236682892, 0,
|
|
2101
|
+
-0.3532794713973999, 0.8823202252388, 0.3109731376171112, 0,
|
|
2102
|
+
-0.24129553139209747, -0.4070987403392792, 0.8809353709220886, 0,
|
|
2103
|
+
-0.06187915802001953, 0.060364335775375366, -0.010368337854743004, 1,
|
|
2104
|
+
],
|
|
2105
|
+
radius: 0.0064259846694767475,
|
|
2106
|
+
},
|
|
2107
|
+
'pinky-finger-tip': {
|
|
2108
|
+
offsetMatrix: [
|
|
2109
|
+
0.9038633704185486, 0.23618005216121674, 0.3567195236682892, 0,
|
|
2110
|
+
-0.3532794713973999, 0.8823202252388, 0.3109731376171112, 0,
|
|
2111
|
+
-0.24129553139209747, -0.4070987403392792, 0.8809353709220886, 0,
|
|
2112
|
+
-0.056796226650476456, 0.07042007893323898, -0.02921444922685623, 1,
|
|
2113
|
+
],
|
|
2114
|
+
radius: 0.005425984505563974,
|
|
2115
|
+
},
|
|
2116
|
+
},
|
|
2117
|
+
gripOffsetMatrix: [
|
|
2118
|
+
0.08027800917625427, -0.8086723685264587, -0.5827556252479553, 0,
|
|
2119
|
+
-0.4154181480407715, -0.5585916638374329, 0.7179154753684998, 0,
|
|
2120
|
+
-0.9060805439949036, 0.1844543218612671, -0.3807799518108368, 0,
|
|
2121
|
+
-0.038054611533880234, -0.002910431008785963, 0.03720742464065552, 1,
|
|
2122
|
+
],
|
|
2123
|
+
};
|
|
2124
|
+
|
|
2125
|
+
const pointHandPose = {
|
|
2126
|
+
jointTransforms: {
|
|
2127
|
+
wrist: {
|
|
2128
|
+
offsetMatrix: [
|
|
2129
|
+
0.9340395331382751, -0.13936476409435272, 0.32885703444480896, 0,
|
|
2130
|
+
-0.005510995630174875, 0.914999783039093, 0.40341612696647644, 0,
|
|
2131
|
+
-0.3571262061595917, -0.37861889600753784, 0.8538784384727478, 0,
|
|
2132
|
+
-0.05789132043719292, 0.01670890860259533, 0.11183350533246994, 1,
|
|
2133
|
+
],
|
|
2134
|
+
radius: 0.021460847929120064,
|
|
2135
|
+
},
|
|
2136
|
+
'thumb-metacarpal': {
|
|
2137
|
+
offsetMatrix: [
|
|
2138
|
+
0.02145560085773468, -0.9978390336036682, 0.0621047280728817, 0,
|
|
2139
|
+
0.41311800479888916, 0.06541631370782852, 0.9083252549171448, 0,
|
|
2140
|
+
-0.9104245901107788, 0.006167683284729719, 0.4136286973953247, 0,
|
|
2141
|
+
-0.016488194465637207, 0.012708572670817375, 0.08862338215112686, 1,
|
|
2142
|
+
],
|
|
2143
|
+
radius: 0.019382517784833908,
|
|
2144
|
+
},
|
|
2145
|
+
'thumb-phalanx-proximal': {
|
|
2146
|
+
offsetMatrix: [
|
|
2147
|
+
0.21270370483398438, -0.966137707233429, 0.14606566727161407, 0,
|
|
2148
|
+
0.49890995025634766, 0.2359165996313095, 0.8339261412620544, 0,
|
|
2149
|
+
-0.8401462435722351, -0.10450579971075058, 0.5321959853172302, 0,
|
|
2150
|
+
0.013112368993461132, 0.012508046813309193, 0.07517509907484055, 1,
|
|
2151
|
+
],
|
|
2152
|
+
radius: 0.01228295173496008,
|
|
2153
|
+
},
|
|
2154
|
+
'thumb-phalanx-distal': {
|
|
2155
|
+
offsetMatrix: [
|
|
2156
|
+
0.01653280481696129, -0.9986647963523865, 0.048943229019641876, 0,
|
|
2157
|
+
0.26313456892967224, 0.051570065319538116, 0.9633802771568298, 0,
|
|
2158
|
+
-0.9646173715591431, -0.0030490627977997065, 0.26363563537597656, 0,
|
|
2159
|
+
0.04150351136922836, 0.016039609909057617, 0.05719054117798805, 1,
|
|
2160
|
+
],
|
|
2161
|
+
radius: 0.009768804535269737,
|
|
2162
|
+
},
|
|
2163
|
+
'thumb-tip': {
|
|
2164
|
+
offsetMatrix: [
|
|
2165
|
+
0.01653280481696129, -0.9986647963523865, 0.048943229019641876, 0,
|
|
2166
|
+
0.26313456892967224, 0.051570065319538116, 0.9633802771568298, 0,
|
|
2167
|
+
-0.9646173715591431, -0.0030490627977997065, 0.26363563537597656, 0,
|
|
2168
|
+
0.06548332422971725, 0.01683700829744339, 0.0516640841960907, 1,
|
|
2169
|
+
],
|
|
2170
|
+
radius: 0.008768804371356964,
|
|
2171
|
+
},
|
|
2172
|
+
'index-finger-metacarpal': {
|
|
2173
|
+
offsetMatrix: [
|
|
2174
|
+
0.9340395331382751, -0.13936476409435272, 0.32885703444480896, 0,
|
|
2175
|
+
-0.005510995630174875, 0.914999783039093, 0.40341612696647644, 0,
|
|
2176
|
+
-0.3571262061595917, -0.37861889600753784, 0.8538784384727478, 0,
|
|
2177
|
+
-0.02592567168176174, 0.019982583820819855, 0.08479326963424683, 1,
|
|
2178
|
+
],
|
|
2179
|
+
radius: 0.021228281781077385,
|
|
2180
|
+
},
|
|
2181
|
+
'index-finger-phalanx-proximal': {
|
|
2182
|
+
offsetMatrix: [
|
|
2183
|
+
0.9063700437545776, -0.21756279468536377, 0.3621589243412018, 0,
|
|
2184
|
+
0.0970839336514473, 0.9415287375450134, 0.3226419687271118, 0,
|
|
2185
|
+
-0.41117796301841736, -0.2572731077671051, 0.8744958639144897, 0,
|
|
2186
|
+
-0.0015709538711234927, 0.043078210204839706, 0.034657616168260574, 1,
|
|
2187
|
+
],
|
|
2188
|
+
radius: 0.010295259766280651,
|
|
2189
|
+
},
|
|
2190
|
+
'index-finger-phalanx-intermediate': {
|
|
2191
|
+
offsetMatrix: [
|
|
2192
|
+
0.9159826040267944, -0.1651475727558136, 0.36565208435058594, 0,
|
|
2193
|
+
0.09755707532167435, 0.9756820797920227, 0.1962820291519165, 0,
|
|
2194
|
+
-0.3891757130622864, -0.14411886036396027, 0.9098196625709534, 0,
|
|
2195
|
+
0.014023927971720695, 0.052835866808891296, 0.0014903299743309617, 1,
|
|
2196
|
+
],
|
|
2197
|
+
radius: 0.00853810179978609,
|
|
2198
|
+
},
|
|
2199
|
+
'index-finger-phalanx-distal': {
|
|
2200
|
+
offsetMatrix: [
|
|
2201
|
+
0.9378057718276978, -0.12329639494419098, 0.3245268166065216, 0,
|
|
2202
|
+
0.032558172941207886, 0.9619227051734924, 0.2713746726512909, 0,
|
|
2203
|
+
-0.3456292748451233, -0.2439306229352951, 0.9061115384101868, 0,
|
|
2204
|
+
0.023482320830225945, 0.05633850023150444, -0.020621655508875847, 1,
|
|
2205
|
+
],
|
|
2206
|
+
radius: 0.007636196445673704,
|
|
2207
|
+
},
|
|
2208
|
+
'index-finger-tip': {
|
|
2209
|
+
offsetMatrix: [
|
|
2210
|
+
0.9378057718276978, -0.12329639494419098, 0.3245268166065216, 0,
|
|
2211
|
+
0.032558172941207886, 0.9619227051734924, 0.2713746726512909, 0,
|
|
2212
|
+
-0.3456292748451233, -0.2439306229352951, 0.9061115384101868, 0,
|
|
2213
|
+
0.03096788562834263, 0.06281610578298569, -0.040703095495700836, 1,
|
|
2214
|
+
],
|
|
2215
|
+
radius: 0.006636196281760931,
|
|
2216
|
+
},
|
|
2217
|
+
'middle-finger-metacarpal': {
|
|
2218
|
+
offsetMatrix: [
|
|
2219
|
+
0.9340395331382751, -0.13936476409435272, 0.32885703444480896, 0,
|
|
2220
|
+
-0.005510995630174875, 0.914999783039093, 0.40341612696647644, 0,
|
|
2221
|
+
-0.3571262061595917, -0.37861889600753784, 0.8538784384727478, 0,
|
|
2222
|
+
-0.04184452444314957, 0.022474845871329308, 0.08177298307418823, 1,
|
|
2223
|
+
],
|
|
2224
|
+
radius: 0.021231964230537415,
|
|
2225
|
+
},
|
|
2226
|
+
'middle-finger-phalanx-proximal': {
|
|
2227
|
+
offsetMatrix: [
|
|
2228
|
+
0.9720265865325928, -0.08313076198101044, 0.21966552734375, 0,
|
|
2229
|
+
0.20477405190467834, 0.7580050826072693, -0.6192700862884521, 0,
|
|
2230
|
+
-0.11502730846405029, 0.6469289064407349, 0.7538246512413025, 0,
|
|
2231
|
+
-0.022107340395450592, 0.05035499855875969, 0.02970452979207039, 1,
|
|
2232
|
+
],
|
|
2233
|
+
radius: 0.01117393933236599,
|
|
2234
|
+
},
|
|
2235
|
+
'middle-finger-phalanx-intermediate': {
|
|
2236
|
+
offsetMatrix: [
|
|
2237
|
+
0.9779140949249268, -0.07129573822021484, 0.19646917283535004, 0,
|
|
2238
|
+
0.1287083923816681, -0.5352076292037964, -0.8348574042320251, 0,
|
|
2239
|
+
0.1646735966205597, 0.8417060971260071, -0.5142109394073486, 0,
|
|
2240
|
+
-0.017169542610645294, 0.022584279999136925, -0.00265491777099669, 1,
|
|
2241
|
+
],
|
|
2242
|
+
radius: 0.008030958473682404,
|
|
2243
|
+
},
|
|
2244
|
+
'middle-finger-phalanx-distal': {
|
|
2245
|
+
offsetMatrix: [
|
|
2246
|
+
0.9774913787841797, -0.19657190144062042, 0.07661263644695282, 0,
|
|
2247
|
+
-0.1924918293952942, -0.9796126484870911, -0.05749811604619026, 0,
|
|
2248
|
+
0.08635343611240387, 0.041456472128629684, -0.995401918888092, 0,
|
|
2249
|
+
-0.02170622907578945, -0.0006043742760084569, 0.011511396616697311, 1,
|
|
2250
|
+
],
|
|
2251
|
+
radius: 0.007629410829395056,
|
|
2252
|
+
},
|
|
2253
|
+
'middle-finger-tip': {
|
|
2254
|
+
offsetMatrix: [
|
|
2255
|
+
0.9774913787841797, -0.19657190144062042, 0.07661263644695282, 0,
|
|
2256
|
+
-0.1924918293952942, -0.9796126484870911, -0.05749811604619026, 0,
|
|
2257
|
+
0.08635343611240387, 0.041456472128629684, -0.995401918888092, 0,
|
|
2258
|
+
-0.02438267692923546, -0.0026927536819130182, 0.03627248480916023, 1,
|
|
2259
|
+
],
|
|
2260
|
+
radius: 0.006629410665482283,
|
|
2261
|
+
},
|
|
2262
|
+
'ring-finger-metacarpal': {
|
|
2263
|
+
offsetMatrix: [
|
|
2264
|
+
0.9340395331382751, -0.13936476409435272, 0.32885703444480896, 0,
|
|
2265
|
+
-0.005510995630174875, 0.914999783039093, 0.40341612696647644, 0,
|
|
2266
|
+
-0.3571262061595917, -0.37861889600753784, 0.8538784384727478, 0,
|
|
2267
|
+
-0.05944233387708664, 0.0264605600386858, 0.07478221505880356, 1,
|
|
2268
|
+
],
|
|
2269
|
+
radius: 0.019088275730609894,
|
|
2270
|
+
},
|
|
2271
|
+
'ring-finger-phalanx-proximal': {
|
|
2272
|
+
offsetMatrix: [
|
|
2273
|
+
0.9842101335525513, 0.024470895528793335, 0.1753024309873581, 0,
|
|
2274
|
+
0.12200043350458145, 0.6237703561782837, -0.7720272541046143, 0,
|
|
2275
|
+
-0.12824076414108276, 0.7812241315841675, 0.610936164855957, 0,
|
|
2276
|
+
-0.04249368980526924, 0.0467497780919075, 0.027722163125872612, 1,
|
|
2277
|
+
],
|
|
2278
|
+
radius: 0.00992213748395443,
|
|
2279
|
+
},
|
|
2280
|
+
'ring-finger-phalanx-intermediate': {
|
|
2281
|
+
offsetMatrix: [
|
|
2282
|
+
0.9941774606704712, 0.05949164181947708, 0.08983955532312393, 0,
|
|
2283
|
+
0.10504482686519623, -0.7208291888237, -0.6851072907447815, 0,
|
|
2284
|
+
0.024001073092222214, 0.6905553936958313, -0.7228817939758301, 0,
|
|
2285
|
+
-0.0374927744269371, 0.016285063698887825, 0.0038980208337306976, 1,
|
|
2286
|
+
],
|
|
2287
|
+
radius: 0.007611672393977642,
|
|
2288
|
+
},
|
|
2289
|
+
'ring-finger-phalanx-distal': {
|
|
2290
|
+
offsetMatrix: [
|
|
2291
|
+
0.9995742440223694, 0.01638498157262802, 0.02412819117307663, 0,
|
|
2292
|
+
0.007813597097992897, -0.9474818110466003, 0.31971633434295654, 0,
|
|
2293
|
+
0.028100071474909782, -0.31939181685447693, -0.9472070932388306, 0,
|
|
2294
|
+
-0.038130562752485275, -0.0020653479732573032, 0.02310742810368538, 1,
|
|
2295
|
+
],
|
|
2296
|
+
radius: 0.007231088820844889,
|
|
2297
|
+
},
|
|
2298
|
+
'ring-finger-tip': {
|
|
2299
|
+
offsetMatrix: [
|
|
2300
|
+
0.9995742440223694, 0.01638498157262802, 0.02412819117307663, 0,
|
|
2301
|
+
0.007813597097992897, -0.9474818110466003, 0.31971633434295654, 0,
|
|
2302
|
+
0.028100071474909782, -0.31939181685447693, -0.9472070932388306, 0,
|
|
2303
|
+
-0.0390593595802784, 0.004176302347332239, 0.0466572530567646, 1,
|
|
2304
|
+
],
|
|
2305
|
+
radius: 0.0062310886569321156,
|
|
2306
|
+
},
|
|
2307
|
+
'pinky-finger-metacarpal': {
|
|
2308
|
+
offsetMatrix: [
|
|
2309
|
+
0.9147363901138306, 0.3458845317363739, 0.20885537564754486, 0,
|
|
2310
|
+
-0.3923271894454956, 0.8839452862739563, 0.2544005811214447, 0,
|
|
2311
|
+
-0.09662359952926636, -0.3146490156650543, 0.9442773461341858, 0,
|
|
2312
|
+
-0.06715242564678192, 0.024195827543735504, 0.07137546688318253, 1,
|
|
2313
|
+
],
|
|
2314
|
+
radius: 0.01808827556669712,
|
|
2315
|
+
},
|
|
2316
|
+
'pinky-finger-phalanx-proximal': {
|
|
2317
|
+
offsetMatrix: [
|
|
2318
|
+
0.9613109827041626, 0.22439135611057281, 0.15977802872657776, 0,
|
|
2319
|
+
0.01002211682498455, 0.5511574745178223, -0.8343409299850464, 0,
|
|
2320
|
+
-0.27528178691864014, 0.8036624789237976, 0.5275853276252747, 0,
|
|
2321
|
+
-0.06273911893367767, 0.038559623062610626, 0.028268879279494286, 1,
|
|
2322
|
+
],
|
|
2323
|
+
radius: 0.008483353070914745,
|
|
2324
|
+
},
|
|
2325
|
+
'pinky-finger-phalanx-intermediate': {
|
|
2326
|
+
offsetMatrix: [
|
|
2327
|
+
0.9820972084999084, 0.18811029195785522, -0.00995189044624567, 0,
|
|
2328
|
+
0.14063723385334015, -0.7673450708389282, -0.6256227493286133, 0,
|
|
2329
|
+
-0.12532226741313934, 0.6130226850509644, -0.7800630927085876, 0,
|
|
2330
|
+
-0.05428232625126839, 0.013870777562260628, 0.012061242014169693, 1,
|
|
2331
|
+
],
|
|
2332
|
+
radius: 0.0067641944624483585,
|
|
2333
|
+
},
|
|
2334
|
+
'pinky-finger-phalanx-distal': {
|
|
2335
|
+
offsetMatrix: [
|
|
2336
|
+
0.9744614362716675, 0.20454788208007812, -0.09265263378620148, 0,
|
|
2337
|
+
0.22429193556308746, -0.9065253138542175, 0.35764020681381226, 0,
|
|
2338
|
+
-0.010836843401193619, -0.3692878782749176, -0.9292529225349426, 0,
|
|
2339
|
+
-0.05173685774207115, 0.0014194445684552193, 0.02790539152920246, 1,
|
|
2340
|
+
],
|
|
2341
|
+
radius: 0.0064259846694767475,
|
|
2342
|
+
},
|
|
2343
|
+
'pinky-finger-tip': {
|
|
2344
|
+
offsetMatrix: [
|
|
2345
|
+
0.9744614362716675, 0.20454788208007812, -0.09265263378620148, 0,
|
|
2346
|
+
0.22429193556308746, -0.9065253138542175, 0.35764020681381226, 0,
|
|
2347
|
+
-0.010836843401193619, -0.3692878782749176, -0.9292529225349426, 0,
|
|
2348
|
+
-0.05098633095622063, 0.008463085629045963, 0.048688892275094986, 1,
|
|
2349
|
+
],
|
|
2350
|
+
radius: 0.005425984505563974,
|
|
2351
|
+
},
|
|
2352
|
+
},
|
|
2353
|
+
gripOffsetMatrix: [
|
|
2354
|
+
0.005510995630174875, -0.9149997234344482, -0.40341615676879883, 0,
|
|
2355
|
+
-0.3571262061595917, -0.37861889600753784, 0.8538784384727478, 0,
|
|
2356
|
+
-0.9340395331382751, 0.13936474919319153, -0.32885703444480896, 0,
|
|
2357
|
+
-0.031803809106349945, 0.007837686687707901, 0.04313928261399269, 1,
|
|
2358
|
+
],
|
|
2359
|
+
};
|
|
2360
|
+
|
|
2361
|
+
const relaxedHandPose = {
|
|
2362
|
+
jointTransforms: {
|
|
2363
|
+
wrist: {
|
|
2364
|
+
offsetMatrix: [
|
|
2365
|
+
0.9616971015930176, -0.13805118203163147, 0.2368120402097702, 0,
|
|
2366
|
+
0.0005348679260350764, 0.8648636937141418, 0.5020061135292053, 0,
|
|
2367
|
+
-0.2741127610206604, -0.48265108466148376, 0.8318111300468445, 0,
|
|
2368
|
+
-0.04913589730858803, 0.0021463718730956316, 0.11701996624469757, 1,
|
|
2369
|
+
],
|
|
2370
|
+
radius: 0.021460847929120064,
|
|
2371
|
+
},
|
|
2372
|
+
'thumb-metacarpal': {
|
|
2373
|
+
offsetMatrix: [
|
|
2374
|
+
-0.07536252588033676, -0.9959676265716553, -0.04867160692811012, 0,
|
|
2375
|
+
0.5877083539962769, -0.08379616588354111, 0.8047218918800354, 0,
|
|
2376
|
+
-0.8055551648139954, 0.032041035592556, 0.5916536450386047, 0,
|
|
2377
|
+
-0.010643752291798592, 0.0006936835707165301, 0.08736639469861984, 1,
|
|
2378
|
+
],
|
|
2379
|
+
radius: 0.019382517784833908,
|
|
2380
|
+
},
|
|
2381
|
+
'thumb-phalanx-proximal': {
|
|
2382
|
+
offsetMatrix: [
|
|
2383
|
+
0.1374533325433731, -0.9904957413673401, 0.004982374142855406, 0,
|
|
2384
|
+
0.5534393787384033, 0.08097179979085922, 0.8289443850517273, 0,
|
|
2385
|
+
-0.8214688897132874, -0.11118389666080475, 0.559309184551239, 0,
|
|
2386
|
+
0.015547193586826324, -0.0003480653394944966, 0.0681300163269043, 1,
|
|
2387
|
+
],
|
|
2388
|
+
radius: 0.01228295173496008,
|
|
2389
|
+
},
|
|
2390
|
+
'thumb-phalanx-distal': {
|
|
2391
|
+
offsetMatrix: [
|
|
2392
|
+
-0.04659227654337883, -0.9974699020385742, -0.05369402840733528, 0,
|
|
2393
|
+
0.6812446117401123, -0.07104194164276123, 0.728600800037384, 0,
|
|
2394
|
+
-0.7305715084075928, -0.002631746232509613, 0.6828309893608093, 0,
|
|
2395
|
+
0.04330715537071228, 0.003409178927540779, 0.0492292083799839, 1,
|
|
2396
|
+
],
|
|
2397
|
+
radius: 0.009768804535269737,
|
|
2398
|
+
},
|
|
2399
|
+
'thumb-tip': {
|
|
2400
|
+
offsetMatrix: [
|
|
2401
|
+
-0.04659227654337883, -0.9974699020385742, -0.05369402840733528, 0,
|
|
2402
|
+
0.6812446117401123, -0.07104194164276123, 0.728600800037384, 0,
|
|
2403
|
+
-0.7305715084075928, -0.002631746232509613, 0.6828309893608093, 0,
|
|
2404
|
+
0.062003348022699356, 0.004069602582603693, 0.03322213143110275, 1,
|
|
2405
|
+
],
|
|
2406
|
+
radius: 0.008768804371356964,
|
|
2407
|
+
},
|
|
2408
|
+
'index-finger-metacarpal': {
|
|
2409
|
+
offsetMatrix: [
|
|
2410
|
+
0.9616971015930176, -0.13805118203163147, 0.2368120402097702, 0,
|
|
2411
|
+
0.0005348679260350764, 0.8648636937141418, 0.5020061135292053, 0,
|
|
2412
|
+
-0.2741127610206604, -0.48265108466148376, 0.8318111300468445, 0,
|
|
2413
|
+
-0.02009812369942665, 0.008770795539021492, 0.08660387247800827, 1,
|
|
2414
|
+
],
|
|
2415
|
+
radius: 0.021228281781077385,
|
|
2416
|
+
},
|
|
2417
|
+
'index-finger-phalanx-proximal': {
|
|
2418
|
+
offsetMatrix: [
|
|
2419
|
+
0.9001791477203369, -0.2598813474178314, 0.3494834005832672, 0,
|
|
2420
|
+
0.06073702871799469, 0.8695210218429565, 0.490146666765213, 0,
|
|
2421
|
+
-0.4312632381916046, -0.41999316215515137, 0.7985095381736755, 0,
|
|
2422
|
+
-0.00017739279428496957, 0.03890012577176094, 0.039073407649993896, 1,
|
|
2423
|
+
],
|
|
2424
|
+
radius: 0.010295259766280651,
|
|
2425
|
+
},
|
|
2426
|
+
'index-finger-phalanx-intermediate': {
|
|
2427
|
+
offsetMatrix: [
|
|
2428
|
+
0.9082008600234985, -0.20898112654685974, 0.36262574791908264, 0,
|
|
2429
|
+
0.11045389622449875, 0.9553793668746948, 0.27395179867744446, 0,
|
|
2430
|
+
-0.40369608998298645, -0.20874978601932526, 0.8907597661018372, 0,
|
|
2431
|
+
0.01617925800383091, 0.05482936650514603, 0.008788082748651505, 1,
|
|
2432
|
+
],
|
|
2433
|
+
radius: 0.00853810179978609,
|
|
2434
|
+
},
|
|
2435
|
+
'index-finger-phalanx-distal': {
|
|
2436
|
+
offsetMatrix: [
|
|
2437
|
+
0.9309692978858948, -0.16783711314201355, 0.32423174381256104, 0,
|
|
2438
|
+
0.1080828532576561, 0.9749603867530823, 0.1943446695804596, 0,
|
|
2439
|
+
-0.34873148798942566, -0.14588497579097748, 0.9257990717887878, 0,
|
|
2440
|
+
0.02599053829908371, 0.059902746230363846, -0.012860597111284733, 1,
|
|
2441
|
+
],
|
|
2442
|
+
radius: 0.007636196445673704,
|
|
2443
|
+
},
|
|
2444
|
+
'index-finger-tip': {
|
|
2445
|
+
offsetMatrix: [
|
|
2446
|
+
0.9309692978858948, -0.16783711314201355, 0.32423174381256104, 0,
|
|
2447
|
+
0.1080828532576561, 0.9749603867530823, 0.1943446695804596, 0,
|
|
2448
|
+
-0.34873148798942566, -0.14588497579097748, 0.9257990717887878, 0,
|
|
2449
|
+
0.03362493962049484, 0.06421422213315964, -0.033461250364780426, 1,
|
|
2450
|
+
],
|
|
2451
|
+
radius: 0.006636196281760931,
|
|
2452
|
+
},
|
|
2453
|
+
'middle-finger-metacarpal': {
|
|
2454
|
+
offsetMatrix: [
|
|
2455
|
+
0.9616971015930176, -0.13805118203163147, 0.2368120402097702, 0,
|
|
2456
|
+
0.0005348679260350764, 0.8648636937141418, 0.5020061135292053, 0,
|
|
2457
|
+
-0.2741127610206604, -0.48265108466148376, 0.8318111300468445, 0,
|
|
2458
|
+
-0.03627845644950867, 0.011579737067222595, 0.08550142496824265, 1,
|
|
2459
|
+
],
|
|
2460
|
+
radius: 0.021231964230537415,
|
|
2461
|
+
},
|
|
2462
|
+
'middle-finger-phalanx-proximal': {
|
|
2463
|
+
offsetMatrix: [
|
|
2464
|
+
0.9876697659492493, -0.06786545366048813, 0.1410750150680542, 0,
|
|
2465
|
+
-0.015095947310328484, 0.855663537979126, 0.5173118710517883, 0,
|
|
2466
|
+
-0.15582047402858734, -0.5130629539489746, 0.8440889716148376, 0,
|
|
2467
|
+
-0.021259509027004242, 0.04587256908416748, 0.03659208118915558, 1,
|
|
2468
|
+
],
|
|
2469
|
+
radius: 0.01117393933236599,
|
|
2470
|
+
},
|
|
2471
|
+
'middle-finger-phalanx-intermediate': {
|
|
2472
|
+
offsetMatrix: [
|
|
2473
|
+
0.988391637802124, -0.04354291781783104, 0.14555205404758453, 0,
|
|
2474
|
+
0.008894841186702251, 0.9729899168014526, 0.23067504167556763, 0,
|
|
2475
|
+
-0.15166506171226501, -0.22670257091522217, 0.9620829224586487, 0,
|
|
2476
|
+
-0.014570588245987892, 0.06789684295654297, 0.0003578895702958107, 1,
|
|
2477
|
+
],
|
|
2478
|
+
radius: 0.008030958473682404,
|
|
2479
|
+
},
|
|
2480
|
+
'middle-finger-phalanx-distal': {
|
|
2481
|
+
offsetMatrix: [
|
|
2482
|
+
0.9853697419166565, 0.044260796159505844, 0.16458062827587128, 0,
|
|
2483
|
+
-0.0757969319820404, 0.9787378311157227, 0.19059516489505768, 0,
|
|
2484
|
+
-0.1526455283164978, -0.20028135180473328, 0.9677740931510925, 0,
|
|
2485
|
+
-0.010392282158136368, 0.07414241135120392, -0.026147106662392616, 1,
|
|
2486
|
+
],
|
|
2487
|
+
radius: 0.007629410829395056,
|
|
2488
|
+
},
|
|
2489
|
+
'middle-finger-tip': {
|
|
2490
|
+
offsetMatrix: [
|
|
2491
|
+
0.9853697419166565, 0.044260796159505844, 0.16458062827587128, 0,
|
|
2492
|
+
-0.0757969319820404, 0.9787378311157227, 0.19059516489505768, 0,
|
|
2493
|
+
-0.1526455283164978, -0.20028135180473328, 0.9677740931510925, 0,
|
|
2494
|
+
-0.0069718430750072, 0.08024183660745621, -0.05014154314994812, 1,
|
|
2495
|
+
],
|
|
2496
|
+
radius: 0.006629410665482283,
|
|
2497
|
+
},
|
|
2498
|
+
'ring-finger-metacarpal': {
|
|
2499
|
+
offsetMatrix: [
|
|
2500
|
+
0.9616971015930176, -0.13805118203163147, 0.2368120402097702, 0,
|
|
2501
|
+
0.0005348679260350764, 0.8648636937141418, 0.5020061135292053, 0,
|
|
2502
|
+
-0.2741127610206604, -0.48265108466148376, 0.8318111300468445, 0,
|
|
2503
|
+
-0.05402477830648422, 0.015797706320881844, 0.08152295649051666, 1,
|
|
2504
|
+
],
|
|
2505
|
+
radius: 0.019088275730609894,
|
|
2506
|
+
},
|
|
2507
|
+
'ring-finger-phalanx-proximal': {
|
|
2508
|
+
offsetMatrix: [
|
|
2509
|
+
0.9940828680992126, 0.05735103040933609, 0.09224652498960495, 0,
|
|
2510
|
+
-0.10022822767496109, 0.8116500377655029, 0.5754809379577637, 0,
|
|
2511
|
+
-0.041867565363645554, -0.5813214182853699, 0.8125960826873779, 0,
|
|
2512
|
+
-0.041623555123806, 0.04171867296099663, 0.03582974523305893, 1,
|
|
2513
|
+
],
|
|
2514
|
+
radius: 0.00992213748395443,
|
|
2515
|
+
},
|
|
2516
|
+
'ring-finger-phalanx-intermediate': {
|
|
2517
|
+
offsetMatrix: [
|
|
2518
|
+
0.9843675494194031, 0.12044742703437805, 0.12850022315979004, 0,
|
|
2519
|
+
-0.15629759430885315, 0.9337108135223389, 0.3221098482608795, 0,
|
|
2520
|
+
-0.08118485659360886, -0.3371586799621582, 0.937940776348114, 0,
|
|
2521
|
+
-0.039990875869989395, 0.06438793987035751, 0.004141641780734062, 1,
|
|
2522
|
+
],
|
|
2523
|
+
radius: 0.007611672393977642,
|
|
2524
|
+
},
|
|
2525
|
+
'ring-finger-phalanx-distal': {
|
|
2526
|
+
offsetMatrix: [
|
|
2527
|
+
0.9748351573944092, 0.11857274919748306, 0.18877571821212769, 0,
|
|
2528
|
+
-0.15575434267520905, 0.9681083559989929, 0.19623035192489624, 0,
|
|
2529
|
+
-0.15948788821697235, -0.22069483995437622, 0.9622148275375366, 0,
|
|
2530
|
+
-0.03783353418111801, 0.07334739714860916, -0.020782606676220894, 1,
|
|
2531
|
+
],
|
|
2532
|
+
radius: 0.007231088820844889,
|
|
2533
|
+
},
|
|
2534
|
+
'ring-finger-tip': {
|
|
2535
|
+
offsetMatrix: [
|
|
2536
|
+
0.9748351573944092, 0.11857274919748306, 0.18877571821212769, 0,
|
|
2537
|
+
-0.15575434267520905, 0.9681083559989929, 0.19623035192489624, 0,
|
|
2538
|
+
-0.15948788821697235, -0.22069483995437622, 0.9622148275375366, 0,
|
|
2539
|
+
-0.03445569798350334, 0.0802423357963562, -0.04392268508672714, 1,
|
|
2540
|
+
],
|
|
2541
|
+
radius: 0.0062310886569321156,
|
|
2542
|
+
},
|
|
2543
|
+
'pinky-finger-metacarpal': {
|
|
2544
|
+
offsetMatrix: [
|
|
2545
|
+
0.9181402921676636, 0.35625091195106506, 0.17350243031978607, 0,
|
|
2546
|
+
-0.39615097641944885, 0.8352503180503845, 0.38134080171585083, 0,
|
|
2547
|
+
-0.009065053425729275, -0.41885748505592346, 0.9080066680908203, 0,
|
|
2548
|
+
-0.06191859766840935, 0.013620133511722088, 0.07850203663110733, 1,
|
|
2549
|
+
],
|
|
2550
|
+
radius: 0.01808827556669712,
|
|
2551
|
+
},
|
|
2552
|
+
'pinky-finger-phalanx-proximal': {
|
|
2553
|
+
offsetMatrix: [
|
|
2554
|
+
0.9714386463165283, 0.236698180437088, -0.016745081171393394, 0,
|
|
2555
|
+
-0.18462024629116058, 0.7982627749443054, 0.5733163952827454, 0,
|
|
2556
|
+
0.14906984567642212, -0.5538501739501953, 0.8191629648208618, 0,
|
|
2557
|
+
-0.061502378433942795, 0.032741155475378036, 0.03705105185508728, 1,
|
|
2558
|
+
],
|
|
2559
|
+
radius: 0.008483353070914745,
|
|
2560
|
+
},
|
|
2561
|
+
'pinky-finger-phalanx-intermediate': {
|
|
2562
|
+
offsetMatrix: [
|
|
2563
|
+
0.9337416291236877, 0.35620439052581787, -0.03527557849884033, 0,
|
|
2564
|
+
-0.33203884959220886, 0.8987522721290588, 0.28634607791900635, 0,
|
|
2565
|
+
0.13370157778263092, -0.2556603252887726, 0.9574766755104065, 0,
|
|
2566
|
+
-0.06608185172080994, 0.049755651503801346, 0.011886020191013813, 1,
|
|
2567
|
+
],
|
|
2568
|
+
radius: 0.0067641944624483585,
|
|
2569
|
+
},
|
|
2570
|
+
'pinky-finger-phalanx-distal': {
|
|
2571
|
+
offsetMatrix: [
|
|
2572
|
+
0.9419984817504883, 0.3303581774234772, 0.059175245463848114, 0,
|
|
2573
|
+
-0.33483216166496277, 0.9130291938781738, 0.23294763267040253, 0,
|
|
2574
|
+
0.02292730286717415, -0.2392500638961792, 0.970687210559845, 0,
|
|
2575
|
+
-0.0687975287437439, 0.054948460310697556, -0.007561664097011089, 1,
|
|
2576
|
+
],
|
|
2577
|
+
radius: 0.0064259846694767475,
|
|
2578
|
+
},
|
|
2579
|
+
'pinky-finger-tip': {
|
|
2580
|
+
offsetMatrix: [
|
|
2581
|
+
0.9419984817504883, 0.3303581774234772, 0.059175245463848114, 0,
|
|
2582
|
+
-0.33483216166496277, 0.9130291938781738, 0.23294763267040253, 0,
|
|
2583
|
+
0.02292730286717415, -0.2392500638961792, 0.970687210559845, 0,
|
|
2584
|
+
-0.06947512179613113, 0.0613851435482502, -0.028543535619974136, 1,
|
|
2585
|
+
],
|
|
2586
|
+
radius: 0.005425984505563974,
|
|
2587
|
+
},
|
|
2588
|
+
},
|
|
2589
|
+
gripOffsetMatrix: [
|
|
2590
|
+
-0.0005348679260350764, -0.8648636937141418, -0.5020061135292053, 0,
|
|
2591
|
+
-0.2741127908229828, -0.48265108466148376, 0.8318111896514893, 0,
|
|
2592
|
+
-0.9616971015930176, 0.13805119693279266, -0.2368120402097702, 0,
|
|
2593
|
+
-0.02878567762672901, 0.0017147823236882687, 0.04536811262369156, 1,
|
|
2594
|
+
],
|
|
2595
|
+
};
|
|
2596
|
+
|
|
2597
|
+
const oculusHandConfig = {
|
|
2598
|
+
profileId: 'oculus-hand',
|
|
2599
|
+
fallbackProfileIds: [
|
|
2600
|
+
'generic-hand',
|
|
2601
|
+
'generic-hand-select',
|
|
2602
|
+
'generic-trigger',
|
|
2603
|
+
],
|
|
2604
|
+
poses: {
|
|
2605
|
+
default: relaxedHandPose,
|
|
2606
|
+
pinch: pinchHandPose,
|
|
2607
|
+
point: pointHandPose,
|
|
2608
|
+
},
|
|
2609
|
+
};
|
|
2610
|
+
const XRHandGamepadConfig = {
|
|
2611
|
+
mapping: GamepadMappingType.None,
|
|
2612
|
+
buttons: [{ id: 'pinch', type: 'analog', eventTrigger: 'select' }],
|
|
2613
|
+
axes: [],
|
|
2614
|
+
};
|
|
2615
|
+
const fromPosition = create$2();
|
|
2616
|
+
const fromQuaternion = create();
|
|
2617
|
+
const fromScale = create$2();
|
|
2618
|
+
const toPosition = create$2();
|
|
2619
|
+
const toQuaternion = create();
|
|
2620
|
+
const toScale = create$2();
|
|
2621
|
+
const interpolatedPosition = create$2();
|
|
2622
|
+
const interpolatedQuaternion = create();
|
|
2623
|
+
const interpolatedScale = create$2();
|
|
2624
|
+
const interpolateMatrix = (out, fromMatrix, toMatrix, alpha) => {
|
|
2625
|
+
getTranslation(fromPosition, fromMatrix);
|
|
2626
|
+
getRotation(fromQuaternion, fromMatrix);
|
|
2627
|
+
getScaling(fromScale, fromMatrix);
|
|
2628
|
+
getTranslation(toPosition, toMatrix);
|
|
2629
|
+
getRotation(toQuaternion, toMatrix);
|
|
2630
|
+
getScaling(toScale, toMatrix);
|
|
2631
|
+
lerp(interpolatedPosition, fromPosition, toPosition, alpha);
|
|
2632
|
+
slerp(interpolatedQuaternion, fromQuaternion, toQuaternion, alpha);
|
|
2633
|
+
lerp(interpolatedScale, fromScale, toScale, alpha);
|
|
2634
|
+
fromRotationTranslationScale(out, interpolatedQuaternion, interpolatedPosition, interpolatedScale);
|
|
2635
|
+
return out;
|
|
2636
|
+
};
|
|
2637
|
+
const mirrorMultiplierMatrix = [
|
|
2638
|
+
1, -1, -1, 0, -1, 1, 1, 0, -1, 1, 1, 0, -1, 1, 1, 1,
|
|
2639
|
+
];
|
|
2640
|
+
const mirrorMatrixToRight = (matrixLeft) => {
|
|
2641
|
+
for (let i = 0; i < 16; i++) {
|
|
2642
|
+
matrixLeft[i] *= mirrorMultiplierMatrix[i];
|
|
2643
|
+
}
|
|
2644
|
+
};
|
|
2645
|
+
const PRIVATE$e = Symbol('@immersive-web-emulation-runtime/xr-hand-input');
|
|
2646
|
+
class XRHandInput extends XRTrackedInput {
|
|
2647
|
+
constructor(handInputConfig, handedness, globalSpace) {
|
|
2648
|
+
if (handedness !== XRHandedness.Left && handedness !== XRHandedness.Right) {
|
|
2649
|
+
throw new DOMException('handedness for XRHandInput must be either "left" or "right"', 'InvalidStateError');
|
|
2650
|
+
}
|
|
2651
|
+
if (!handInputConfig.poses.default || !handInputConfig.poses.pinch) {
|
|
2652
|
+
throw new DOMException('"default" and "pinch" hand pose configs are required', 'InvalidStateError');
|
|
2653
|
+
}
|
|
2654
|
+
const targetRaySpace = new XRSpace(globalSpace);
|
|
2655
|
+
const gripSpace = new XRSpace(targetRaySpace);
|
|
2656
|
+
const profiles = [
|
|
2657
|
+
handInputConfig.profileId,
|
|
2658
|
+
...handInputConfig.fallbackProfileIds,
|
|
2659
|
+
];
|
|
2660
|
+
const hand = new XRHand();
|
|
2661
|
+
Object.values(XRHandJoint).forEach((jointName) => {
|
|
2662
|
+
hand.set(jointName, new XRJointSpace(jointName, targetRaySpace));
|
|
2663
|
+
});
|
|
2664
|
+
const inputSource = new XRInputSource(handedness, XRTargetRayMode.TrackedPointer, profiles, targetRaySpace, new Gamepad(XRHandGamepadConfig), gripSpace, hand);
|
|
2665
|
+
super(inputSource);
|
|
2666
|
+
this[PRIVATE$e] = {
|
|
2667
|
+
poseId: 'default',
|
|
2668
|
+
poses: handInputConfig.poses,
|
|
2669
|
+
};
|
|
2670
|
+
this.updateHandPose();
|
|
2671
|
+
}
|
|
2672
|
+
get poseId() {
|
|
2673
|
+
return this[PRIVATE$e].poseId;
|
|
2674
|
+
}
|
|
2675
|
+
set poseId(poseId) {
|
|
2676
|
+
if (!this[PRIVATE$e].poses[poseId]) {
|
|
2677
|
+
console.warn(`Pose config ${poseId} not found`);
|
|
2678
|
+
return;
|
|
2679
|
+
}
|
|
2680
|
+
this[PRIVATE$e].poseId = poseId;
|
|
2681
|
+
}
|
|
2682
|
+
updateHandPose() {
|
|
2683
|
+
const targetPose = this[PRIVATE$e].poses[this[PRIVATE$e].poseId];
|
|
2684
|
+
const pinchPose = this[PRIVATE$e].poses.pinch;
|
|
2685
|
+
Object.values(XRHandJoint).forEach((jointName) => {
|
|
2686
|
+
const targetJointMatrix = targetPose.jointTransforms[jointName].offsetMatrix;
|
|
2687
|
+
const pinchJointMatrix = pinchPose.jointTransforms[jointName].offsetMatrix;
|
|
2688
|
+
const jointSpace = this.inputSource.hand.get(jointName);
|
|
2689
|
+
interpolateMatrix(jointSpace[PRIVATE$k].offsetMatrix, targetJointMatrix, pinchJointMatrix, this.pinchValue);
|
|
2690
|
+
if (this.inputSource.handedness === XRHandedness.Right) {
|
|
2691
|
+
mirrorMatrixToRight(jointSpace[PRIVATE$k].offsetMatrix);
|
|
2692
|
+
}
|
|
2693
|
+
jointSpace[PRIVATE$f].radius =
|
|
2694
|
+
(1 - this.pinchValue) * targetPose.jointTransforms[jointName].radius +
|
|
2695
|
+
this.pinchValue * pinchPose.jointTransforms[jointName].radius;
|
|
2696
|
+
});
|
|
2697
|
+
if (targetPose.gripOffsetMatrix && pinchPose.gripOffsetMatrix) {
|
|
2698
|
+
interpolateMatrix(this.inputSource.gripSpace[PRIVATE$k].offsetMatrix, targetPose.gripOffsetMatrix, pinchPose.gripOffsetMatrix, this.pinchValue);
|
|
2699
|
+
}
|
|
2700
|
+
}
|
|
2701
|
+
get pinchValue() {
|
|
2702
|
+
return this[PRIVATE$h].inputSource.gamepad[PRIVATE$j]
|
|
2703
|
+
.buttonsMap['pinch'].value;
|
|
2704
|
+
}
|
|
2705
|
+
updatePinchValue(value) {
|
|
2706
|
+
if (value > 1 || value < 0) {
|
|
2707
|
+
console.warn(`Out-of-range value ${value} provided for pinch`);
|
|
2708
|
+
return;
|
|
2709
|
+
}
|
|
2710
|
+
const gamepadButton = this[PRIVATE$h].inputSource.gamepad[PRIVATE$j]
|
|
2711
|
+
.buttonsMap['pinch'];
|
|
2712
|
+
gamepadButton[PRIVATE$j].pendingValue = value;
|
|
2713
|
+
}
|
|
2714
|
+
onFrameStart(frame) {
|
|
2715
|
+
super.onFrameStart(frame);
|
|
2716
|
+
this.updateHandPose();
|
|
2717
|
+
}
|
|
2718
|
+
}
|
|
2719
|
+
|
|
2720
|
+
const PRIVATE$d = Symbol('@immersive-web-emulation-runtime/xr-pose');
|
|
2721
|
+
class XRPose {
|
|
2722
|
+
constructor(transform, emulatedPosition = false, linearVelocity = undefined, angularVelocity = undefined) {
|
|
2723
|
+
this[PRIVATE$d] = {
|
|
2724
|
+
transform,
|
|
2725
|
+
emulatedPosition,
|
|
2726
|
+
linearVelocity,
|
|
2727
|
+
angularVelocity,
|
|
2728
|
+
};
|
|
2729
|
+
}
|
|
2730
|
+
get transform() {
|
|
2731
|
+
return this[PRIVATE$d].transform;
|
|
2732
|
+
}
|
|
2733
|
+
get emulatedPosition() {
|
|
2734
|
+
return this[PRIVATE$d].emulatedPosition;
|
|
2735
|
+
}
|
|
2736
|
+
get linearVelocity() {
|
|
2737
|
+
return this[PRIVATE$d].linearVelocity;
|
|
2738
|
+
}
|
|
2739
|
+
get angularVelocity() {
|
|
2740
|
+
return this[PRIVATE$d].angularVelocity;
|
|
2741
|
+
}
|
|
2742
|
+
}
|
|
2743
|
+
|
|
2744
|
+
const PRIVATE$c = Symbol('@immersive-web-emulation-runtime/xr-joint-pose');
|
|
2745
|
+
class XRJointPose extends XRPose {
|
|
2746
|
+
constructor(transform, radius, emulatedPosition = false, linearVelocity = undefined, angularVelocity = undefined) {
|
|
2747
|
+
super(transform, emulatedPosition, linearVelocity, angularVelocity);
|
|
2748
|
+
this[PRIVATE$c] = { radius };
|
|
2749
|
+
}
|
|
2750
|
+
get radius() {
|
|
2751
|
+
return this[PRIVATE$c].radius;
|
|
2752
|
+
}
|
|
2753
|
+
}
|
|
2754
|
+
|
|
2755
|
+
class PolyfillDOMPointReadOnly {
|
|
2756
|
+
constructor(x = 0, y = 0, z = 0, w = 1) {
|
|
2757
|
+
this.x = x;
|
|
2758
|
+
this.y = y;
|
|
2759
|
+
this.z = z;
|
|
2760
|
+
this.w = w;
|
|
2761
|
+
Object.freeze(this);
|
|
2762
|
+
}
|
|
2763
|
+
static fromPoint(other) {
|
|
2764
|
+
return new PolyfillDOMPointReadOnly(other.x, other.y, other.z, other.w);
|
|
2765
|
+
}
|
|
2766
|
+
matrixTransform(_matrix) {
|
|
2767
|
+
// Implement matrix transformation logic here
|
|
2768
|
+
// This is a placeholder implementation
|
|
2769
|
+
return new PolyfillDOMPointReadOnly();
|
|
2770
|
+
}
|
|
2771
|
+
toJSON() {
|
|
2772
|
+
// Implement toJSON logic here
|
|
2773
|
+
// This is a placeholder implementation
|
|
2774
|
+
return { x: this.x, y: this.y, z: this.z, w: this.w };
|
|
2775
|
+
}
|
|
2776
|
+
}
|
|
2777
|
+
const DOMPointReadOnly = typeof globalThis.DOMPointReadOnly !== 'undefined'
|
|
2778
|
+
? globalThis.DOMPointReadOnly
|
|
2779
|
+
: PolyfillDOMPointReadOnly;
|
|
2780
|
+
|
|
2781
|
+
const PRIVATE$b = Symbol('@immersive-web-emulation-runtime/xr-rigid-transform');
|
|
2782
|
+
class XRRigidTransform {
|
|
2783
|
+
constructor(position, orientation) {
|
|
2784
|
+
// Default values
|
|
2785
|
+
const defaultPosition = fromValues$2(0, 0, 0);
|
|
2786
|
+
const defaultOrientation = create();
|
|
2787
|
+
this[PRIVATE$b] = {
|
|
2788
|
+
matrix: create$3(),
|
|
2789
|
+
position: position
|
|
2790
|
+
? fromValues$2(position.x, position.y, position.z)
|
|
2791
|
+
: defaultPosition,
|
|
2792
|
+
orientation: orientation
|
|
2793
|
+
? normalize(create(), fromValues(orientation.x, orientation.y, orientation.z, orientation.w))
|
|
2794
|
+
: defaultOrientation,
|
|
2795
|
+
inverse: null,
|
|
2796
|
+
};
|
|
2797
|
+
this.updateMatrix();
|
|
2798
|
+
}
|
|
2799
|
+
updateMatrix() {
|
|
2800
|
+
fromRotationTranslation(this[PRIVATE$b].matrix, this[PRIVATE$b].orientation, this[PRIVATE$b].position);
|
|
2801
|
+
}
|
|
2802
|
+
get matrix() {
|
|
2803
|
+
return this[PRIVATE$b].matrix;
|
|
2804
|
+
}
|
|
2805
|
+
get position() {
|
|
2806
|
+
const pos = this[PRIVATE$b].position;
|
|
2807
|
+
return new DOMPointReadOnly(pos[0], pos[1], pos[2], 1);
|
|
2808
|
+
}
|
|
2809
|
+
get orientation() {
|
|
2810
|
+
const ori = this[PRIVATE$b].orientation;
|
|
2811
|
+
return new DOMPointReadOnly(ori[0], ori[1], ori[2], ori[3]);
|
|
2812
|
+
}
|
|
2813
|
+
get inverse() {
|
|
2814
|
+
if (!this[PRIVATE$b].inverse) {
|
|
2815
|
+
const invMatrix = create$3();
|
|
2816
|
+
if (!invert(invMatrix, this[PRIVATE$b].matrix)) {
|
|
2817
|
+
throw new Error('Matrix is not invertible.');
|
|
2818
|
+
}
|
|
2819
|
+
// Decomposing the inverse matrix into position and orientation
|
|
2820
|
+
let invPosition = create$2();
|
|
2821
|
+
getTranslation(invPosition, invMatrix);
|
|
2822
|
+
let invOrientation = create();
|
|
2823
|
+
getRotation(invOrientation, invMatrix);
|
|
2824
|
+
// Creating a new XRRigidTransform for the inverse
|
|
2825
|
+
this[PRIVATE$b].inverse = new XRRigidTransform(new DOMPointReadOnly(invPosition[0], invPosition[1], invPosition[2], 1), new DOMPointReadOnly(invOrientation[0], invOrientation[1], invOrientation[2], invOrientation[3]));
|
|
2826
|
+
// Setting the inverse of the inverse to be this transform
|
|
2827
|
+
this[PRIVATE$b].inverse[PRIVATE$b].inverse = this;
|
|
2828
|
+
}
|
|
2829
|
+
return this[PRIVATE$b].inverse;
|
|
2830
|
+
}
|
|
2831
|
+
}
|
|
2832
|
+
|
|
2833
|
+
const PRIVATE$a = Symbol('@immersive-web-emulation-runtime/xr-viewer-pose');
|
|
2834
|
+
class XRViewerPose extends XRPose {
|
|
2835
|
+
constructor(transform, views, emulatedPosition = false, linearVelocity = undefined, angularVelocity = undefined) {
|
|
2836
|
+
super(transform, emulatedPosition, linearVelocity, angularVelocity);
|
|
2837
|
+
this[PRIVATE$a] = {
|
|
2838
|
+
views: Object.freeze(views),
|
|
2839
|
+
};
|
|
2840
|
+
}
|
|
2841
|
+
get views() {
|
|
2842
|
+
return this[PRIVATE$a].views;
|
|
2843
|
+
}
|
|
2844
|
+
}
|
|
2845
|
+
|
|
2846
|
+
const PRIVATE$9 = Symbol('@immersive-web-emulation-runtime/xr-frame');
|
|
2847
|
+
const spaceGlobalMatrix = create$3();
|
|
2848
|
+
const baseSpaceGlobalMatrix = create$3();
|
|
2849
|
+
const baseSpaceGlobalMatrixInverse = create$3();
|
|
2850
|
+
const getOffsetMatrix = (offsetMatrix, space, baseSpace) => {
|
|
2851
|
+
XRSpaceUtils.calculateGlobalOffsetMatrix(space, spaceGlobalMatrix);
|
|
2852
|
+
XRSpaceUtils.calculateGlobalOffsetMatrix(baseSpace, baseSpaceGlobalMatrix);
|
|
2853
|
+
invert(baseSpaceGlobalMatrixInverse, baseSpaceGlobalMatrix);
|
|
2854
|
+
multiply$1(offsetMatrix, baseSpaceGlobalMatrixInverse, spaceGlobalMatrix);
|
|
2855
|
+
};
|
|
2856
|
+
class XRFrame {
|
|
2857
|
+
constructor(session, id, active, animationFrame, predictedDisplayTime) {
|
|
2858
|
+
this[PRIVATE$9] = {
|
|
2859
|
+
session,
|
|
2860
|
+
id,
|
|
2861
|
+
active,
|
|
2862
|
+
animationFrame,
|
|
2863
|
+
predictedDisplayTime,
|
|
2864
|
+
tempMat4: create$3(),
|
|
2865
|
+
};
|
|
2866
|
+
}
|
|
2867
|
+
get session() {
|
|
2868
|
+
return this[PRIVATE$9].session;
|
|
2869
|
+
}
|
|
2870
|
+
get predictedDisplayTime() {
|
|
2871
|
+
return this[PRIVATE$9].predictedDisplayTime;
|
|
2872
|
+
}
|
|
2873
|
+
getPose(space, baseSpace) {
|
|
2874
|
+
if (!this[PRIVATE$9].active) {
|
|
2875
|
+
throw new DOMException('XRFrame access outside the callback that produced it is invalid.', 'InvalidStateError');
|
|
2876
|
+
}
|
|
2877
|
+
getOffsetMatrix(this[PRIVATE$9].tempMat4, space, baseSpace);
|
|
2878
|
+
const position = create$2();
|
|
2879
|
+
getTranslation(position, this[PRIVATE$9].tempMat4);
|
|
2880
|
+
const orientation = create();
|
|
2881
|
+
getRotation(orientation, this[PRIVATE$9].tempMat4);
|
|
2882
|
+
return new XRPose(new XRRigidTransform({ x: position[0], y: position[1], z: position[2], w: 1.0 }, {
|
|
2883
|
+
x: orientation[0],
|
|
2884
|
+
y: orientation[1],
|
|
2885
|
+
z: orientation[2],
|
|
2886
|
+
w: orientation[3],
|
|
2887
|
+
}), space[PRIVATE$k].emulated);
|
|
2888
|
+
}
|
|
2889
|
+
getViewerPose(referenceSpace) {
|
|
2890
|
+
if (!this[PRIVATE$9].animationFrame) {
|
|
2891
|
+
throw new DOMException('getViewerPose can only be called on XRFrame objects passed to XRSession.requestAnimationFrame callbacks.', 'InvalidStateError');
|
|
2892
|
+
}
|
|
2893
|
+
const session = this[PRIVATE$9].session;
|
|
2894
|
+
const device = session[PRIVATE$6].device;
|
|
2895
|
+
const pose = this.getPose(device.viewerSpace, referenceSpace);
|
|
2896
|
+
const eyes = session[PRIVATE$6].mode === XRSessionMode.Inline
|
|
2897
|
+
? [XREye.None]
|
|
2898
|
+
: [XREye.Left, XREye.Right];
|
|
2899
|
+
const views = [];
|
|
2900
|
+
eyes.forEach((eye) => {
|
|
2901
|
+
const viewSpace = device.viewSpaces[eye];
|
|
2902
|
+
const viewPose = this.getPose(viewSpace, referenceSpace);
|
|
2903
|
+
const projectionMatrix = session[PRIVATE$6].getProjectionMatrix(eye);
|
|
2904
|
+
const view = new XRView(eye, new Float32Array(projectionMatrix), viewPose.transform, session);
|
|
2905
|
+
views.push(view);
|
|
2906
|
+
});
|
|
2907
|
+
return new XRViewerPose(pose.transform, views, false);
|
|
2908
|
+
}
|
|
2909
|
+
getJointPose(joint, baseSpace) {
|
|
2910
|
+
const xrPose = this.getPose(joint, baseSpace);
|
|
2911
|
+
const radius = joint[PRIVATE$f].radius;
|
|
2912
|
+
return new XRJointPose(xrPose.transform, radius, false);
|
|
2913
|
+
}
|
|
2914
|
+
fillJointRadii(jointSpaces, radii) {
|
|
2915
|
+
// converting from sequence type to array
|
|
2916
|
+
jointSpaces = Array.from(jointSpaces);
|
|
2917
|
+
if (!this[PRIVATE$9].active) {
|
|
2918
|
+
throw new DOMException('XRFrame access outside the callback that produced it is invalid.', 'InvalidStateError');
|
|
2919
|
+
}
|
|
2920
|
+
if (jointSpaces.length > radii.length) {
|
|
2921
|
+
throw new DOMException('The length of jointSpaces is larger than the number of elements in radii', 'TypeError');
|
|
2922
|
+
}
|
|
2923
|
+
let allValid = true;
|
|
2924
|
+
for (let offset = 0; offset < jointSpaces.length; offset++) {
|
|
2925
|
+
if (!jointSpaces[offset][PRIVATE$f].radius) {
|
|
2926
|
+
radii[offset] = NaN;
|
|
2927
|
+
allValid = false;
|
|
2928
|
+
}
|
|
2929
|
+
else {
|
|
2930
|
+
radii[offset] = jointSpaces[offset][PRIVATE$f].radius;
|
|
2931
|
+
}
|
|
2932
|
+
}
|
|
2933
|
+
return allValid;
|
|
2934
|
+
}
|
|
2935
|
+
fillPoses(spaces, baseSpace, transforms) {
|
|
2936
|
+
// converting from sequence type to array
|
|
2937
|
+
spaces = Array.from(spaces);
|
|
2938
|
+
if (!this[PRIVATE$9].active) {
|
|
2939
|
+
throw new DOMException('XRFrame access outside the callback that produced it is invalid.', 'InvalidStateError');
|
|
2940
|
+
}
|
|
2941
|
+
if (spaces.length * 16 > transforms.length) {
|
|
2942
|
+
throw new DOMException('The length of spaces multiplied by 16 is larger than the number of elements in transforms', 'TypeError');
|
|
2943
|
+
}
|
|
2944
|
+
spaces.forEach((space, i) => {
|
|
2945
|
+
getOffsetMatrix(this[PRIVATE$9].tempMat4, space, baseSpace);
|
|
2946
|
+
for (let j = 0; j < 16; j++) {
|
|
2947
|
+
transforms[i * 16 + j] = this[PRIVATE$9].tempMat4[j];
|
|
2948
|
+
}
|
|
2949
|
+
});
|
|
2950
|
+
return true;
|
|
2951
|
+
}
|
|
2952
|
+
}
|
|
2953
|
+
|
|
2954
|
+
class XRInputSourcesChangeEvent extends Event {
|
|
2955
|
+
constructor(type, eventInitDict) {
|
|
2956
|
+
super(type, eventInitDict);
|
|
2957
|
+
if (!eventInitDict.session) {
|
|
2958
|
+
throw new Error('XRInputSourcesChangeEventInit.session is required');
|
|
2959
|
+
}
|
|
2960
|
+
if (!eventInitDict.added) {
|
|
2961
|
+
throw new Error('XRInputSourcesChangeEventInit.added is required');
|
|
2962
|
+
}
|
|
2963
|
+
if (!eventInitDict.removed) {
|
|
2964
|
+
throw new Error('XRInputSourcesChangeEventInit.removed is required');
|
|
2965
|
+
}
|
|
2966
|
+
this.session = eventInitDict.session;
|
|
2967
|
+
this.added = eventInitDict.added;
|
|
2968
|
+
this.removed = eventInitDict.removed;
|
|
2969
|
+
}
|
|
2970
|
+
}
|
|
2971
|
+
|
|
2972
|
+
var _a;
|
|
2973
|
+
const PRIVATE$8 = Symbol('@immersive-web-emulation-runtime/xr-reference-space');
|
|
2974
|
+
var XRReferenceSpaceType;
|
|
2975
|
+
(function (XRReferenceSpaceType) {
|
|
2976
|
+
XRReferenceSpaceType["Viewer"] = "viewer";
|
|
2977
|
+
XRReferenceSpaceType["Local"] = "local";
|
|
2978
|
+
XRReferenceSpaceType["LocalFloor"] = "local-floor";
|
|
2979
|
+
XRReferenceSpaceType["BoundedFloor"] = "bounded-floor";
|
|
2980
|
+
XRReferenceSpaceType["Unbounded"] = "unbounded";
|
|
2981
|
+
})(XRReferenceSpaceType || (XRReferenceSpaceType = {}));
|
|
2982
|
+
class XRReferenceSpace extends XRSpace {
|
|
2983
|
+
constructor(type, parentSpace, offsetMatrix) {
|
|
2984
|
+
super(parentSpace, offsetMatrix);
|
|
2985
|
+
this[_a] = {
|
|
2986
|
+
type: null,
|
|
2987
|
+
onreset: () => { },
|
|
2988
|
+
};
|
|
2989
|
+
this[PRIVATE$8].type = type;
|
|
2990
|
+
}
|
|
2991
|
+
get onreset() {
|
|
2992
|
+
var _b;
|
|
2993
|
+
return (_b = this[PRIVATE$8].onreset) !== null && _b !== void 0 ? _b : (() => { });
|
|
2994
|
+
}
|
|
2995
|
+
set onreset(callback) {
|
|
2996
|
+
if (this[PRIVATE$8].onreset) {
|
|
2997
|
+
this.removeEventListener('reset', this[PRIVATE$8].onreset);
|
|
2998
|
+
}
|
|
2999
|
+
this[PRIVATE$8].onreset = callback;
|
|
3000
|
+
if (callback) {
|
|
3001
|
+
this.addEventListener('reset', callback);
|
|
3002
|
+
}
|
|
3003
|
+
}
|
|
3004
|
+
// Create a new XRReferenceSpace with an offset from the current space
|
|
3005
|
+
getOffsetReferenceSpace(originOffset) {
|
|
3006
|
+
// Create a new XRReferenceSpace with the originOffset as its offsetMatrix
|
|
3007
|
+
// The new space's parent is set to 'this' (the current XRReferenceSpace)
|
|
3008
|
+
return new XRReferenceSpace(this[PRIVATE$8].type, this, originOffset);
|
|
3009
|
+
}
|
|
3010
|
+
}
|
|
3011
|
+
_a = PRIVATE$8;
|
|
3012
|
+
|
|
3013
|
+
const PRIVATE$7 = Symbol('@immersive-web-emulation-runtime/xr-render-state');
|
|
3014
|
+
class XRRenderState {
|
|
3015
|
+
constructor(init = {}, oldState) {
|
|
3016
|
+
this[PRIVATE$7] = {
|
|
3017
|
+
depthNear: init.depthNear || (oldState === null || oldState === void 0 ? void 0 : oldState.depthNear) || 0.1,
|
|
3018
|
+
depthFar: init.depthFar || (oldState === null || oldState === void 0 ? void 0 : oldState.depthFar) || 1000.0,
|
|
3019
|
+
inlineVerticalFieldOfView: init.inlineVerticalFieldOfView ||
|
|
3020
|
+
(oldState === null || oldState === void 0 ? void 0 : oldState.inlineVerticalFieldOfView) ||
|
|
3021
|
+
null,
|
|
3022
|
+
baseLayer: init.baseLayer || (oldState === null || oldState === void 0 ? void 0 : oldState.baseLayer) || null,
|
|
3023
|
+
};
|
|
3024
|
+
}
|
|
3025
|
+
get depthNear() {
|
|
3026
|
+
return this[PRIVATE$7].depthNear;
|
|
3027
|
+
}
|
|
3028
|
+
get depthFar() {
|
|
3029
|
+
return this[PRIVATE$7].depthFar;
|
|
3030
|
+
}
|
|
3031
|
+
get inlineVerticalFieldOfView() {
|
|
3032
|
+
return this[PRIVATE$7].inlineVerticalFieldOfView;
|
|
3033
|
+
}
|
|
3034
|
+
get baseLayer() {
|
|
3035
|
+
return this[PRIVATE$7].baseLayer;
|
|
3036
|
+
}
|
|
3037
|
+
}
|
|
3038
|
+
|
|
3039
|
+
class XRSessionEvent extends Event {
|
|
3040
|
+
constructor(type, eventInitDict) {
|
|
3041
|
+
super(type, eventInitDict);
|
|
3042
|
+
if (!eventInitDict.session) {
|
|
3043
|
+
throw new Error('XRSessionEventInit.session is required');
|
|
3044
|
+
}
|
|
3045
|
+
this.session = eventInitDict.session;
|
|
3046
|
+
}
|
|
3047
|
+
}
|
|
3048
|
+
|
|
3049
|
+
var XRVisibilityState;
|
|
3050
|
+
(function (XRVisibilityState) {
|
|
3051
|
+
XRVisibilityState["Visible"] = "visible";
|
|
3052
|
+
XRVisibilityState["VisibleBlurred"] = "visible-blurred";
|
|
3053
|
+
XRVisibilityState["Hidden"] = "hidden";
|
|
3054
|
+
})(XRVisibilityState || (XRVisibilityState = {}));
|
|
3055
|
+
var XRSessionMode;
|
|
3056
|
+
(function (XRSessionMode) {
|
|
3057
|
+
XRSessionMode["Inline"] = "inline";
|
|
3058
|
+
XRSessionMode["ImmersiveVR"] = "immersive-vr";
|
|
3059
|
+
XRSessionMode["ImmersiveAR"] = "immersive-ar";
|
|
3060
|
+
})(XRSessionMode || (XRSessionMode = {}));
|
|
3061
|
+
const PRIVATE$6 = Symbol('@immersive-web-emulation-runtime/xr-session');
|
|
3062
|
+
class XRSession extends EventTarget {
|
|
3063
|
+
constructor(device, mode, enabledFeatures) {
|
|
3064
|
+
super();
|
|
3065
|
+
this[PRIVATE$6] = {
|
|
3066
|
+
device,
|
|
3067
|
+
mode,
|
|
3068
|
+
renderState: new XRRenderState(),
|
|
3069
|
+
pendingRenderState: null,
|
|
3070
|
+
enabledFeatures: enabledFeatures,
|
|
3071
|
+
isSystemKeyboardSupported: false,
|
|
3072
|
+
ended: false,
|
|
3073
|
+
projectionMatrices: {
|
|
3074
|
+
[XREye.Left]: create$3(),
|
|
3075
|
+
[XREye.Right]: create$3(),
|
|
3076
|
+
[XREye.None]: create$3(),
|
|
3077
|
+
},
|
|
3078
|
+
getProjectionMatrix: (eye) => {
|
|
3079
|
+
return this[PRIVATE$6].projectionMatrices[eye];
|
|
3080
|
+
},
|
|
3081
|
+
referenceSpaceIsSupported: (referenceSpaceType) => {
|
|
3082
|
+
if (!this[PRIVATE$6].enabledFeatures.includes(referenceSpaceType)) {
|
|
3083
|
+
return false;
|
|
3084
|
+
}
|
|
3085
|
+
switch (referenceSpaceType) {
|
|
3086
|
+
case XRReferenceSpaceType.Viewer:
|
|
3087
|
+
return true;
|
|
3088
|
+
case XRReferenceSpaceType.Local:
|
|
3089
|
+
case XRReferenceSpaceType.LocalFloor:
|
|
3090
|
+
case XRReferenceSpaceType.BoundedFloor:
|
|
3091
|
+
case XRReferenceSpaceType.Unbounded:
|
|
3092
|
+
return this[PRIVATE$6].mode != XRSessionMode.Inline;
|
|
3093
|
+
}
|
|
3094
|
+
},
|
|
3095
|
+
frameHandle: 0,
|
|
3096
|
+
frameCallbacks: [],
|
|
3097
|
+
currentFrameCallbacks: null,
|
|
3098
|
+
onDeviceFrame: () => {
|
|
3099
|
+
if (this[PRIVATE$6].ended) {
|
|
3100
|
+
return;
|
|
3101
|
+
}
|
|
3102
|
+
this[PRIVATE$6].deviceFrameHandle = globalThis.requestAnimationFrame(this[PRIVATE$6].onDeviceFrame);
|
|
3103
|
+
if (this[PRIVATE$6].pendingRenderState != null) {
|
|
3104
|
+
this[PRIVATE$6].renderState = this[PRIVATE$6].pendingRenderState;
|
|
3105
|
+
this[PRIVATE$6].pendingRenderState = null;
|
|
3106
|
+
this[PRIVATE$6].device[PRIVATE$1].onBaseLayerSet(this[PRIVATE$6].renderState.baseLayer);
|
|
3107
|
+
}
|
|
3108
|
+
const baseLayer = this[PRIVATE$6].renderState.baseLayer;
|
|
3109
|
+
if (baseLayer === null) {
|
|
3110
|
+
return;
|
|
3111
|
+
}
|
|
3112
|
+
const context = baseLayer.context;
|
|
3113
|
+
const canvas = context.canvas;
|
|
3114
|
+
/**
|
|
3115
|
+
* This code snippet is designed to clear the buffers attached to an opaque framebuffer
|
|
3116
|
+
* at the beginning of each XR animation frame, but it only applies to immersive XR sessions.
|
|
3117
|
+
* The process is as follows:
|
|
3118
|
+
*
|
|
3119
|
+
* 1. Check if the session is immersive: It verifies if `session.immersive` is true.
|
|
3120
|
+
* This ensures that the buffer clearing operations are only performed for immersive
|
|
3121
|
+
* sessions, which have exclusive access to the XR device's display.
|
|
3122
|
+
*
|
|
3123
|
+
* 2. Save current clear values: The current clear values for the color, depth, and
|
|
3124
|
+
* stencil buffers are stored. These values need to be restored after clearing the
|
|
3125
|
+
* buffers to maintain the application's rendering state as expected.
|
|
3126
|
+
*
|
|
3127
|
+
* 3. Set clear values to defaults: The clear color is set to transparent black, the
|
|
3128
|
+
* clear depth to the maximum depth value (1.0), and the clear stencil to 0. This
|
|
3129
|
+
* ensures that the buffers are reset to a known state, free from any residual data.
|
|
3130
|
+
*
|
|
3131
|
+
* 4. Clear the buffers: The depth, color, and stencil buffers are cleared, removing
|
|
3132
|
+
* any content from previous frames and preparing them for new rendering operations.
|
|
3133
|
+
*
|
|
3134
|
+
* 5. Restore previous clear values: The original clear values are reinstated to return
|
|
3135
|
+
* the WebGL context to its state prior to this operation, allowing subsequent rendering
|
|
3136
|
+
* to proceed without interference.
|
|
3137
|
+
*
|
|
3138
|
+
* This clearing process is crucial for some XR devices to function correctly and to
|
|
3139
|
+
* prevent rendering artifacts from past frames. It ensures that each new frame starts
|
|
3140
|
+
* with a clean slate.
|
|
3141
|
+
*/
|
|
3142
|
+
if (this[PRIVATE$6].mode != XRSessionMode.Inline) {
|
|
3143
|
+
const currentClearColor = context.getParameter(context.COLOR_CLEAR_VALUE);
|
|
3144
|
+
const currentClearDepth = context.getParameter(context.DEPTH_CLEAR_VALUE);
|
|
3145
|
+
const currentClearStencil = context.getParameter(context.STENCIL_CLEAR_VALUE);
|
|
3146
|
+
context.clearColor(0.0, 0.0, 0.0, 0.0);
|
|
3147
|
+
context.clearDepth(1);
|
|
3148
|
+
context.clearStencil(0.0);
|
|
3149
|
+
context.clear(context.DEPTH_BUFFER_BIT |
|
|
3150
|
+
context.COLOR_BUFFER_BIT |
|
|
3151
|
+
context.STENCIL_BUFFER_BIT);
|
|
3152
|
+
context.clearColor(currentClearColor[0], currentClearColor[1], currentClearColor[2], currentClearColor[3]);
|
|
3153
|
+
context.clearDepth(currentClearDepth);
|
|
3154
|
+
context.clearStencil(currentClearStencil);
|
|
3155
|
+
}
|
|
3156
|
+
// Calculate projection matrices
|
|
3157
|
+
const { depthNear, depthFar } = this[PRIVATE$6].renderState;
|
|
3158
|
+
const { width, height } = canvas;
|
|
3159
|
+
if (this[PRIVATE$6].mode !== XRSessionMode.Inline) {
|
|
3160
|
+
const aspect = (width * (this[PRIVATE$6].device.stereoEnabled ? 0.5 : 1.0)) / height;
|
|
3161
|
+
perspective(this[PRIVATE$6].projectionMatrices[XREye.Left], this[PRIVATE$6].device.fovy, aspect, depthNear, depthFar);
|
|
3162
|
+
copy$3(this[PRIVATE$6].projectionMatrices[XREye.Right], this[PRIVATE$6].projectionMatrices[XREye.Left]);
|
|
3163
|
+
}
|
|
3164
|
+
else {
|
|
3165
|
+
const aspect = width / height;
|
|
3166
|
+
perspective(this[PRIVATE$6].projectionMatrices[XREye.None], this[PRIVATE$6].renderState.inlineVerticalFieldOfView, aspect, depthNear, depthFar);
|
|
3167
|
+
}
|
|
3168
|
+
const frame = new XRFrame(this, this[PRIVATE$6].frameHandle, true, true, performance.now());
|
|
3169
|
+
this[PRIVATE$6].device[PRIVATE$1].onFrameStart(frame);
|
|
3170
|
+
this[PRIVATE$6].updateActiveInputSources();
|
|
3171
|
+
/*
|
|
3172
|
+
* For each entry in callbacks, in order:
|
|
3173
|
+
* - If the entry’s cancelled boolean is true, continue to the next entry.
|
|
3174
|
+
* - Invoke the Web IDL callback function, passing now and frame as the arguments.
|
|
3175
|
+
* - If an exception is thrown, report the exception.
|
|
3176
|
+
*/
|
|
3177
|
+
// - Let callbacks be a list of the entries in session’s list of animation frame
|
|
3178
|
+
// callback, in the order in which they were added to the list.
|
|
3179
|
+
const callbacks = (this[PRIVATE$6].currentFrameCallbacks =
|
|
3180
|
+
this[PRIVATE$6].frameCallbacks);
|
|
3181
|
+
// - Set session’s list of animation frame callbacks to the empty list.
|
|
3182
|
+
this[PRIVATE$6].frameCallbacks = [];
|
|
3183
|
+
const rightNow = performance.now();
|
|
3184
|
+
for (let i = 0; i < callbacks.length; i++) {
|
|
3185
|
+
try {
|
|
3186
|
+
if (!callbacks[i].cancelled) {
|
|
3187
|
+
callbacks[i].callback(rightNow, frame);
|
|
3188
|
+
}
|
|
3189
|
+
}
|
|
3190
|
+
catch (err) {
|
|
3191
|
+
console.error(err);
|
|
3192
|
+
}
|
|
3193
|
+
}
|
|
3194
|
+
this[PRIVATE$6].currentFrameCallbacks = null;
|
|
3195
|
+
// - Set frame’s active boolean to false.
|
|
3196
|
+
frame[PRIVATE$9].active = false;
|
|
3197
|
+
},
|
|
3198
|
+
nominalFrameRate: device.internalNominalFrameRate,
|
|
3199
|
+
referenceSpaces: [],
|
|
3200
|
+
inputSourceArray: [],
|
|
3201
|
+
activeInputSources: [],
|
|
3202
|
+
updateActiveInputSources: () => {
|
|
3203
|
+
const handTrackingOn = this[PRIVATE$6].enabledFeatures.includes(WebXRFeatures.HandTracking);
|
|
3204
|
+
const prevInputs = this[PRIVATE$6].activeInputSources;
|
|
3205
|
+
const currInputs = this[PRIVATE$6].device.inputSources.filter((inputSource) => !inputSource.hand || handTrackingOn);
|
|
3206
|
+
const added = currInputs.filter((item) => !prevInputs.includes(item));
|
|
3207
|
+
const removed = prevInputs.filter((item) => !currInputs.includes(item));
|
|
3208
|
+
if (added.length > 0 || removed.length > 0) {
|
|
3209
|
+
this.dispatchEvent(new XRInputSourcesChangeEvent('inputsourceschange', {
|
|
3210
|
+
session: this,
|
|
3211
|
+
added,
|
|
3212
|
+
removed,
|
|
3213
|
+
}));
|
|
3214
|
+
}
|
|
3215
|
+
this[PRIVATE$6].activeInputSources = currInputs;
|
|
3216
|
+
},
|
|
3217
|
+
onend: null,
|
|
3218
|
+
oninputsourceschange: null,
|
|
3219
|
+
onselect: null,
|
|
3220
|
+
onselectstart: null,
|
|
3221
|
+
onselectend: null,
|
|
3222
|
+
onsqueeze: null,
|
|
3223
|
+
onsqueezestart: null,
|
|
3224
|
+
onsqueezeend: null,
|
|
3225
|
+
onvisibilitychange: null,
|
|
3226
|
+
onframeratechange: null,
|
|
3227
|
+
};
|
|
3228
|
+
// start the frameloop
|
|
3229
|
+
this[PRIVATE$6].onDeviceFrame();
|
|
3230
|
+
}
|
|
3231
|
+
get visibilityState() {
|
|
3232
|
+
return this[PRIVATE$6].device.visibilityState;
|
|
3233
|
+
}
|
|
3234
|
+
get frameRate() {
|
|
3235
|
+
return this[PRIVATE$6].nominalFrameRate;
|
|
3236
|
+
}
|
|
3237
|
+
get supportedFrameRates() {
|
|
3238
|
+
return new Float32Array(this[PRIVATE$6].device.supportedFrameRates);
|
|
3239
|
+
}
|
|
3240
|
+
get renderState() {
|
|
3241
|
+
return this[PRIVATE$6].renderState;
|
|
3242
|
+
}
|
|
3243
|
+
get inputSources() {
|
|
3244
|
+
// use the same array object
|
|
3245
|
+
this[PRIVATE$6].inputSourceArray.length = 0;
|
|
3246
|
+
if (!this[PRIVATE$6].ended && this[PRIVATE$6].mode !== XRSessionMode.Inline) {
|
|
3247
|
+
this[PRIVATE$6].inputSourceArray.push(...this[PRIVATE$6].activeInputSources);
|
|
3248
|
+
}
|
|
3249
|
+
return this[PRIVATE$6].inputSourceArray;
|
|
3250
|
+
}
|
|
3251
|
+
get enabledFeatures() {
|
|
3252
|
+
return this[PRIVATE$6].enabledFeatures;
|
|
3253
|
+
}
|
|
3254
|
+
get isSystemKeyboardSupported() {
|
|
3255
|
+
return this[PRIVATE$6].isSystemKeyboardSupported;
|
|
3256
|
+
}
|
|
3257
|
+
updateRenderState(state = {}) {
|
|
3258
|
+
if (this[PRIVATE$6].ended) {
|
|
3259
|
+
throw new DOMException('XRSession has already ended.', 'InvalidStateError');
|
|
3260
|
+
}
|
|
3261
|
+
if (state.baseLayer &&
|
|
3262
|
+
state.baseLayer[PRIVATE$5].session !== this) {
|
|
3263
|
+
throw new DOMException('Base layer was created by a different XRSession', 'InvalidStateError');
|
|
3264
|
+
}
|
|
3265
|
+
if (state.inlineVerticalFieldOfView != null &&
|
|
3266
|
+
this[PRIVATE$6].mode !== XRSessionMode.Inline) {
|
|
3267
|
+
throw new DOMException('InlineVerticalFieldOfView must not be set for an immersive session', 'InvalidStateError');
|
|
3268
|
+
}
|
|
3269
|
+
this[PRIVATE$6].pendingRenderState = new XRRenderState(state, this[PRIVATE$6].renderState);
|
|
3270
|
+
}
|
|
3271
|
+
// the nominal frame rate updates are emulated, no actual update to the
|
|
3272
|
+
// display frame rate of the device will be executed
|
|
3273
|
+
async updateTargetFrameRate(rate) {
|
|
3274
|
+
return new Promise((resolve, reject) => {
|
|
3275
|
+
if (this[PRIVATE$6].ended) {
|
|
3276
|
+
reject(new DOMException('XRSession has already ended.', 'InvalidStateError'));
|
|
3277
|
+
}
|
|
3278
|
+
else if (!this[PRIVATE$6].device.supportedFrameRates.includes(rate)) {
|
|
3279
|
+
reject(new DOMException('Requested frame rate not supported.', 'InvalidStateError'));
|
|
3280
|
+
}
|
|
3281
|
+
else {
|
|
3282
|
+
if (this[PRIVATE$6].nominalFrameRate === rate) {
|
|
3283
|
+
console.log(`Requested frame rate is the same as the current nominal frame rate, no update made`);
|
|
3284
|
+
}
|
|
3285
|
+
else {
|
|
3286
|
+
this[PRIVATE$6].nominalFrameRate = rate;
|
|
3287
|
+
this.dispatchEvent(new XRSessionEvent('frameratechange', { session: this }));
|
|
3288
|
+
console.log(`Nominal frame rate updated to ${rate}`);
|
|
3289
|
+
}
|
|
3290
|
+
resolve();
|
|
3291
|
+
}
|
|
3292
|
+
});
|
|
3293
|
+
}
|
|
3294
|
+
async requestReferenceSpace(type) {
|
|
3295
|
+
return new Promise((resolve, reject) => {
|
|
3296
|
+
if (this[PRIVATE$6].ended ||
|
|
3297
|
+
!this[PRIVATE$6].referenceSpaceIsSupported(type)) {
|
|
3298
|
+
reject(new DOMException('The requested reference space type is not supported.', 'NotSupportedError'));
|
|
3299
|
+
return;
|
|
3300
|
+
}
|
|
3301
|
+
let referenceSpace;
|
|
3302
|
+
switch (type) {
|
|
3303
|
+
case XRReferenceSpaceType.Viewer:
|
|
3304
|
+
referenceSpace = this[PRIVATE$6].device.viewerSpace;
|
|
3305
|
+
break;
|
|
3306
|
+
case XRReferenceSpaceType.Local:
|
|
3307
|
+
// creating an XRReferenceSpace with the current headset transform in global space
|
|
3308
|
+
referenceSpace = new XRReferenceSpace(type, this[PRIVATE$6].device[PRIVATE$1].globalSpace, this[PRIVATE$6].device.viewerSpace[PRIVATE$k].offsetMatrix);
|
|
3309
|
+
break;
|
|
3310
|
+
case XRReferenceSpaceType.LocalFloor:
|
|
3311
|
+
case XRReferenceSpaceType.BoundedFloor:
|
|
3312
|
+
case XRReferenceSpaceType.Unbounded:
|
|
3313
|
+
// TO-DO: add boundary geometry for bounded-floor
|
|
3314
|
+
referenceSpace = new XRReferenceSpace(type, this[PRIVATE$6].device[PRIVATE$1].globalSpace);
|
|
3315
|
+
break;
|
|
3316
|
+
}
|
|
3317
|
+
this[PRIVATE$6].referenceSpaces.push(referenceSpace);
|
|
3318
|
+
resolve(referenceSpace);
|
|
3319
|
+
});
|
|
3320
|
+
}
|
|
3321
|
+
requestAnimationFrame(callback) {
|
|
3322
|
+
if (this[PRIVATE$6].ended) {
|
|
3323
|
+
return 0;
|
|
3324
|
+
}
|
|
3325
|
+
const frameHandle = ++this[PRIVATE$6].frameHandle;
|
|
3326
|
+
this[PRIVATE$6].frameCallbacks.push({
|
|
3327
|
+
handle: frameHandle,
|
|
3328
|
+
callback,
|
|
3329
|
+
cancelled: false,
|
|
3330
|
+
});
|
|
3331
|
+
return frameHandle;
|
|
3332
|
+
}
|
|
3333
|
+
cancelAnimationFrame(handle) {
|
|
3334
|
+
// Remove the callback with that handle from the queue
|
|
3335
|
+
let callbacks = this[PRIVATE$6].frameCallbacks;
|
|
3336
|
+
let index = callbacks.findIndex((d) => d && d.handle === handle);
|
|
3337
|
+
if (index > -1) {
|
|
3338
|
+
callbacks[index].cancelled = true;
|
|
3339
|
+
callbacks.splice(index, 1);
|
|
3340
|
+
}
|
|
3341
|
+
// If cancelAnimationFrame is called from within a frame callback, also check
|
|
3342
|
+
// the remaining callbacks for the current frame:
|
|
3343
|
+
callbacks = this[PRIVATE$6].currentFrameCallbacks;
|
|
3344
|
+
if (callbacks) {
|
|
3345
|
+
index = callbacks.findIndex((d) => d && d.handle === handle);
|
|
3346
|
+
if (index > -1) {
|
|
3347
|
+
callbacks[index].cancelled = true;
|
|
3348
|
+
// Rely on cancelled flag only; don't mutate this array while it's being iterated
|
|
3349
|
+
}
|
|
3350
|
+
}
|
|
3351
|
+
}
|
|
3352
|
+
async end() {
|
|
3353
|
+
return new Promise((resolve, reject) => {
|
|
3354
|
+
if (this[PRIVATE$6].ended || this[PRIVATE$6].deviceFrameHandle === null) {
|
|
3355
|
+
reject(new DOMException('XRSession has already ended.', 'InvalidStateError'));
|
|
3356
|
+
}
|
|
3357
|
+
else {
|
|
3358
|
+
globalThis.cancelAnimationFrame(this[PRIVATE$6].deviceFrameHandle);
|
|
3359
|
+
this[PRIVATE$6].device[PRIVATE$1].onSessionEnd();
|
|
3360
|
+
this.dispatchEvent(new XRSessionEvent('end', { session: this }));
|
|
3361
|
+
resolve();
|
|
3362
|
+
}
|
|
3363
|
+
});
|
|
3364
|
+
}
|
|
3365
|
+
// events
|
|
3366
|
+
get onend() {
|
|
3367
|
+
var _a;
|
|
3368
|
+
return (_a = this[PRIVATE$6].onend) !== null && _a !== void 0 ? _a : (() => { });
|
|
3369
|
+
}
|
|
3370
|
+
set onend(callback) {
|
|
3371
|
+
if (this[PRIVATE$6].onend) {
|
|
3372
|
+
this.removeEventListener('end', this[PRIVATE$6].onend);
|
|
3373
|
+
}
|
|
3374
|
+
this[PRIVATE$6].onend = callback;
|
|
3375
|
+
if (callback) {
|
|
3376
|
+
this.addEventListener('end', callback);
|
|
3377
|
+
}
|
|
3378
|
+
}
|
|
3379
|
+
get oninputsourceschange() {
|
|
3380
|
+
var _a;
|
|
3381
|
+
return (_a = this[PRIVATE$6].oninputsourceschange) !== null && _a !== void 0 ? _a : (() => { });
|
|
3382
|
+
}
|
|
3383
|
+
set oninputsourceschange(callback) {
|
|
3384
|
+
if (this[PRIVATE$6].oninputsourceschange) {
|
|
3385
|
+
this.removeEventListener('inputsourceschange', this[PRIVATE$6].oninputsourceschange);
|
|
3386
|
+
}
|
|
3387
|
+
this[PRIVATE$6].oninputsourceschange = callback;
|
|
3388
|
+
if (callback) {
|
|
3389
|
+
this.addEventListener('inputsourceschange', callback);
|
|
3390
|
+
}
|
|
3391
|
+
}
|
|
3392
|
+
get onselect() {
|
|
3393
|
+
var _a;
|
|
3394
|
+
return (_a = this[PRIVATE$6].onselect) !== null && _a !== void 0 ? _a : (() => { });
|
|
3395
|
+
}
|
|
3396
|
+
set onselect(callback) {
|
|
3397
|
+
if (this[PRIVATE$6].onselect) {
|
|
3398
|
+
this.removeEventListener('select', this[PRIVATE$6].onselect);
|
|
3399
|
+
}
|
|
3400
|
+
this[PRIVATE$6].onselect = callback;
|
|
3401
|
+
if (callback) {
|
|
3402
|
+
this.addEventListener('select', callback);
|
|
3403
|
+
}
|
|
3404
|
+
}
|
|
3405
|
+
get onselectstart() {
|
|
3406
|
+
var _a;
|
|
3407
|
+
return (_a = this[PRIVATE$6].onselectstart) !== null && _a !== void 0 ? _a : (() => { });
|
|
3408
|
+
}
|
|
3409
|
+
set onselectstart(callback) {
|
|
3410
|
+
if (this[PRIVATE$6].onselectstart) {
|
|
3411
|
+
this.removeEventListener('selectstart', this[PRIVATE$6].onselectstart);
|
|
3412
|
+
}
|
|
3413
|
+
this[PRIVATE$6].onselectstart = callback;
|
|
3414
|
+
if (callback) {
|
|
3415
|
+
this.addEventListener('selectstart', callback);
|
|
3416
|
+
}
|
|
3417
|
+
}
|
|
3418
|
+
get onselectend() {
|
|
3419
|
+
var _a;
|
|
3420
|
+
return (_a = this[PRIVATE$6].onselectend) !== null && _a !== void 0 ? _a : (() => { });
|
|
3421
|
+
}
|
|
3422
|
+
set onselectend(callback) {
|
|
3423
|
+
if (this[PRIVATE$6].onselectend) {
|
|
3424
|
+
this.removeEventListener('selectend', this[PRIVATE$6].onselectend);
|
|
3425
|
+
}
|
|
3426
|
+
this[PRIVATE$6].onselectend = callback;
|
|
3427
|
+
if (callback) {
|
|
3428
|
+
this.addEventListener('selectend', callback);
|
|
3429
|
+
}
|
|
3430
|
+
}
|
|
3431
|
+
get onsqueeze() {
|
|
3432
|
+
var _a;
|
|
3433
|
+
return (_a = this[PRIVATE$6].onsqueeze) !== null && _a !== void 0 ? _a : (() => { });
|
|
3434
|
+
}
|
|
3435
|
+
set onsqueeze(callback) {
|
|
3436
|
+
if (this[PRIVATE$6].onsqueeze) {
|
|
3437
|
+
this.removeEventListener('squeeze', this[PRIVATE$6].onsqueeze);
|
|
3438
|
+
}
|
|
3439
|
+
this[PRIVATE$6].onsqueeze = callback;
|
|
3440
|
+
if (callback) {
|
|
3441
|
+
this.addEventListener('squeeze', callback);
|
|
3442
|
+
}
|
|
3443
|
+
}
|
|
3444
|
+
get onsqueezestart() {
|
|
3445
|
+
var _a;
|
|
3446
|
+
return (_a = this[PRIVATE$6].onsqueezestart) !== null && _a !== void 0 ? _a : (() => { });
|
|
3447
|
+
}
|
|
3448
|
+
set onsqueezestart(callback) {
|
|
3449
|
+
if (this[PRIVATE$6].onsqueezestart) {
|
|
3450
|
+
this.removeEventListener('squeezestart', this[PRIVATE$6].onsqueezestart);
|
|
3451
|
+
}
|
|
3452
|
+
this[PRIVATE$6].onsqueezestart = callback;
|
|
3453
|
+
if (callback) {
|
|
3454
|
+
this.addEventListener('squeezestart', callback);
|
|
3455
|
+
}
|
|
3456
|
+
}
|
|
3457
|
+
get onsqueezeend() {
|
|
3458
|
+
var _a;
|
|
3459
|
+
return (_a = this[PRIVATE$6].onsqueezeend) !== null && _a !== void 0 ? _a : (() => { });
|
|
3460
|
+
}
|
|
3461
|
+
set onsqueezeend(callback) {
|
|
3462
|
+
if (this[PRIVATE$6].onsqueezeend) {
|
|
3463
|
+
this.removeEventListener('squeezeend', this[PRIVATE$6].onsqueezeend);
|
|
3464
|
+
}
|
|
3465
|
+
this[PRIVATE$6].onsqueezeend = callback;
|
|
3466
|
+
if (callback) {
|
|
3467
|
+
this.addEventListener('squeezeend', callback);
|
|
3468
|
+
}
|
|
3469
|
+
}
|
|
3470
|
+
get onvisibilitychange() {
|
|
3471
|
+
var _a;
|
|
3472
|
+
return (_a = this[PRIVATE$6].onvisibilitychange) !== null && _a !== void 0 ? _a : (() => { });
|
|
3473
|
+
}
|
|
3474
|
+
set onvisibilitychange(callback) {
|
|
3475
|
+
if (this[PRIVATE$6].onvisibilitychange) {
|
|
3476
|
+
this.removeEventListener('visibilitychange', this[PRIVATE$6].onvisibilitychange);
|
|
3477
|
+
}
|
|
3478
|
+
this[PRIVATE$6].onvisibilitychange = callback;
|
|
3479
|
+
if (callback) {
|
|
3480
|
+
this.addEventListener('visibilitychange', callback);
|
|
3481
|
+
}
|
|
3482
|
+
}
|
|
3483
|
+
get onframeratechange() {
|
|
3484
|
+
var _a;
|
|
3485
|
+
return (_a = this[PRIVATE$6].onframeratechange) !== null && _a !== void 0 ? _a : (() => { });
|
|
3486
|
+
}
|
|
3487
|
+
set onframeratechange(callback) {
|
|
3488
|
+
if (this[PRIVATE$6].onframeratechange) {
|
|
3489
|
+
this.removeEventListener('frameratechange', this[PRIVATE$6].onframeratechange);
|
|
3490
|
+
}
|
|
3491
|
+
this[PRIVATE$6].onframeratechange = callback;
|
|
3492
|
+
if (callback) {
|
|
3493
|
+
this.addEventListener('frameratechange', callback);
|
|
3494
|
+
}
|
|
3495
|
+
}
|
|
3496
|
+
}
|
|
3497
|
+
|
|
3498
|
+
class XRLayer extends EventTarget {
|
|
3499
|
+
}
|
|
3500
|
+
const PRIVATE$5 = Symbol('@immersive-web-emulation-runtime/XRWebGLLayer');
|
|
3501
|
+
const defaultLayerInit = {
|
|
3502
|
+
antialias: true,
|
|
3503
|
+
depth: true,
|
|
3504
|
+
stencil: false,
|
|
3505
|
+
alpha: true,
|
|
3506
|
+
ignoreDepthValues: false,
|
|
3507
|
+
framebufferScaleFactor: 1.0,
|
|
3508
|
+
};
|
|
3509
|
+
class XRWebGLLayer extends XRLayer {
|
|
3510
|
+
constructor(session, context, layerInit = {}) {
|
|
3511
|
+
super();
|
|
3512
|
+
if (session[PRIVATE$6].ended) {
|
|
3513
|
+
throw new DOMException('Session has ended', 'InvalidStateError');
|
|
3514
|
+
}
|
|
3515
|
+
// TO-DO: Check that the context attribute has xrCompatible set to true
|
|
3516
|
+
// may require polyfilling the context and perhaps canvas.getContext
|
|
3517
|
+
// Default values for XRWebGLLayerInit, can be overridden by layerInit
|
|
3518
|
+
const config = { ...defaultLayerInit, ...layerInit };
|
|
3519
|
+
this[PRIVATE$5] = {
|
|
3520
|
+
session,
|
|
3521
|
+
context,
|
|
3522
|
+
antialias: config.antialias,
|
|
3523
|
+
};
|
|
3524
|
+
}
|
|
3525
|
+
get context() {
|
|
3526
|
+
return this[PRIVATE$5].context;
|
|
3527
|
+
}
|
|
3528
|
+
get antialias() {
|
|
3529
|
+
return this[PRIVATE$5].antialias;
|
|
3530
|
+
}
|
|
3531
|
+
get ignoreDepthValues() {
|
|
3532
|
+
return true;
|
|
3533
|
+
}
|
|
3534
|
+
get framebuffer() {
|
|
3535
|
+
return null;
|
|
3536
|
+
}
|
|
3537
|
+
get framebufferWidth() {
|
|
3538
|
+
return this[PRIVATE$5].context.drawingBufferWidth;
|
|
3539
|
+
}
|
|
3540
|
+
get framebufferHeight() {
|
|
3541
|
+
return this[PRIVATE$5].context.drawingBufferHeight;
|
|
3542
|
+
}
|
|
3543
|
+
getViewport(view) {
|
|
3544
|
+
if (view[PRIVATE$g].session !== this[PRIVATE$5].session) {
|
|
3545
|
+
throw new DOMException("View's session differs from Layer's session", 'InvalidStateError');
|
|
3546
|
+
}
|
|
3547
|
+
// TO-DO: check frame
|
|
3548
|
+
return this[PRIVATE$5].session[PRIVATE$6].device[PRIVATE$1].getViewport(this, view);
|
|
3549
|
+
}
|
|
3550
|
+
static getNativeFramebufferScaleFactor(session) {
|
|
3551
|
+
if (!(session instanceof XRSession)) {
|
|
3552
|
+
throw new TypeError('getNativeFramebufferScaleFactor must be passed a session.');
|
|
3553
|
+
}
|
|
3554
|
+
if (session[PRIVATE$6].ended) {
|
|
3555
|
+
return 0.0;
|
|
3556
|
+
}
|
|
3557
|
+
// Return 1.0 for simplicity, actual implementation might vary based on the device capabilities
|
|
3558
|
+
return 1.0;
|
|
3559
|
+
}
|
|
3560
|
+
}
|
|
3561
|
+
|
|
3562
|
+
const PRIVATE$4 = Symbol('@immersive-web-emulation-runtime/action-player');
|
|
3563
|
+
class ActionPlayer {
|
|
3564
|
+
constructor(refSpace, recording, ipd) {
|
|
3565
|
+
const { schema, frames } = recording;
|
|
3566
|
+
if (!frames || !schema || frames.length === 0) {
|
|
3567
|
+
throw new DOMException('wrong recording format', 'NotSupportedError');
|
|
3568
|
+
}
|
|
3569
|
+
const viewerSpace = new XRReferenceSpace(XRReferenceSpaceType.Viewer, refSpace);
|
|
3570
|
+
const viewSpaces = {
|
|
3571
|
+
[XREye.Left]: new XRSpace(viewerSpace),
|
|
3572
|
+
[XREye.Right]: new XRSpace(viewerSpace),
|
|
3573
|
+
[XREye.None]: new XRSpace(viewerSpace),
|
|
3574
|
+
};
|
|
3575
|
+
this[PRIVATE$4] = {
|
|
3576
|
+
refSpace,
|
|
3577
|
+
inputSources: new Map(),
|
|
3578
|
+
inputSchemas: new Map(),
|
|
3579
|
+
frames,
|
|
3580
|
+
recordedFramePointer: 0,
|
|
3581
|
+
startingTimeStamp: frames[0][0],
|
|
3582
|
+
endingTimeStamp: frames[frames.length - 1][0],
|
|
3583
|
+
playbackTime: frames[0][0],
|
|
3584
|
+
playing: false,
|
|
3585
|
+
viewerSpace,
|
|
3586
|
+
viewSpaces,
|
|
3587
|
+
vec3: create$2(),
|
|
3588
|
+
quat: create(),
|
|
3589
|
+
};
|
|
3590
|
+
fromTranslation(this[PRIVATE$4].viewSpaces[XREye.Left][PRIVATE$k].offsetMatrix, fromValues$2(-ipd / 2, 0, 0));
|
|
3591
|
+
fromTranslation(this[PRIVATE$4].viewSpaces[XREye.Right][PRIVATE$k].offsetMatrix, fromValues$2(ipd / 2, 0, 0));
|
|
3592
|
+
schema.forEach((schemaEntry) => {
|
|
3593
|
+
const index = schemaEntry[0];
|
|
3594
|
+
const schema = schemaEntry[1];
|
|
3595
|
+
let gamepad;
|
|
3596
|
+
if (schema.hasGamepad) {
|
|
3597
|
+
const buttons = [];
|
|
3598
|
+
for (let i = 0; i < schema.numButtons; i++) {
|
|
3599
|
+
buttons.push({ id: i.toString(), type: 'manual' });
|
|
3600
|
+
}
|
|
3601
|
+
const axes = [];
|
|
3602
|
+
for (let i = 0; i < schema.numAxes; i++) {
|
|
3603
|
+
axes.push({ id: i.toString(), type: 'manual' });
|
|
3604
|
+
}
|
|
3605
|
+
gamepad = new Gamepad({
|
|
3606
|
+
mapping: schema.mapping,
|
|
3607
|
+
buttons,
|
|
3608
|
+
axes,
|
|
3609
|
+
});
|
|
3610
|
+
}
|
|
3611
|
+
const targetRaySpace = new XRSpace(refSpace);
|
|
3612
|
+
let hand = undefined;
|
|
3613
|
+
if (schema.hasHand) {
|
|
3614
|
+
hand = new XRHand();
|
|
3615
|
+
Object.values(XRHandJoint).forEach((jointName) => {
|
|
3616
|
+
hand.set(jointName, new XRJointSpace(jointName, targetRaySpace));
|
|
3617
|
+
});
|
|
3618
|
+
}
|
|
3619
|
+
const inputSource = new XRInputSource(schema.handedness, schema.targetRayMode, schema.profiles, targetRaySpace, gamepad, schema.hasGrip ? new XRSpace(refSpace) : undefined, schema.hasHand ? hand : undefined);
|
|
3620
|
+
this[PRIVATE$4].inputSources.set(index, {
|
|
3621
|
+
active: false,
|
|
3622
|
+
source: inputSource,
|
|
3623
|
+
});
|
|
3624
|
+
this[PRIVATE$4].inputSchemas.set(index, schema);
|
|
3625
|
+
});
|
|
3626
|
+
}
|
|
3627
|
+
play() {
|
|
3628
|
+
this[PRIVATE$4].recordedFramePointer = 0;
|
|
3629
|
+
this[PRIVATE$4].playbackTime = this[PRIVATE$4].startingTimeStamp;
|
|
3630
|
+
this[PRIVATE$4].playing = true;
|
|
3631
|
+
this[PRIVATE$4].actualTimeStamp = performance.now();
|
|
3632
|
+
}
|
|
3633
|
+
stop() {
|
|
3634
|
+
this[PRIVATE$4].playing = false;
|
|
3635
|
+
}
|
|
3636
|
+
get playing() {
|
|
3637
|
+
return this[PRIVATE$4].playing;
|
|
3638
|
+
}
|
|
3639
|
+
get viewerSpace() {
|
|
3640
|
+
return this[PRIVATE$4].viewerSpace;
|
|
3641
|
+
}
|
|
3642
|
+
get viewSpaces() {
|
|
3643
|
+
return this[PRIVATE$4].viewSpaces;
|
|
3644
|
+
}
|
|
3645
|
+
get inputSources() {
|
|
3646
|
+
return Array.from(this[PRIVATE$4].inputSources.values())
|
|
3647
|
+
.filter((wrapper) => wrapper.active)
|
|
3648
|
+
.map((wrapper) => wrapper.source);
|
|
3649
|
+
}
|
|
3650
|
+
playFrame() {
|
|
3651
|
+
const now = performance.now();
|
|
3652
|
+
const delta = now - this[PRIVATE$4].actualTimeStamp;
|
|
3653
|
+
this[PRIVATE$4].actualTimeStamp = now;
|
|
3654
|
+
this[PRIVATE$4].playbackTime += delta;
|
|
3655
|
+
if (this[PRIVATE$4].playbackTime > this[PRIVATE$4].endingTimeStamp) {
|
|
3656
|
+
this.stop();
|
|
3657
|
+
return;
|
|
3658
|
+
}
|
|
3659
|
+
while (this[PRIVATE$4].frames[this[PRIVATE$4].recordedFramePointer + 1][0] < this[PRIVATE$4].playbackTime) {
|
|
3660
|
+
this[PRIVATE$4].recordedFramePointer++;
|
|
3661
|
+
}
|
|
3662
|
+
const lastFrameData = this[PRIVATE$4].frames[this[PRIVATE$4].recordedFramePointer];
|
|
3663
|
+
const nextFrameData = this[PRIVATE$4].frames[this[PRIVATE$4].recordedFramePointer + 1];
|
|
3664
|
+
const alpha = (this[PRIVATE$4].playbackTime - lastFrameData[0]) /
|
|
3665
|
+
(nextFrameData[0] - lastFrameData[0]);
|
|
3666
|
+
this.updateXRSpaceFromMergedFrames(this[PRIVATE$4].viewerSpace, lastFrameData.slice(1, 8), nextFrameData.slice(1, 8), alpha);
|
|
3667
|
+
const lastFrameInputs = new Map();
|
|
3668
|
+
for (let i = 8; i < lastFrameData.length; i++) {
|
|
3669
|
+
const { index, inputData } = this.processRawInputData(lastFrameData[i]);
|
|
3670
|
+
lastFrameInputs.set(index, inputData);
|
|
3671
|
+
}
|
|
3672
|
+
const nextFrameInputs = new Map();
|
|
3673
|
+
for (let i = 8; i < nextFrameData.length; i++) {
|
|
3674
|
+
const { index, inputData } = this.processRawInputData(nextFrameData[i]);
|
|
3675
|
+
nextFrameInputs.set(index, inputData);
|
|
3676
|
+
}
|
|
3677
|
+
this[PRIVATE$4].inputSources.forEach((sourceWrapper) => {
|
|
3678
|
+
sourceWrapper.active = false;
|
|
3679
|
+
});
|
|
3680
|
+
nextFrameInputs.forEach((inputData, index) => {
|
|
3681
|
+
this[PRIVATE$4].inputSources.get(index).active = true;
|
|
3682
|
+
const inputSource = this[PRIVATE$4].inputSources.get(index).source;
|
|
3683
|
+
const schema = this[PRIVATE$4].inputSchemas.get(index);
|
|
3684
|
+
this.updateInputSource(inputSource, schema, lastFrameInputs.has(index) ? lastFrameInputs.get(index) : inputData, inputData, alpha);
|
|
3685
|
+
});
|
|
3686
|
+
}
|
|
3687
|
+
updateInputSource(inputSource, schema, lastInputData, nextInputData, alpha) {
|
|
3688
|
+
this.updateXRSpaceFromMergedFrames(inputSource.targetRaySpace, lastInputData.targetRayTransform, nextInputData.targetRayTransform, alpha);
|
|
3689
|
+
if (schema.hasGrip) {
|
|
3690
|
+
this.updateXRSpaceFromMergedFrames(inputSource.gripSpace, lastInputData.gripTransform, nextInputData.gripTransform, alpha);
|
|
3691
|
+
}
|
|
3692
|
+
if (schema.hasHand) {
|
|
3693
|
+
for (let i = 0; i < 25; i++) {
|
|
3694
|
+
const lastTransformArray = lastInputData.handTransforms.slice(i * 8, i * 8 + 7);
|
|
3695
|
+
const nextTransformArray = nextInputData.handTransforms.slice(i * 8, i * 8 + 7);
|
|
3696
|
+
const lastRadius = lastInputData.handTransforms[i * 8 + 7];
|
|
3697
|
+
const nextRadius = nextInputData.handTransforms[i * 8 + 7];
|
|
3698
|
+
const jointSpace = inputSource.hand.get(schema.jointSequence[i]);
|
|
3699
|
+
this.updateXRSpaceFromMergedFrames(jointSpace, lastTransformArray, nextTransformArray, alpha);
|
|
3700
|
+
jointSpace[PRIVATE$f].radius =
|
|
3701
|
+
(nextRadius - lastRadius) * alpha + lastRadius;
|
|
3702
|
+
}
|
|
3703
|
+
}
|
|
3704
|
+
if (schema.hasGamepad) {
|
|
3705
|
+
const gamepad = inputSource.gamepad;
|
|
3706
|
+
nextInputData.buttons.forEach((states, index) => {
|
|
3707
|
+
const gamepadButton = gamepad.buttons[index];
|
|
3708
|
+
gamepadButton[PRIVATE$j].pressed = states[0] === 1 ? true : false;
|
|
3709
|
+
gamepadButton[PRIVATE$j].touched = states[1] === 1 ? true : false;
|
|
3710
|
+
const lastValue = lastInputData.buttons[index][2];
|
|
3711
|
+
const nextValue = states[2];
|
|
3712
|
+
gamepadButton[PRIVATE$j].value =
|
|
3713
|
+
(nextValue - lastValue) * alpha + lastValue;
|
|
3714
|
+
});
|
|
3715
|
+
nextInputData.axes.forEach((nextValue, index) => {
|
|
3716
|
+
const lastValue = lastInputData.axes[index];
|
|
3717
|
+
gamepad[PRIVATE$j].axesMap[index.toString()].x =
|
|
3718
|
+
(nextValue - lastValue) * alpha + lastValue;
|
|
3719
|
+
});
|
|
3720
|
+
}
|
|
3721
|
+
}
|
|
3722
|
+
updateXRSpaceFromMergedFrames(space, lastTransform, nextTransform, alpha) {
|
|
3723
|
+
const f1p = fromValues$2(lastTransform[0], lastTransform[1], lastTransform[2]);
|
|
3724
|
+
const f1q = fromValues(lastTransform[3], lastTransform[4], lastTransform[5], lastTransform[6]);
|
|
3725
|
+
const f2p = fromValues$2(nextTransform[0], nextTransform[1], nextTransform[2]);
|
|
3726
|
+
const f2q = fromValues(nextTransform[3], nextTransform[4], nextTransform[5], nextTransform[6]);
|
|
3727
|
+
lerp(this[PRIVATE$4].vec3, f1p, f2p, alpha);
|
|
3728
|
+
slerp(this[PRIVATE$4].quat, f1q, f2q, alpha);
|
|
3729
|
+
fromRotationTranslation(space[PRIVATE$k].offsetMatrix, this[PRIVATE$4].quat, this[PRIVATE$4].vec3);
|
|
3730
|
+
}
|
|
3731
|
+
processRawInputData(inputDataRaw) {
|
|
3732
|
+
const index = inputDataRaw[0];
|
|
3733
|
+
const schema = this[PRIVATE$4].inputSchemas.get(index);
|
|
3734
|
+
const targetRayTransform = inputDataRaw.slice(1, 8);
|
|
3735
|
+
const inputData = { targetRayTransform };
|
|
3736
|
+
let dataCounter = 8;
|
|
3737
|
+
if (schema.hasGrip) {
|
|
3738
|
+
inputData.gripTransform = inputDataRaw[dataCounter++];
|
|
3739
|
+
}
|
|
3740
|
+
if (schema.hasHand) {
|
|
3741
|
+
inputData.handTransforms = inputDataRaw[dataCounter++];
|
|
3742
|
+
}
|
|
3743
|
+
if (schema.hasGamepad) {
|
|
3744
|
+
const gamepadData = inputDataRaw[dataCounter];
|
|
3745
|
+
inputData.buttons = gamepadData.slice(0, schema.numButtons);
|
|
3746
|
+
inputData.axes = gamepadData.slice(schema.numButtons);
|
|
3747
|
+
}
|
|
3748
|
+
return { index, inputData };
|
|
3749
|
+
}
|
|
3750
|
+
}
|
|
3751
|
+
|
|
3752
|
+
const VERSION = "0.0.1";
|
|
3753
|
+
|
|
3754
|
+
class XRReferenceSpaceEvent extends Event {
|
|
3755
|
+
constructor(type, eventInitDict) {
|
|
3756
|
+
super(type, eventInitDict);
|
|
3757
|
+
if (!eventInitDict.referenceSpace) {
|
|
3758
|
+
throw new Error('XRReferenceSpaceEventInit.referenceSpace is required');
|
|
3759
|
+
}
|
|
3760
|
+
this.referenceSpace = eventInitDict.referenceSpace;
|
|
3761
|
+
this.transform = eventInitDict.transform;
|
|
3762
|
+
}
|
|
3763
|
+
}
|
|
3764
|
+
|
|
3765
|
+
const PRIVATE$3 = Symbol('@immersive-web-emulation-runtime/xr-system');
|
|
3766
|
+
class XRSystem extends EventTarget {
|
|
3767
|
+
constructor(device) {
|
|
3768
|
+
super();
|
|
3769
|
+
this[PRIVATE$3] = { device };
|
|
3770
|
+
// Initialize device change monitoring here if applicable
|
|
3771
|
+
}
|
|
3772
|
+
isSessionSupported(mode) {
|
|
3773
|
+
return new Promise((resolve, _reject) => {
|
|
3774
|
+
if (mode === XRSessionMode.Inline) {
|
|
3775
|
+
resolve(true);
|
|
3776
|
+
}
|
|
3777
|
+
else {
|
|
3778
|
+
// Check for spatial tracking permission if necessary
|
|
3779
|
+
resolve(this[PRIVATE$3].device.supportedSessionModes.includes(mode));
|
|
3780
|
+
}
|
|
3781
|
+
});
|
|
3782
|
+
}
|
|
3783
|
+
requestSession(mode, options = {}) {
|
|
3784
|
+
return new Promise((resolve, reject) => {
|
|
3785
|
+
this.isSessionSupported(mode)
|
|
3786
|
+
.then((isSupported) => {
|
|
3787
|
+
if (!isSupported) {
|
|
3788
|
+
reject(new DOMException('The requested XRSession mode is not supported.', 'NotSupportedError'));
|
|
3789
|
+
return;
|
|
3790
|
+
}
|
|
3791
|
+
// Check for active sessions and other constraints here
|
|
3792
|
+
if (this[PRIVATE$3].activeSession) {
|
|
3793
|
+
reject(new DOMException('An active XRSession already exists.', 'InvalidStateError'));
|
|
3794
|
+
return;
|
|
3795
|
+
}
|
|
3796
|
+
// Handle required and optional features
|
|
3797
|
+
const { requiredFeatures = [], optionalFeatures = [] } = options;
|
|
3798
|
+
const { supportedFeatures } = this[PRIVATE$3].device;
|
|
3799
|
+
// Check if all required features are supported
|
|
3800
|
+
const allRequiredSupported = requiredFeatures.every((feature) => supportedFeatures.includes(feature));
|
|
3801
|
+
if (!allRequiredSupported) {
|
|
3802
|
+
reject(new Error('One or more required features are not supported by the device.'));
|
|
3803
|
+
return;
|
|
3804
|
+
}
|
|
3805
|
+
// Filter out unsupported optional features
|
|
3806
|
+
const supportedOptionalFeatures = optionalFeatures.filter((feature) => supportedFeatures.includes(feature));
|
|
3807
|
+
// Combine required and supported optional features into enabled features
|
|
3808
|
+
const enabledFeatures = Array.from(new Set([
|
|
3809
|
+
...requiredFeatures,
|
|
3810
|
+
...supportedOptionalFeatures,
|
|
3811
|
+
WebXRFeatures.Viewer,
|
|
3812
|
+
WebXRFeatures.Local,
|
|
3813
|
+
]));
|
|
3814
|
+
// Proceed with session creation
|
|
3815
|
+
const session = new XRSession(this[PRIVATE$3].device, mode, enabledFeatures);
|
|
3816
|
+
this[PRIVATE$3].activeSession = session;
|
|
3817
|
+
// Listen for session end to clear the active session
|
|
3818
|
+
session.addEventListener('end', () => {
|
|
3819
|
+
this[PRIVATE$3].activeSession = undefined;
|
|
3820
|
+
});
|
|
3821
|
+
resolve(session);
|
|
3822
|
+
})
|
|
3823
|
+
.catch(reject);
|
|
3824
|
+
});
|
|
3825
|
+
}
|
|
3826
|
+
}
|
|
3827
|
+
|
|
3828
|
+
const PRIVATE$2 = Symbol('@immersive-web-emulation-runtime/xr-viewport');
|
|
3829
|
+
class XRViewport {
|
|
3830
|
+
constructor(x, y, width, height) {
|
|
3831
|
+
this[PRIVATE$2] = { x, y, width, height };
|
|
3832
|
+
}
|
|
3833
|
+
get x() {
|
|
3834
|
+
return this[PRIVATE$2].x;
|
|
3835
|
+
}
|
|
3836
|
+
get y() {
|
|
3837
|
+
return this[PRIVATE$2].y;
|
|
3838
|
+
}
|
|
3839
|
+
get width() {
|
|
3840
|
+
return this[PRIVATE$2].width;
|
|
3841
|
+
}
|
|
3842
|
+
get height() {
|
|
3843
|
+
return this[PRIVATE$2].height;
|
|
3844
|
+
}
|
|
3845
|
+
}
|
|
3846
|
+
|
|
3847
|
+
var WebXRFeatures;
|
|
3848
|
+
(function (WebXRFeatures) {
|
|
3849
|
+
WebXRFeatures["Viewer"] = "viewer";
|
|
3850
|
+
WebXRFeatures["Local"] = "local";
|
|
3851
|
+
WebXRFeatures["LocalFloor"] = "local-floor";
|
|
3852
|
+
WebXRFeatures["BoundedFloor"] = "bounded-floor";
|
|
3853
|
+
WebXRFeatures["Unbounded"] = "unbounded";
|
|
3854
|
+
WebXRFeatures["DomOverlay"] = "dom-overlay";
|
|
3855
|
+
WebXRFeatures["Anchors"] = "anchors";
|
|
3856
|
+
WebXRFeatures["PlaneDetection"] = "plane-detection";
|
|
3857
|
+
WebXRFeatures["MeshDetection"] = "mesh-detection";
|
|
3858
|
+
WebXRFeatures["HitTest"] = "hit-test";
|
|
3859
|
+
WebXRFeatures["HandTracking"] = "hand-tracking";
|
|
3860
|
+
WebXRFeatures["DepthSensing"] = "depth-sensing";
|
|
3861
|
+
})(WebXRFeatures || (WebXRFeatures = {}));
|
|
3862
|
+
const PRIVATE$1 = Symbol('@immersive-web-emulation-runtime/xr-device');
|
|
3863
|
+
const DEFAULTS = {
|
|
3864
|
+
ipd: 0.063,
|
|
3865
|
+
fovy: Math.PI / 2,
|
|
3866
|
+
headsetPosition: new Vector3(0, 1.6, 0),
|
|
3867
|
+
headsetQuaternion: new Quaternion(),
|
|
3868
|
+
stereoEnabled: false,
|
|
3869
|
+
};
|
|
3870
|
+
/**
|
|
3871
|
+
* XRDevice is not a standard API class outlined in the WebXR Device API Specifications
|
|
3872
|
+
* Instead, it serves as an user-facing interface to control the emulated XR Device
|
|
3873
|
+
*/
|
|
3874
|
+
class XRDevice {
|
|
3875
|
+
constructor(deviceConfig, deviceOptions = {}) {
|
|
3876
|
+
var _a, _b, _c, _d, _e, _f;
|
|
3877
|
+
const globalSpace = new GlobalSpace();
|
|
3878
|
+
const viewerSpace = new XRReferenceSpace(XRReferenceSpaceType.Viewer, globalSpace);
|
|
3879
|
+
const viewSpaces = {
|
|
3880
|
+
[XREye.Left]: new XRSpace(viewerSpace),
|
|
3881
|
+
[XREye.Right]: new XRSpace(viewerSpace),
|
|
3882
|
+
[XREye.None]: new XRSpace(viewerSpace),
|
|
3883
|
+
};
|
|
3884
|
+
const controllerConfig = deviceConfig.controllerConfig;
|
|
3885
|
+
const controllers = {};
|
|
3886
|
+
if (controllerConfig) {
|
|
3887
|
+
Object.values(XRHandedness).forEach((handedness) => {
|
|
3888
|
+
if (controllerConfig.layout[handedness]) {
|
|
3889
|
+
controllers[handedness] = new XRController(controllerConfig, handedness, globalSpace);
|
|
3890
|
+
}
|
|
3891
|
+
});
|
|
3892
|
+
}
|
|
3893
|
+
const hands = {
|
|
3894
|
+
[XRHandedness.Left]: new XRHandInput(oculusHandConfig, XRHandedness.Left, globalSpace),
|
|
3895
|
+
[XRHandedness.Right]: new XRHandInput(oculusHandConfig, XRHandedness.Right, globalSpace),
|
|
3896
|
+
};
|
|
3897
|
+
const canvasContainer = (_a = deviceOptions.canvasContainer) !== null && _a !== void 0 ? _a : document.createElement('div');
|
|
3898
|
+
canvasContainer.dataset.webxr_runtime = `Immersive Web Emulation Runtime v${VERSION}`;
|
|
3899
|
+
canvasContainer.style.position = 'fixed';
|
|
3900
|
+
canvasContainer.style.width = '100%';
|
|
3901
|
+
canvasContainer.style.height = '100%';
|
|
3902
|
+
canvasContainer.style.top = '0';
|
|
3903
|
+
canvasContainer.style.left = '0';
|
|
3904
|
+
canvasContainer.style.display = 'flex';
|
|
3905
|
+
canvasContainer.style.justifyContent = 'center';
|
|
3906
|
+
canvasContainer.style.alignItems = 'center';
|
|
3907
|
+
canvasContainer.style.overflow = 'hidden';
|
|
3908
|
+
canvasContainer.style.zIndex = '999';
|
|
3909
|
+
this[PRIVATE$1] = {
|
|
3910
|
+
name: deviceConfig.name,
|
|
3911
|
+
supportedSessionModes: deviceConfig.supportedSessionModes,
|
|
3912
|
+
supportedFeatures: deviceConfig.supportedFeatures,
|
|
3913
|
+
supportedFrameRates: deviceConfig.supportedFrameRates,
|
|
3914
|
+
isSystemKeyboardSupported: deviceConfig.isSystemKeyboardSupported,
|
|
3915
|
+
internalNominalFrameRate: deviceConfig.internalNominalFrameRate,
|
|
3916
|
+
position: (_b = deviceOptions.headsetPosition) !== null && _b !== void 0 ? _b : DEFAULTS.headsetPosition.clone(),
|
|
3917
|
+
quaternion: (_c = deviceOptions.headsetQuaternion) !== null && _c !== void 0 ? _c : DEFAULTS.headsetQuaternion.clone(),
|
|
3918
|
+
stereoEnabled: (_d = deviceOptions.stereoEnabled) !== null && _d !== void 0 ? _d : DEFAULTS.stereoEnabled,
|
|
3919
|
+
ipd: (_e = deviceOptions.ipd) !== null && _e !== void 0 ? _e : DEFAULTS.ipd,
|
|
3920
|
+
fovy: (_f = deviceOptions.fovy) !== null && _f !== void 0 ? _f : DEFAULTS.fovy,
|
|
3921
|
+
controllers,
|
|
3922
|
+
hands,
|
|
3923
|
+
primaryInputMode: 'controller',
|
|
3924
|
+
pendingReferenceSpaceReset: false,
|
|
3925
|
+
visibilityState: XRVisibilityState.Visible,
|
|
3926
|
+
pendingVisibilityState: null,
|
|
3927
|
+
matrix: create$3(),
|
|
3928
|
+
globalSpace,
|
|
3929
|
+
viewerSpace,
|
|
3930
|
+
viewSpaces,
|
|
3931
|
+
canvasContainer,
|
|
3932
|
+
getViewport: (layer, view) => {
|
|
3933
|
+
const canvas = layer.context.canvas;
|
|
3934
|
+
const { width, height } = canvas;
|
|
3935
|
+
switch (view.eye) {
|
|
3936
|
+
case XREye.None:
|
|
3937
|
+
return new XRViewport(0, 0, width, height);
|
|
3938
|
+
case XREye.Left:
|
|
3939
|
+
return new XRViewport(0, 0, this[PRIVATE$1].stereoEnabled ? width / 2 : width, height);
|
|
3940
|
+
case XREye.Right:
|
|
3941
|
+
return new XRViewport(width / 2, 0, this[PRIVATE$1].stereoEnabled ? width / 2 : 0, height);
|
|
3942
|
+
}
|
|
3943
|
+
},
|
|
3944
|
+
updateViews: () => {
|
|
3945
|
+
// update viewerSpace
|
|
3946
|
+
const viewerSpace = this[PRIVATE$1].viewerSpace;
|
|
3947
|
+
fromRotationTranslation(viewerSpace[PRIVATE$k].offsetMatrix, this[PRIVATE$1].quaternion.quat, this[PRIVATE$1].position.vec3);
|
|
3948
|
+
// update viewSpaces
|
|
3949
|
+
fromTranslation(this[PRIVATE$1].viewSpaces[XREye.Left][PRIVATE$k].offsetMatrix, fromValues$2(-this[PRIVATE$1].ipd / 2, 0, 0));
|
|
3950
|
+
fromTranslation(this[PRIVATE$1].viewSpaces[XREye.Right][PRIVATE$k].offsetMatrix, fromValues$2(this[PRIVATE$1].ipd / 2, 0, 0));
|
|
3951
|
+
},
|
|
3952
|
+
onBaseLayerSet: (baseLayer) => {
|
|
3953
|
+
if (!baseLayer)
|
|
3954
|
+
return;
|
|
3955
|
+
// backup canvas data
|
|
3956
|
+
const canvas = baseLayer.context.canvas;
|
|
3957
|
+
if (canvas.parentElement !== this[PRIVATE$1].canvasContainer) {
|
|
3958
|
+
this[PRIVATE$1].canvasData = {
|
|
3959
|
+
canvas,
|
|
3960
|
+
parent: canvas.parentElement,
|
|
3961
|
+
width: canvas.width,
|
|
3962
|
+
height: canvas.height,
|
|
3963
|
+
};
|
|
3964
|
+
this[PRIVATE$1].canvasContainer.appendChild(canvas);
|
|
3965
|
+
document.body.appendChild(this[PRIVATE$1].canvasContainer);
|
|
3966
|
+
}
|
|
3967
|
+
canvas.width = window.innerWidth;
|
|
3968
|
+
canvas.height = window.innerHeight;
|
|
3969
|
+
},
|
|
3970
|
+
onSessionEnd: () => {
|
|
3971
|
+
if (this[PRIVATE$1].canvasData) {
|
|
3972
|
+
const { canvas, parent, width, height } = this[PRIVATE$1].canvasData;
|
|
3973
|
+
canvas.width = width;
|
|
3974
|
+
canvas.height = height;
|
|
3975
|
+
if (parent) {
|
|
3976
|
+
parent.appendChild(canvas);
|
|
3977
|
+
}
|
|
3978
|
+
else {
|
|
3979
|
+
this[PRIVATE$1].canvasContainer.removeChild(canvas);
|
|
3980
|
+
}
|
|
3981
|
+
document.body.removeChild(this[PRIVATE$1].canvasContainer);
|
|
3982
|
+
window.dispatchEvent(new Event('resize'));
|
|
3983
|
+
}
|
|
3984
|
+
},
|
|
3985
|
+
onFrameStart: (frame) => {
|
|
3986
|
+
var _a;
|
|
3987
|
+
if ((_a = this[PRIVATE$1].actionPlayer) === null || _a === void 0 ? void 0 : _a.playing) {
|
|
3988
|
+
this[PRIVATE$1].actionPlayer.playFrame();
|
|
3989
|
+
}
|
|
3990
|
+
else {
|
|
3991
|
+
const session = frame.session;
|
|
3992
|
+
this[PRIVATE$1].updateViews();
|
|
3993
|
+
if (this[PRIVATE$1].pendingVisibilityState) {
|
|
3994
|
+
this[PRIVATE$1].visibilityState =
|
|
3995
|
+
this[PRIVATE$1].pendingVisibilityState;
|
|
3996
|
+
this[PRIVATE$1].pendingVisibilityState = null;
|
|
3997
|
+
session.dispatchEvent(new XRSessionEvent('visibilitychange', { session }));
|
|
3998
|
+
}
|
|
3999
|
+
if (this[PRIVATE$1].visibilityState === XRVisibilityState.Visible) {
|
|
4000
|
+
this.activeInputs.forEach((activeInput) => {
|
|
4001
|
+
activeInput.onFrameStart(frame);
|
|
4002
|
+
});
|
|
4003
|
+
}
|
|
4004
|
+
if (this[PRIVATE$1].pendingReferenceSpaceReset) {
|
|
4005
|
+
session[PRIVATE$6].referenceSpaces.forEach((referenceSpace) => {
|
|
4006
|
+
switch (referenceSpace[PRIVATE$8].type) {
|
|
4007
|
+
case XRReferenceSpaceType.Local:
|
|
4008
|
+
case XRReferenceSpaceType.LocalFloor:
|
|
4009
|
+
case XRReferenceSpaceType.BoundedFloor:
|
|
4010
|
+
case XRReferenceSpaceType.Unbounded:
|
|
4011
|
+
referenceSpace.dispatchEvent(new XRReferenceSpaceEvent('reset', { referenceSpace }));
|
|
4012
|
+
break;
|
|
4013
|
+
}
|
|
4014
|
+
});
|
|
4015
|
+
this[PRIVATE$1].pendingReferenceSpaceReset = false;
|
|
4016
|
+
}
|
|
4017
|
+
}
|
|
4018
|
+
this[PRIVATE$1].updateViews();
|
|
4019
|
+
},
|
|
4020
|
+
};
|
|
4021
|
+
this[PRIVATE$1].updateViews();
|
|
4022
|
+
}
|
|
4023
|
+
installRuntime(globalObject = globalThis) {
|
|
4024
|
+
Object.defineProperty(WebGL2RenderingContext.prototype, 'makeXRCompatible', {
|
|
4025
|
+
value: function () {
|
|
4026
|
+
return new Promise((resolve, _reject) => {
|
|
4027
|
+
resolve(true);
|
|
4028
|
+
});
|
|
4029
|
+
},
|
|
4030
|
+
configurable: true,
|
|
4031
|
+
});
|
|
4032
|
+
Object.defineProperty(globalThis.navigator, 'xr', {
|
|
4033
|
+
value: new XRSystem(this),
|
|
4034
|
+
configurable: true,
|
|
4035
|
+
});
|
|
4036
|
+
globalObject['XRSystem'] = XRSystem;
|
|
4037
|
+
globalObject['XRSession'] = XRSession;
|
|
4038
|
+
globalObject['XRRenderState'] = XRRenderState;
|
|
4039
|
+
globalObject['XRFrame'] = XRFrame;
|
|
4040
|
+
globalObject['XRSpace'] = XRSpace;
|
|
4041
|
+
globalObject['XRReferenceSpace'] = XRReferenceSpace;
|
|
4042
|
+
globalObject['XRJointSpace'] = XRJointSpace;
|
|
4043
|
+
globalObject['XRView'] = XRView;
|
|
4044
|
+
globalObject['XRViewport'] = XRViewport;
|
|
4045
|
+
globalObject['XRRigidTransform'] = XRRigidTransform;
|
|
4046
|
+
globalObject['XRPose'] = XRPose;
|
|
4047
|
+
globalObject['XRViewerPose'] = XRViewerPose;
|
|
4048
|
+
globalObject['XRJointPose'] = XRJointPose;
|
|
4049
|
+
globalObject['XRInputSource'] = XRInputSource;
|
|
4050
|
+
globalObject['XRInputSourceArray'] = XRInputSourceArray;
|
|
4051
|
+
globalObject['XRHand'] = XRHand;
|
|
4052
|
+
globalObject['XRLayer'] = XRLayer;
|
|
4053
|
+
globalObject['XRWebGLLayer'] = XRWebGLLayer;
|
|
4054
|
+
globalObject['XRSessionEvent'] = XRSessionEvent;
|
|
4055
|
+
globalObject['XRInputSourceEvent'] = XRInputSourceEvent;
|
|
4056
|
+
globalObject['XRInputSourcesChangeEvent'] = XRInputSourcesChangeEvent;
|
|
4057
|
+
globalObject['XRReferenceSpaceEvent'] = XRReferenceSpaceEvent;
|
|
4058
|
+
}
|
|
4059
|
+
get supportedSessionModes() {
|
|
4060
|
+
return this[PRIVATE$1].supportedSessionModes;
|
|
4061
|
+
}
|
|
4062
|
+
get supportedFeatures() {
|
|
4063
|
+
return this[PRIVATE$1].supportedFeatures;
|
|
4064
|
+
}
|
|
4065
|
+
get supportedFrameRates() {
|
|
4066
|
+
return this[PRIVATE$1].supportedFrameRates;
|
|
4067
|
+
}
|
|
4068
|
+
get isSystemKeyboardSupported() {
|
|
4069
|
+
return this[PRIVATE$1].isSystemKeyboardSupported;
|
|
4070
|
+
}
|
|
4071
|
+
get internalNominalFrameRate() {
|
|
4072
|
+
return this[PRIVATE$1].internalNominalFrameRate;
|
|
4073
|
+
}
|
|
4074
|
+
get stereoEnabled() {
|
|
4075
|
+
return this[PRIVATE$1].stereoEnabled;
|
|
4076
|
+
}
|
|
4077
|
+
set stereoEnabled(value) {
|
|
4078
|
+
this[PRIVATE$1].stereoEnabled = value;
|
|
4079
|
+
}
|
|
4080
|
+
get ipd() {
|
|
4081
|
+
return this[PRIVATE$1].ipd;
|
|
4082
|
+
}
|
|
4083
|
+
set ipd(value) {
|
|
4084
|
+
this[PRIVATE$1].ipd = value;
|
|
4085
|
+
}
|
|
4086
|
+
get fovy() {
|
|
4087
|
+
return this[PRIVATE$1].fovy;
|
|
4088
|
+
}
|
|
4089
|
+
set fovy(value) {
|
|
4090
|
+
this[PRIVATE$1].fovy = value;
|
|
4091
|
+
}
|
|
4092
|
+
get position() {
|
|
4093
|
+
return this[PRIVATE$1].position;
|
|
4094
|
+
}
|
|
4095
|
+
get quaternion() {
|
|
4096
|
+
return this[PRIVATE$1].quaternion;
|
|
4097
|
+
}
|
|
4098
|
+
get viewerSpace() {
|
|
4099
|
+
var _a;
|
|
4100
|
+
if ((_a = this[PRIVATE$1].actionPlayer) === null || _a === void 0 ? void 0 : _a.playing) {
|
|
4101
|
+
return this[PRIVATE$1].actionPlayer.viewerSpace;
|
|
4102
|
+
}
|
|
4103
|
+
else {
|
|
4104
|
+
return this[PRIVATE$1].viewerSpace;
|
|
4105
|
+
}
|
|
4106
|
+
}
|
|
4107
|
+
get viewSpaces() {
|
|
4108
|
+
var _a;
|
|
4109
|
+
if ((_a = this[PRIVATE$1].actionPlayer) === null || _a === void 0 ? void 0 : _a.playing) {
|
|
4110
|
+
return this[PRIVATE$1].actionPlayer.viewSpaces;
|
|
4111
|
+
}
|
|
4112
|
+
else {
|
|
4113
|
+
return this[PRIVATE$1].viewSpaces;
|
|
4114
|
+
}
|
|
4115
|
+
}
|
|
4116
|
+
get controllers() {
|
|
4117
|
+
return this[PRIVATE$1].controllers;
|
|
4118
|
+
}
|
|
4119
|
+
get hands() {
|
|
4120
|
+
return this[PRIVATE$1].hands;
|
|
4121
|
+
}
|
|
4122
|
+
get primaryInputMode() {
|
|
4123
|
+
return this[PRIVATE$1].primaryInputMode;
|
|
4124
|
+
}
|
|
4125
|
+
set primaryInputMode(mode) {
|
|
4126
|
+
if (mode !== 'controller' && mode !== 'hand') {
|
|
4127
|
+
console.warn('primary input mode can only be "controller" or "hand"');
|
|
4128
|
+
return;
|
|
4129
|
+
}
|
|
4130
|
+
this[PRIVATE$1].primaryInputMode = mode;
|
|
4131
|
+
}
|
|
4132
|
+
get activeInputs() {
|
|
4133
|
+
if (this[PRIVATE$1].visibilityState !== XRVisibilityState.Visible) {
|
|
4134
|
+
return [];
|
|
4135
|
+
}
|
|
4136
|
+
const activeInputs = this[PRIVATE$1].primaryInputMode === 'controller'
|
|
4137
|
+
? Object.values(this[PRIVATE$1].controllers)
|
|
4138
|
+
: Object.values(this[PRIVATE$1].hands);
|
|
4139
|
+
return activeInputs.filter((input) => input.connected);
|
|
4140
|
+
}
|
|
4141
|
+
get inputSources() {
|
|
4142
|
+
var _a;
|
|
4143
|
+
if ((_a = this[PRIVATE$1].actionPlayer) === null || _a === void 0 ? void 0 : _a.playing) {
|
|
4144
|
+
return this[PRIVATE$1].actionPlayer.inputSources;
|
|
4145
|
+
}
|
|
4146
|
+
else {
|
|
4147
|
+
return this.activeInputs.map((input) => input.inputSource);
|
|
4148
|
+
}
|
|
4149
|
+
}
|
|
4150
|
+
get canvasContainer() {
|
|
4151
|
+
return this[PRIVATE$1].canvasContainer;
|
|
4152
|
+
}
|
|
4153
|
+
recenter() {
|
|
4154
|
+
const deltaVec = new Vector3(-this.position.x, 0, -this.position.z);
|
|
4155
|
+
const forward = new Vector3(0, 0, -1).applyQuaternion(this.quaternion);
|
|
4156
|
+
forward.y = 0;
|
|
4157
|
+
forward.normalize();
|
|
4158
|
+
const angle = Math.atan2(forward.x, -forward.z);
|
|
4159
|
+
const deltaQuat = new Quaternion().setFromAxisAngle(new Vector3(0, 1, 0), angle);
|
|
4160
|
+
this.position.add(deltaVec);
|
|
4161
|
+
this.quaternion.multiply(deltaQuat);
|
|
4162
|
+
[
|
|
4163
|
+
...Object.values(this[PRIVATE$1].controllers),
|
|
4164
|
+
...Object.values(this[PRIVATE$1].hands),
|
|
4165
|
+
].forEach((activeInput) => {
|
|
4166
|
+
activeInput.position.add(deltaVec);
|
|
4167
|
+
activeInput.quaternion.multiply(deltaQuat);
|
|
4168
|
+
activeInput.position.applyQuaternion(deltaQuat);
|
|
4169
|
+
});
|
|
4170
|
+
this[PRIVATE$1].pendingReferenceSpaceReset = true;
|
|
4171
|
+
}
|
|
4172
|
+
get visibilityState() {
|
|
4173
|
+
return this[PRIVATE$1].visibilityState;
|
|
4174
|
+
}
|
|
4175
|
+
// visibility state updates are queued until the XRSession produces frames
|
|
4176
|
+
updateVisibilityState(state) {
|
|
4177
|
+
if (!Object.values(XRVisibilityState).includes(state)) {
|
|
4178
|
+
throw new DOMException('Invalid XRVisibilityState value', 'NotSupportedError');
|
|
4179
|
+
}
|
|
4180
|
+
if (state !== this[PRIVATE$1].visibilityState) {
|
|
4181
|
+
this[PRIVATE$1].pendingVisibilityState = state;
|
|
4182
|
+
}
|
|
4183
|
+
}
|
|
4184
|
+
createActionPlayer(refSpace, recording) {
|
|
4185
|
+
this[PRIVATE$1].actionPlayer = new ActionPlayer(refSpace, recording, this[PRIVATE$1].ipd);
|
|
4186
|
+
return this[PRIVATE$1].actionPlayer;
|
|
4187
|
+
}
|
|
4188
|
+
}
|
|
4189
|
+
|
|
4190
|
+
// value pulled from https://felixtrz.github.io/webxr-device-config/
|
|
4191
|
+
const gamepadConfigLeft = {
|
|
4192
|
+
mapping: GamepadMappingType.XRStandard,
|
|
4193
|
+
buttons: [
|
|
4194
|
+
{ id: 'trigger', type: 'analog', eventTrigger: 'select' },
|
|
4195
|
+
{ id: 'squeeze', type: 'analog', eventTrigger: 'squeeze' },
|
|
4196
|
+
null,
|
|
4197
|
+
{ id: 'thumbstick', type: 'binary' },
|
|
4198
|
+
{ id: 'x-button', type: 'binary' },
|
|
4199
|
+
{ id: 'y-button', type: 'binary' },
|
|
4200
|
+
{ id: 'thumbrest', type: 'binary' },
|
|
4201
|
+
],
|
|
4202
|
+
axes: [
|
|
4203
|
+
null,
|
|
4204
|
+
null,
|
|
4205
|
+
{ id: 'thumbstick', type: 'x-axis' },
|
|
4206
|
+
{ id: 'thumbstick', type: 'y-axis' },
|
|
4207
|
+
],
|
|
4208
|
+
};
|
|
4209
|
+
const gamepadConfigRight = {
|
|
4210
|
+
mapping: GamepadMappingType.XRStandard,
|
|
4211
|
+
buttons: [
|
|
4212
|
+
{ id: 'trigger', type: 'analog', eventTrigger: 'select' },
|
|
4213
|
+
{ id: 'squeeze', type: 'analog', eventTrigger: 'squeeze' },
|
|
4214
|
+
null,
|
|
4215
|
+
{ id: 'thumbstick', type: 'binary' },
|
|
4216
|
+
{ id: 'a-button', type: 'binary' },
|
|
4217
|
+
{ id: 'b-button', type: 'binary' },
|
|
4218
|
+
{ id: 'thumbrest', type: 'binary' },
|
|
4219
|
+
],
|
|
4220
|
+
axes: [
|
|
4221
|
+
null,
|
|
4222
|
+
null,
|
|
4223
|
+
{ id: 'thumbstick', type: 'x-axis' },
|
|
4224
|
+
{ id: 'thumbstick', type: 'y-axis' },
|
|
4225
|
+
],
|
|
4226
|
+
};
|
|
4227
|
+
const oculusTouchV2 = {
|
|
4228
|
+
profileId: 'oculus-touch-v2',
|
|
4229
|
+
fallbackProfileIds: ['oculus-touch', 'generic-trigger-squeeze-thumbstick'],
|
|
4230
|
+
layout: {
|
|
4231
|
+
left: {
|
|
4232
|
+
gamepad: gamepadConfigLeft,
|
|
4233
|
+
gripOffsetMatrix: [
|
|
4234
|
+
0.9925461411476135, 4.673031295254759e-9, -0.12186938524246216, 0,
|
|
4235
|
+
0.08617470413446426, 0.7071065306663513, 0.7018362283706665, 0,
|
|
4236
|
+
0.0861746296286583, -0.70710688829422, 0.7018358707427979, 0,
|
|
4237
|
+
-0.003979847766458988, -0.01585787907242775, 0.04964185878634453, 1,
|
|
4238
|
+
],
|
|
4239
|
+
numHapticActuators: 1,
|
|
4240
|
+
},
|
|
4241
|
+
right: {
|
|
4242
|
+
gamepad: gamepadConfigRight,
|
|
4243
|
+
gripOffsetMatrix: [
|
|
4244
|
+
0.9925461411476135, 3.688163374704345e-8, 0.12186937034130096, 0,
|
|
4245
|
+
-0.08617469668388367, 0.7071066498756409, 0.7018361687660217, 0,
|
|
4246
|
+
-0.0861746147274971, -0.7071068286895752, 0.7018359899520874, 0,
|
|
4247
|
+
0.003979853354394436, -0.01585787907242775, 0.04964182525873184, 1,
|
|
4248
|
+
],
|
|
4249
|
+
numHapticActuators: 1,
|
|
4250
|
+
},
|
|
4251
|
+
},
|
|
4252
|
+
};
|
|
4253
|
+
const oculusTouchV3 = {
|
|
4254
|
+
profileId: 'oculus-touch-v3',
|
|
4255
|
+
fallbackProfileIds: ['oculus-touch', 'generic-trigger-squeeze-thumbstick'],
|
|
4256
|
+
layout: {
|
|
4257
|
+
left: {
|
|
4258
|
+
gamepad: gamepadConfigLeft,
|
|
4259
|
+
gripOffsetMatrix: [
|
|
4260
|
+
0.9925461411476135, 2.0823669899527886e-8, -0.12186937034130096, 0,
|
|
4261
|
+
0.08617465198040009, 0.7071067094802856, 0.701836109161377, 0,
|
|
4262
|
+
0.08617466688156128, -0.7071067690849304, 0.7018360495567322, 0,
|
|
4263
|
+
-0.003979838453233242, -0.015857907012104988, 0.04964181408286095, 1,
|
|
4264
|
+
],
|
|
4265
|
+
numHapticActuators: 1,
|
|
4266
|
+
},
|
|
4267
|
+
right: {
|
|
4268
|
+
gamepad: gamepadConfigRight,
|
|
4269
|
+
gripOffsetMatrix: [
|
|
4270
|
+
0.9925461411476135, -8.329467959811154e-8, 0.12186941504478455, 0,
|
|
4271
|
+
-0.08617465943098068, 0.7071066498756409, 0.7018361687660217, 0,
|
|
4272
|
+
-0.08617471158504486, -0.7071068286895752, 0.7018359303474426, 0,
|
|
4273
|
+
0.003979798872023821, -0.015857888385653496, 0.049641866236925125, 1,
|
|
4274
|
+
],
|
|
4275
|
+
numHapticActuators: 1,
|
|
4276
|
+
},
|
|
4277
|
+
},
|
|
4278
|
+
};
|
|
4279
|
+
const metaQuestTouchPro = {
|
|
4280
|
+
profileId: 'meta-quest-touch-pro',
|
|
4281
|
+
fallbackProfileIds: [
|
|
4282
|
+
'oculus-touch-v2',
|
|
4283
|
+
'oculus-touch',
|
|
4284
|
+
'generic-trigger-squeeze-thumbstick',
|
|
4285
|
+
],
|
|
4286
|
+
layout: {
|
|
4287
|
+
left: {
|
|
4288
|
+
gamepad: gamepadConfigLeft,
|
|
4289
|
+
gripOffsetMatrix: [
|
|
4290
|
+
0.9925461411476135, -1.5779937356796836e-8, -0.12186935544013977, 0,
|
|
4291
|
+
0.08617467433214188, 0.7071067094802856, 0.701836109161377, 0,
|
|
4292
|
+
0.0861746296286583, -0.7071067690849304, 0.7018360495567322, 0,
|
|
4293
|
+
-0.003979836590588093, -0.015857847407460213, 0.049641840159893036, 1,
|
|
4294
|
+
],
|
|
4295
|
+
numHapticActuators: 3,
|
|
4296
|
+
},
|
|
4297
|
+
right: {
|
|
4298
|
+
gamepad: gamepadConfigRight,
|
|
4299
|
+
gripOffsetMatrix: [
|
|
4300
|
+
0.9925461411476135, 9.267653311439972e-11, 0.12186937034130096, 0,
|
|
4301
|
+
-0.08617467433214188, 0.7071067094802856, 0.7018361687660217, 0,
|
|
4302
|
+
-0.08617464452981949, -0.7071067690849304, 0.7018360495567322, 0,
|
|
4303
|
+
0.003979847766458988, -0.01585782691836357, 0.04964186251163483, 1,
|
|
4304
|
+
],
|
|
4305
|
+
numHapticActuators: 3,
|
|
4306
|
+
},
|
|
4307
|
+
},
|
|
4308
|
+
};
|
|
4309
|
+
const metaQuestTouchPlus = {
|
|
4310
|
+
profileId: 'meta-quest-touch-plus',
|
|
4311
|
+
fallbackProfileIds: [
|
|
4312
|
+
'oculus-touch-v3',
|
|
4313
|
+
'oculus-touch',
|
|
4314
|
+
'generic-trigger-squeeze-thumbstick',
|
|
4315
|
+
],
|
|
4316
|
+
layout: {
|
|
4317
|
+
left: {
|
|
4318
|
+
gamepad: gamepadConfigLeft,
|
|
4319
|
+
gripOffsetMatrix: [
|
|
4320
|
+
0.9925461411476135, 1.0736208366779465e-8, -0.12186933308839798, 0,
|
|
4321
|
+
0.08617459982633591, 0.70710688829422, 0.7018360495567322, 0,
|
|
4322
|
+
0.08617466688156128, -0.7071067094802856, 0.7018362283706665, 0,
|
|
4323
|
+
-0.003979803062975407, -0.015857873484492302, 0.04964187368750572, 1,
|
|
4324
|
+
],
|
|
4325
|
+
numHapticActuators: 1,
|
|
4326
|
+
},
|
|
4327
|
+
right: {
|
|
4328
|
+
gamepad: gamepadConfigRight,
|
|
4329
|
+
gripOffsetMatrix: [
|
|
4330
|
+
0.9925461411476135, -2.6238110351073374e-8, 0.12186934053897858, 0,
|
|
4331
|
+
-0.0861746147274971, 0.7071067690849304, 0.7018360495567322, 0,
|
|
4332
|
+
-0.08617465943098068, -0.7071067094802856, 0.701836109161377, 0,
|
|
4333
|
+
0.003979838453233242, -0.015857869759202003, 0.04964182525873184, 1,
|
|
4334
|
+
],
|
|
4335
|
+
numHapticActuators: 1,
|
|
4336
|
+
},
|
|
4337
|
+
},
|
|
4338
|
+
};
|
|
4339
|
+
|
|
4340
|
+
const oculusQuest1 = {
|
|
4341
|
+
name: 'Oculus Quest 1',
|
|
4342
|
+
controllerConfig: oculusTouchV2,
|
|
4343
|
+
supportedSessionModes: [
|
|
4344
|
+
XRSessionMode.Inline,
|
|
4345
|
+
XRSessionMode.ImmersiveVR,
|
|
4346
|
+
XRSessionMode.ImmersiveAR,
|
|
4347
|
+
],
|
|
4348
|
+
supportedFeatures: [
|
|
4349
|
+
WebXRFeatures.Viewer,
|
|
4350
|
+
WebXRFeatures.Local,
|
|
4351
|
+
WebXRFeatures.LocalFloor,
|
|
4352
|
+
WebXRFeatures.BoundedFloor,
|
|
4353
|
+
WebXRFeatures.Unbounded,
|
|
4354
|
+
WebXRFeatures.Anchors,
|
|
4355
|
+
WebXRFeatures.PlaneDetection,
|
|
4356
|
+
WebXRFeatures.HandTracking,
|
|
4357
|
+
],
|
|
4358
|
+
supportedFrameRates: [72, 80, 90],
|
|
4359
|
+
isSystemKeyboardSupported: true,
|
|
4360
|
+
internalNominalFrameRate: 72,
|
|
4361
|
+
};
|
|
4362
|
+
const metaQuest2 = {
|
|
4363
|
+
name: 'Meta Quest 2',
|
|
4364
|
+
controllerConfig: oculusTouchV3,
|
|
4365
|
+
supportedSessionModes: [
|
|
4366
|
+
XRSessionMode.Inline,
|
|
4367
|
+
XRSessionMode.ImmersiveVR,
|
|
4368
|
+
XRSessionMode.ImmersiveAR,
|
|
4369
|
+
],
|
|
4370
|
+
supportedFeatures: [
|
|
4371
|
+
WebXRFeatures.Viewer,
|
|
4372
|
+
WebXRFeatures.Local,
|
|
4373
|
+
WebXRFeatures.LocalFloor,
|
|
4374
|
+
WebXRFeatures.BoundedFloor,
|
|
4375
|
+
WebXRFeatures.Unbounded,
|
|
4376
|
+
WebXRFeatures.Anchors,
|
|
4377
|
+
WebXRFeatures.PlaneDetection,
|
|
4378
|
+
WebXRFeatures.MeshDetection,
|
|
4379
|
+
WebXRFeatures.HitTest,
|
|
4380
|
+
WebXRFeatures.HandTracking,
|
|
4381
|
+
],
|
|
4382
|
+
supportedFrameRates: [72, 80, 90, 120],
|
|
4383
|
+
isSystemKeyboardSupported: true,
|
|
4384
|
+
internalNominalFrameRate: 72,
|
|
4385
|
+
};
|
|
4386
|
+
const metaQuestPro = {
|
|
4387
|
+
name: 'Meta Quest Pro',
|
|
4388
|
+
controllerConfig: metaQuestTouchPro,
|
|
4389
|
+
supportedSessionModes: [
|
|
4390
|
+
XRSessionMode.Inline,
|
|
4391
|
+
XRSessionMode.ImmersiveVR,
|
|
4392
|
+
XRSessionMode.ImmersiveAR,
|
|
4393
|
+
],
|
|
4394
|
+
supportedFeatures: [
|
|
4395
|
+
WebXRFeatures.Viewer,
|
|
4396
|
+
WebXRFeatures.Local,
|
|
4397
|
+
WebXRFeatures.LocalFloor,
|
|
4398
|
+
WebXRFeatures.BoundedFloor,
|
|
4399
|
+
WebXRFeatures.Unbounded,
|
|
4400
|
+
WebXRFeatures.Anchors,
|
|
4401
|
+
WebXRFeatures.PlaneDetection,
|
|
4402
|
+
WebXRFeatures.MeshDetection,
|
|
4403
|
+
WebXRFeatures.HitTest,
|
|
4404
|
+
WebXRFeatures.HandTracking,
|
|
4405
|
+
],
|
|
4406
|
+
supportedFrameRates: [72, 80, 90, 120],
|
|
4407
|
+
isSystemKeyboardSupported: true,
|
|
4408
|
+
internalNominalFrameRate: 90,
|
|
4409
|
+
};
|
|
4410
|
+
const metaQuest3 = {
|
|
4411
|
+
name: 'Meta Quest 3',
|
|
4412
|
+
controllerConfig: metaQuestTouchPlus,
|
|
4413
|
+
supportedSessionModes: [
|
|
4414
|
+
XRSessionMode.Inline,
|
|
4415
|
+
XRSessionMode.ImmersiveVR,
|
|
4416
|
+
XRSessionMode.ImmersiveAR,
|
|
4417
|
+
],
|
|
4418
|
+
supportedFeatures: [
|
|
4419
|
+
WebXRFeatures.Viewer,
|
|
4420
|
+
WebXRFeatures.Local,
|
|
4421
|
+
WebXRFeatures.LocalFloor,
|
|
4422
|
+
WebXRFeatures.BoundedFloor,
|
|
4423
|
+
WebXRFeatures.Unbounded,
|
|
4424
|
+
WebXRFeatures.Anchors,
|
|
4425
|
+
WebXRFeatures.PlaneDetection,
|
|
4426
|
+
WebXRFeatures.MeshDetection,
|
|
4427
|
+
WebXRFeatures.HitTest,
|
|
4428
|
+
WebXRFeatures.HandTracking,
|
|
4429
|
+
WebXRFeatures.DepthSensing,
|
|
4430
|
+
],
|
|
4431
|
+
supportedFrameRates: [72, 80, 90, 120],
|
|
4432
|
+
isSystemKeyboardSupported: true,
|
|
4433
|
+
internalNominalFrameRate: 90,
|
|
4434
|
+
};
|
|
4435
|
+
|
|
4436
|
+
const PRIVATE = Symbol('@immersive-web-emulation-runtime/action-recorder');
|
|
4437
|
+
const compress = (arr) => {
|
|
4438
|
+
const out = [];
|
|
4439
|
+
arr.forEach((num) => {
|
|
4440
|
+
out.push(parseFloat(num.toFixed(3)));
|
|
4441
|
+
});
|
|
4442
|
+
return out;
|
|
4443
|
+
};
|
|
4444
|
+
class ActionRecorder {
|
|
4445
|
+
constructor(session, refSpace) {
|
|
4446
|
+
this[PRIVATE] = {
|
|
4447
|
+
session,
|
|
4448
|
+
refSpace,
|
|
4449
|
+
inputMap: new Map(),
|
|
4450
|
+
schemaMap: new Map(),
|
|
4451
|
+
compressedFrames: [],
|
|
4452
|
+
jointRadii: new Float32Array(25),
|
|
4453
|
+
jointTransforms: new Float32Array(25 * 16),
|
|
4454
|
+
};
|
|
4455
|
+
}
|
|
4456
|
+
recordFrame(frame) {
|
|
4457
|
+
var _a;
|
|
4458
|
+
const timeStamp = performance.now();
|
|
4459
|
+
const viewerMatrix = (_a = frame.getViewerPose(this[PRIVATE].refSpace)) === null || _a === void 0 ? void 0 : _a.transform.matrix;
|
|
4460
|
+
if (!viewerMatrix)
|
|
4461
|
+
return;
|
|
4462
|
+
const position = getTranslation(create$2(), viewerMatrix);
|
|
4463
|
+
const quaternion = getRotation(create(), viewerMatrix);
|
|
4464
|
+
const actionFrame = {
|
|
4465
|
+
timeStamp,
|
|
4466
|
+
position,
|
|
4467
|
+
quaternion,
|
|
4468
|
+
inputFrames: [],
|
|
4469
|
+
};
|
|
4470
|
+
this[PRIVATE].session.inputSources.forEach((inputSource) => {
|
|
4471
|
+
var _a, _b;
|
|
4472
|
+
if (!this[PRIVATE].inputMap.has(inputSource)) {
|
|
4473
|
+
const schema = {
|
|
4474
|
+
handedness: inputSource.handedness,
|
|
4475
|
+
targetRayMode: inputSource.targetRayMode,
|
|
4476
|
+
profiles: inputSource.profiles,
|
|
4477
|
+
hasGrip: inputSource.gripSpace != null,
|
|
4478
|
+
hasHand: inputSource.hand != null,
|
|
4479
|
+
hasGamepad: inputSource.gamepad != null,
|
|
4480
|
+
};
|
|
4481
|
+
if (schema.hasHand) {
|
|
4482
|
+
schema.jointSequence = Array.from(inputSource.hand.values()).map((jointSpace) => jointSpace.jointName);
|
|
4483
|
+
}
|
|
4484
|
+
if (schema.hasGamepad) {
|
|
4485
|
+
schema.mapping = inputSource.gamepad.mapping;
|
|
4486
|
+
schema.numButtons = inputSource.gamepad.buttons.length;
|
|
4487
|
+
schema.numAxes = inputSource.gamepad.axes.length;
|
|
4488
|
+
}
|
|
4489
|
+
const index = this[PRIVATE].inputMap.size;
|
|
4490
|
+
this[PRIVATE].inputMap.set(inputSource, index);
|
|
4491
|
+
this[PRIVATE].schemaMap.set(index, schema);
|
|
4492
|
+
}
|
|
4493
|
+
const index = this[PRIVATE].inputMap.get(inputSource);
|
|
4494
|
+
const schema = this[PRIVATE].schemaMap.get(index);
|
|
4495
|
+
const targetRayMatrix = (_a = frame.getPose(inputSource.targetRaySpace, this[PRIVATE].refSpace)) === null || _a === void 0 ? void 0 : _a.transform.matrix;
|
|
4496
|
+
if (targetRayMatrix) {
|
|
4497
|
+
const targetRayPosition = getTranslation(create$2(), targetRayMatrix);
|
|
4498
|
+
const targetRayQuaternion = getRotation(create(), targetRayMatrix);
|
|
4499
|
+
const inputFrame = {
|
|
4500
|
+
index,
|
|
4501
|
+
targetRayTransform: {
|
|
4502
|
+
position: targetRayPosition,
|
|
4503
|
+
quaternion: targetRayQuaternion,
|
|
4504
|
+
},
|
|
4505
|
+
};
|
|
4506
|
+
if (schema.hasGrip) {
|
|
4507
|
+
const gripMatrix = (_b = frame.getPose(inputSource.gripSpace, this[PRIVATE].refSpace)) === null || _b === void 0 ? void 0 : _b.transform.matrix;
|
|
4508
|
+
if (gripMatrix) {
|
|
4509
|
+
const position = getTranslation(create$2(), gripMatrix);
|
|
4510
|
+
const quaternion = getRotation(create(), gripMatrix);
|
|
4511
|
+
inputFrame.gripTransform = {
|
|
4512
|
+
position,
|
|
4513
|
+
quaternion,
|
|
4514
|
+
};
|
|
4515
|
+
}
|
|
4516
|
+
}
|
|
4517
|
+
if (schema.hasHand) {
|
|
4518
|
+
const jointSpaces = Array.from(inputSource.hand.values());
|
|
4519
|
+
let allValid = true;
|
|
4520
|
+
// @ts-ignore
|
|
4521
|
+
allValid && (allValid = frame.fillPoses(jointSpaces, inputSource.targetRaySpace, this[PRIVATE].jointTransforms));
|
|
4522
|
+
// @ts-ignore
|
|
4523
|
+
allValid && (allValid = frame.fillJointRadii(jointSpaces, this[PRIVATE].jointRadii));
|
|
4524
|
+
if (allValid) {
|
|
4525
|
+
const hand = {};
|
|
4526
|
+
for (let offset = 0; offset < 25; offset++) {
|
|
4527
|
+
const jointMatrix = this[PRIVATE].jointTransforms.slice(offset * 16, (offset + 1) * 16);
|
|
4528
|
+
const radius = this[PRIVATE].jointRadii[offset];
|
|
4529
|
+
const position = getTranslation(create$2(), jointMatrix);
|
|
4530
|
+
const quaternion = getRotation(create(), jointMatrix);
|
|
4531
|
+
const jointName = jointSpaces[offset].jointName;
|
|
4532
|
+
hand[jointName] = { position, quaternion, radius };
|
|
4533
|
+
}
|
|
4534
|
+
inputFrame.hand = hand;
|
|
4535
|
+
}
|
|
4536
|
+
}
|
|
4537
|
+
if (schema.hasGamepad) {
|
|
4538
|
+
const gamepad = {
|
|
4539
|
+
buttons: inputSource.gamepad.buttons.map((button) => button
|
|
4540
|
+
? [button.pressed ? 1 : 0, button.touched ? 1 : 0, button.value]
|
|
4541
|
+
: null),
|
|
4542
|
+
axes: Array.from(inputSource.gamepad.axes),
|
|
4543
|
+
};
|
|
4544
|
+
inputFrame.gamepad = gamepad;
|
|
4545
|
+
}
|
|
4546
|
+
actionFrame.inputFrames.push(inputFrame);
|
|
4547
|
+
}
|
|
4548
|
+
});
|
|
4549
|
+
this[PRIVATE].compressedFrames.push(this.compressActionFrame(actionFrame));
|
|
4550
|
+
}
|
|
4551
|
+
compressActionFrame(af) {
|
|
4552
|
+
const out = [
|
|
4553
|
+
Math.round(af.timeStamp * 10) / 10,
|
|
4554
|
+
...compress(af.position),
|
|
4555
|
+
...compress(af.quaternion),
|
|
4556
|
+
];
|
|
4557
|
+
af.inputFrames.forEach((inputFrame) => {
|
|
4558
|
+
const index = inputFrame.index;
|
|
4559
|
+
const schema = this[PRIVATE].schemaMap.get(index);
|
|
4560
|
+
const inputOut = [
|
|
4561
|
+
index,
|
|
4562
|
+
...compress(inputFrame.targetRayTransform.position),
|
|
4563
|
+
...compress(inputFrame.targetRayTransform.quaternion),
|
|
4564
|
+
];
|
|
4565
|
+
if (schema.hasGrip) {
|
|
4566
|
+
inputOut.push([
|
|
4567
|
+
...compress(inputFrame.gripTransform.position),
|
|
4568
|
+
...compress(inputFrame.gripTransform.quaternion),
|
|
4569
|
+
]);
|
|
4570
|
+
}
|
|
4571
|
+
if (schema.hasHand) {
|
|
4572
|
+
const handArr = [];
|
|
4573
|
+
Object.values(inputFrame.hand).forEach(({ position, quaternion, radius }) => {
|
|
4574
|
+
handArr.push(...compress(position), ...compress(quaternion), parseFloat(radius.toFixed(3)));
|
|
4575
|
+
});
|
|
4576
|
+
inputOut.push(handArr);
|
|
4577
|
+
}
|
|
4578
|
+
if (schema.hasGamepad) {
|
|
4579
|
+
inputOut.push([
|
|
4580
|
+
...inputFrame.gamepad.buttons,
|
|
4581
|
+
...inputFrame.gamepad.axes,
|
|
4582
|
+
]);
|
|
4583
|
+
}
|
|
4584
|
+
out.push(inputOut);
|
|
4585
|
+
});
|
|
4586
|
+
return out;
|
|
4587
|
+
}
|
|
4588
|
+
log() {
|
|
4589
|
+
const out = {
|
|
4590
|
+
schema: Array.from(this[PRIVATE].schemaMap.entries()),
|
|
4591
|
+
frames: this[PRIVATE].compressedFrames,
|
|
4592
|
+
};
|
|
4593
|
+
console.log(JSON.stringify(out));
|
|
4594
|
+
}
|
|
4595
|
+
}
|
|
4596
|
+
|
|
4597
|
+
exports.ActionRecorder = ActionRecorder;
|
|
4598
|
+
exports.XRDevice = XRDevice;
|
|
4599
|
+
exports.XRFrame = XRFrame;
|
|
4600
|
+
exports.XRHand = XRHand;
|
|
4601
|
+
exports.XRInputSource = XRInputSource;
|
|
4602
|
+
exports.XRInputSourceArray = XRInputSourceArray;
|
|
4603
|
+
exports.XRInputSourceEvent = XRInputSourceEvent;
|
|
4604
|
+
exports.XRInputSourcesChangeEvent = XRInputSourcesChangeEvent;
|
|
4605
|
+
exports.XRJointPose = XRJointPose;
|
|
4606
|
+
exports.XRJointSpace = XRJointSpace;
|
|
4607
|
+
exports.XRLayer = XRLayer;
|
|
4608
|
+
exports.XRPose = XRPose;
|
|
4609
|
+
exports.XRReferenceSpace = XRReferenceSpace;
|
|
4610
|
+
exports.XRReferenceSpaceEvent = XRReferenceSpaceEvent;
|
|
4611
|
+
exports.XRRenderState = XRRenderState;
|
|
4612
|
+
exports.XRRigidTransform = XRRigidTransform;
|
|
4613
|
+
exports.XRSession = XRSession;
|
|
4614
|
+
exports.XRSessionEvent = XRSessionEvent;
|
|
4615
|
+
exports.XRSpace = XRSpace;
|
|
4616
|
+
exports.XRSystem = XRSystem;
|
|
4617
|
+
exports.XRView = XRView;
|
|
4618
|
+
exports.XRViewerPose = XRViewerPose;
|
|
4619
|
+
exports.XRViewport = XRViewport;
|
|
4620
|
+
exports.XRWebGLLayer = XRWebGLLayer;
|
|
4621
|
+
exports.metaQuest2 = metaQuest2;
|
|
4622
|
+
exports.metaQuest3 = metaQuest3;
|
|
4623
|
+
exports.metaQuestPro = metaQuestPro;
|
|
4624
|
+
exports.oculusQuest1 = oculusQuest1;
|
|
4625
|
+
|
|
4626
|
+
Object.defineProperty(exports, '__esModule', { value: true });
|
|
4627
|
+
|
|
4628
|
+
}));
|