mujoco-react 10.4.0 → 10.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +73 -136
- package/dist/{chunk-FBXXXPLQ.js → chunk-EN55TTGH.js} +157 -16
- package/dist/chunk-EN55TTGH.js.map +1 -0
- package/dist/index.d.ts +179 -48
- package/dist/index.js +487 -20
- package/dist/index.js.map +1 -1
- package/dist/onnx.d.ts +65 -0
- package/dist/onnx.js +58 -0
- package/dist/onnx.js.map +1 -0
- package/dist/spark.d.ts +1 -1
- package/dist/spark.js +1 -1
- package/dist/{types-CdFZCYmy.d.ts → types-Dvtm4I0o.d.ts} +155 -4
- package/package.json +14 -3
- package/src/components/CameraView.tsx +245 -0
- package/src/core/GenericIK.ts +22 -3
- package/src/core/MujocoSimProvider.tsx +37 -1
- package/src/core/SceneLoader.ts +3 -2
- package/src/hooks/useCameraStream.ts +115 -0
- package/src/hooks/useControlGroup.ts +0 -0
- package/src/hooks/useIkController.ts +36 -5
- package/src/hooks/usePolicyCameraTensors.ts +215 -0
- package/src/index.ts +44 -0
- package/src/onnx.ts +126 -0
- package/src/policyImageTensors.ts +150 -0
- package/src/rendering/cameraFrameCapture.ts +112 -15
- package/src/types.ts +50 -3
- package/dist/chunk-FBXXXPLQ.js.map +0 -1
package/dist/index.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { withContacts, getContact, captureCameraFrame, captureCameraFrameBlob, createCameraFrameCaptureSession, CAMERA_FRAME_CAPTURE_PRE_RENDER_USER_DATA_KEY, CAPTURE_EXCLUDE_KEY } from './chunk-
|
|
2
|
-
export { CAMERA_FRAME_CAPTURE_PRE_RENDER_USER_DATA_KEY, CAMERA_FRAME_CAPTURE_RENDER_USER_DATA_KEY, CAPTURE_EXCLUDE_KEY, ModelActuators, ModelBodies, ModelCameras, ModelGeoms, ModelJoints, ModelKeyframes, ModelResources, ModelSensors, ModelSites, ScenarioLighting, SplatEnvironment, SplatEnvironmentReadinessStatus, VisualScenarioEffects, captureCameraFrame, captureCameraFrameBlob, createCameraFrameCaptureSession, createPairedSplatEnvironment, createSparkSplatViewerUrl, createSplatEnvironmentUserData, createSplatSceneConfig, createVisualScenarioExecutionContext, getContact, getScenarioBackground, getScenarioCameraPosition, getSplatEnvironmentReadiness, registerModelResources, renderCameraFrameToCanvas, useSplatEnvironment, useSplatSceneConfig, useVisualScenarioEffects, useVisualScenarioExecutionContext, withSplatEnvironment } from './chunk-
|
|
1
|
+
import { withContacts, getContact, captureCameraFrame, captureCameraFrameBlob, createCameraFrameCaptureSession, CAMERA_FRAME_CAPTURE_PRE_RENDER_USER_DATA_KEY, CAPTURE_EXCLUDE_KEY, createCaptureCamera, prepareCaptureCamera } from './chunk-EN55TTGH.js';
|
|
2
|
+
export { CAMERA_FRAME_CAPTURE_PRE_RENDER_USER_DATA_KEY, CAMERA_FRAME_CAPTURE_RENDER_USER_DATA_KEY, CAPTURE_EXCLUDE_KEY, ModelActuators, ModelBodies, ModelCameras, ModelGeoms, ModelJoints, ModelKeyframes, ModelResources, ModelSensors, ModelSites, ScenarioLighting, SplatEnvironment, SplatEnvironmentReadinessStatus, VisualScenarioEffects, captureCameraFrame, captureCameraFrameBlob, captureCameraFrameTensor, createCameraFrameCaptureSession, createPairedSplatEnvironment, createSparkSplatViewerUrl, createSplatEnvironmentUserData, createSplatSceneConfig, createVisualScenarioExecutionContext, dataUrlToPolicyImageTensor, getContact, getScenarioBackground, getScenarioCameraPosition, getSplatEnvironmentReadiness, imageDataToPolicyImageTensor, pixelsToPolicyImageTensor, registerModelResources, renderCameraFrameToCanvas, useSplatEnvironment, useSplatSceneConfig, useVisualScenarioEffects, useVisualScenarioExecutionContext, withSplatEnvironment } from './chunk-EN55TTGH.js';
|
|
3
3
|
import loadMujoco from '@mujoco/mujoco';
|
|
4
4
|
import defaultMujocoWasmUrl from '@mujoco/mujoco/mujoco.wasm?url';
|
|
5
|
-
import { createContext, forwardRef, useRef, useEffect, useContext, useState, useCallback, useMemo, useLayoutEffect } from 'react';
|
|
5
|
+
import { createContext, forwardRef, useRef, useEffect, useContext, useState, useCallback, useMemo, useLayoutEffect, useId } from 'react';
|
|
6
6
|
import { jsx, jsxs } from 'react/jsx-runtime';
|
|
7
7
|
import { Canvas, useThree, useFrame } from '@react-three/fiber';
|
|
8
8
|
import * as THREE11 from 'three';
|
|
@@ -492,8 +492,10 @@ function sceneObjectToXml(obj) {
|
|
|
492
492
|
const solref = obj.solref ? ` solref="${obj.solref}"` : "";
|
|
493
493
|
const solimp = obj.solimp ? ` solimp="${obj.solimp}"` : "";
|
|
494
494
|
const condim = obj.condim ? ` condim="${obj.condim}"` : "";
|
|
495
|
+
const contype = obj.contype ?? 1;
|
|
496
|
+
const conaffinity = obj.conaffinity ?? 1;
|
|
495
497
|
const group = obj.group !== void 0 ? ` group="${obj.group}"` : "";
|
|
496
|
-
return `<body name="${obj.name}" pos="${pos}">${joint}<geom name="${geomName}" type="${obj.type}" size="${size}" rgba="${rgba}" contype="
|
|
498
|
+
return `<body name="${obj.name}" pos="${pos}">${joint}<geom name="${geomName}" type="${obj.type}" size="${size}" rgba="${rgba}" contype="${contype}" conaffinity="${conaffinity}"${mass}${friction}${solref}${solimp}${condim}${group}/></body>`;
|
|
497
499
|
}
|
|
498
500
|
function ensureDir(mujoco, fname) {
|
|
499
501
|
const dirParts = fname.split("/");
|
|
@@ -1170,6 +1172,118 @@ function SceneRenderer({ renderOptions, ...props }) {
|
|
|
1170
1172
|
}
|
|
1171
1173
|
var _previousQuat = new THREE11.Quaternion();
|
|
1172
1174
|
var _currentQuat = new THREE11.Quaternion();
|
|
1175
|
+
var CameraViewportRegistryContext = createContext(null);
|
|
1176
|
+
var nextViewportId = 0;
|
|
1177
|
+
var VIEWPORT_RENDER_PRIORITY = 1;
|
|
1178
|
+
function CameraViewportRenderer({
|
|
1179
|
+
viewportsRef
|
|
1180
|
+
}) {
|
|
1181
|
+
const gl = useThree((state) => state.gl);
|
|
1182
|
+
const scene = useThree((state) => state.scene);
|
|
1183
|
+
const mainCamera = useThree((state) => state.camera);
|
|
1184
|
+
const mujoco = useMujoco();
|
|
1185
|
+
useFrame(() => {
|
|
1186
|
+
const drawWidth = gl.domElement.width;
|
|
1187
|
+
const drawHeight = gl.domElement.height;
|
|
1188
|
+
gl.setScissorTest(false);
|
|
1189
|
+
gl.setViewport(0, 0, drawWidth, drawHeight);
|
|
1190
|
+
gl.render(scene, mainCamera);
|
|
1191
|
+
const api = mujoco.api;
|
|
1192
|
+
if (!api || viewportsRef.current.size === 0) return;
|
|
1193
|
+
const dpr = gl.getPixelRatio();
|
|
1194
|
+
const canvasRect = gl.domElement.getBoundingClientRect();
|
|
1195
|
+
for (const descriptor of viewportsRef.current.values()) {
|
|
1196
|
+
const element = descriptor.getElement();
|
|
1197
|
+
if (!element) continue;
|
|
1198
|
+
const rect = element.getBoundingClientRect();
|
|
1199
|
+
const isOffscreen = rect.bottom < canvasRect.top || rect.top > canvasRect.bottom || rect.right < canvasRect.left || rect.left > canvasRect.right;
|
|
1200
|
+
if (isOffscreen) continue;
|
|
1201
|
+
const width = Math.floor(rect.width * dpr);
|
|
1202
|
+
const height = Math.floor(rect.height * dpr);
|
|
1203
|
+
if (width <= 0 || height <= 0) continue;
|
|
1204
|
+
const left = Math.floor((rect.left - canvasRect.left) * dpr);
|
|
1205
|
+
const bottom = Math.floor((canvasRect.bottom - rect.bottom) * dpr);
|
|
1206
|
+
let resolved;
|
|
1207
|
+
try {
|
|
1208
|
+
resolved = api.resolveCameraCaptureOptions(descriptor.getOptions());
|
|
1209
|
+
} catch {
|
|
1210
|
+
continue;
|
|
1211
|
+
}
|
|
1212
|
+
if (!descriptor.camera) {
|
|
1213
|
+
descriptor.camera = createCaptureCamera(resolved, mainCamera, width, height);
|
|
1214
|
+
} else {
|
|
1215
|
+
prepareCaptureCamera(descriptor.camera, resolved, mainCamera, width, height);
|
|
1216
|
+
}
|
|
1217
|
+
gl.setViewport(left, bottom, width, height);
|
|
1218
|
+
gl.setScissor(left, bottom, width, height);
|
|
1219
|
+
gl.setScissorTest(true);
|
|
1220
|
+
gl.render(scene, descriptor.camera);
|
|
1221
|
+
}
|
|
1222
|
+
gl.setScissorTest(false);
|
|
1223
|
+
gl.setViewport(0, 0, drawWidth, drawHeight);
|
|
1224
|
+
}, VIEWPORT_RENDER_PRIORITY);
|
|
1225
|
+
return null;
|
|
1226
|
+
}
|
|
1227
|
+
function CameraViewportProvider({ children }) {
|
|
1228
|
+
const viewportsRef = useRef(/* @__PURE__ */ new Map());
|
|
1229
|
+
const [count, setCount] = useState(0);
|
|
1230
|
+
const register = useCallback((descriptor) => {
|
|
1231
|
+
const id = nextViewportId++;
|
|
1232
|
+
viewportsRef.current.set(id, descriptor);
|
|
1233
|
+
setCount((value2) => value2 + 1);
|
|
1234
|
+
return () => {
|
|
1235
|
+
viewportsRef.current.delete(id);
|
|
1236
|
+
setCount((value2) => value2 - 1);
|
|
1237
|
+
};
|
|
1238
|
+
}, []);
|
|
1239
|
+
const value = useMemo(() => ({ register }), [register]);
|
|
1240
|
+
return /* @__PURE__ */ jsxs(CameraViewportRegistryContext.Provider, { value, children: [
|
|
1241
|
+
children,
|
|
1242
|
+
count > 0 && /* @__PURE__ */ jsx(CameraViewportRenderer, { viewportsRef })
|
|
1243
|
+
] });
|
|
1244
|
+
}
|
|
1245
|
+
function useCameraViewport(elementRef, options) {
|
|
1246
|
+
const registry = useContext(CameraViewportRegistryContext);
|
|
1247
|
+
if (!registry) {
|
|
1248
|
+
throw new Error("useCameraViewport must be used inside <MujocoCanvas>.");
|
|
1249
|
+
}
|
|
1250
|
+
const optionsRef = useRef(options);
|
|
1251
|
+
optionsRef.current = options;
|
|
1252
|
+
useEffect(() => {
|
|
1253
|
+
const descriptor = {
|
|
1254
|
+
getElement: () => elementRef.current,
|
|
1255
|
+
getOptions: () => optionsRef.current,
|
|
1256
|
+
camera: null
|
|
1257
|
+
};
|
|
1258
|
+
return registry.register(descriptor);
|
|
1259
|
+
}, [registry, elementRef]);
|
|
1260
|
+
}
|
|
1261
|
+
function CameraView({ className, style, ...options }) {
|
|
1262
|
+
const gl = useThree((state) => state.gl);
|
|
1263
|
+
const elementRef = useRef(null);
|
|
1264
|
+
if (!elementRef.current && typeof document !== "undefined") {
|
|
1265
|
+
elementRef.current = document.createElement("div");
|
|
1266
|
+
}
|
|
1267
|
+
useEffect(() => {
|
|
1268
|
+
const element = elementRef.current;
|
|
1269
|
+
const parent = gl.domElement.parentElement;
|
|
1270
|
+
if (!element || !parent) return;
|
|
1271
|
+
element.style.position = "absolute";
|
|
1272
|
+
element.style.overflow = "hidden";
|
|
1273
|
+
parent.appendChild(element);
|
|
1274
|
+
return () => {
|
|
1275
|
+
parent.removeChild(element);
|
|
1276
|
+
};
|
|
1277
|
+
}, [gl]);
|
|
1278
|
+
useEffect(() => {
|
|
1279
|
+
const element = elementRef.current;
|
|
1280
|
+
if (!element) return;
|
|
1281
|
+
element.className = className ?? "";
|
|
1282
|
+
if (style) Object.assign(element.style, style);
|
|
1283
|
+
}, [className, style]);
|
|
1284
|
+
useCameraViewport(elementRef, options);
|
|
1285
|
+
return null;
|
|
1286
|
+
}
|
|
1173
1287
|
function isTargetRef(target) {
|
|
1174
1288
|
return Boolean(target && typeof target === "object" && "current" in target);
|
|
1175
1289
|
}
|
|
@@ -3021,6 +3135,32 @@ function MujocoSimProvider({
|
|
|
3021
3135
|
},
|
|
3022
3136
|
[camera, gl, resolveCameraCaptureOptions, scene]
|
|
3023
3137
|
);
|
|
3138
|
+
const createCameraFrameCaptureSessionApi = useCallback(
|
|
3139
|
+
(options = {}) => createCameraFrameCaptureSession(
|
|
3140
|
+
gl,
|
|
3141
|
+
scene,
|
|
3142
|
+
camera,
|
|
3143
|
+
resolveCameraCaptureOptions(options)
|
|
3144
|
+
),
|
|
3145
|
+
[camera, gl, resolveCameraCaptureOptions, scene]
|
|
3146
|
+
);
|
|
3147
|
+
const captureCameraFrameTensorApi = useCallback(
|
|
3148
|
+
(options = {}) => {
|
|
3149
|
+
const resolved = {
|
|
3150
|
+
...resolveCameraCaptureOptions(options),
|
|
3151
|
+
channels: options.channels,
|
|
3152
|
+
layout: options.layout,
|
|
3153
|
+
range: options.range
|
|
3154
|
+
};
|
|
3155
|
+
const session = createCameraFrameCaptureSession(gl, scene, camera, resolved);
|
|
3156
|
+
try {
|
|
3157
|
+
return session.captureTensor(resolved);
|
|
3158
|
+
} finally {
|
|
3159
|
+
session.dispose();
|
|
3160
|
+
}
|
|
3161
|
+
},
|
|
3162
|
+
[camera, gl, resolveCameraCaptureOptions, scene]
|
|
3163
|
+
);
|
|
3024
3164
|
const recordCameraSequenceApi = useCallback(
|
|
3025
3165
|
async (options) => {
|
|
3026
3166
|
const frameCount = Math.max(0, Math.floor(options.frames));
|
|
@@ -3320,6 +3460,9 @@ function MujocoSimProvider({
|
|
|
3320
3460
|
captureFrameBlob: captureFrameBlobApi,
|
|
3321
3461
|
captureCameraFrame: captureCameraFrameApi,
|
|
3322
3462
|
captureCameraFrameBlob: captureCameraFrameBlobApi,
|
|
3463
|
+
captureCameraFrameTensor: captureCameraFrameTensorApi,
|
|
3464
|
+
createCameraFrameCaptureSession: createCameraFrameCaptureSessionApi,
|
|
3465
|
+
resolveCameraCaptureOptions,
|
|
3323
3466
|
recordCameraSequence: recordCameraSequenceApi,
|
|
3324
3467
|
project2DTo3D,
|
|
3325
3468
|
projectImagePointTo3D: projectImagePointTo3D2,
|
|
@@ -3380,6 +3523,9 @@ function MujocoSimProvider({
|
|
|
3380
3523
|
captureFrameBlobApi,
|
|
3381
3524
|
captureCameraFrameApi,
|
|
3382
3525
|
captureCameraFrameBlobApi,
|
|
3526
|
+
captureCameraFrameTensorApi,
|
|
3527
|
+
createCameraFrameCaptureSessionApi,
|
|
3528
|
+
resolveCameraCaptureOptions,
|
|
3383
3529
|
recordCameraSequenceApi,
|
|
3384
3530
|
project2DTo3D,
|
|
3385
3531
|
projectImagePointTo3D2,
|
|
@@ -3416,7 +3562,7 @@ function MujocoSimProvider({
|
|
|
3416
3562
|
);
|
|
3417
3563
|
return /* @__PURE__ */ jsxs(MujocoSimContext.Provider, { value: contextValue, children: [
|
|
3418
3564
|
/* @__PURE__ */ jsx(SceneRenderer, { renderOptions }),
|
|
3419
|
-
children
|
|
3565
|
+
/* @__PURE__ */ jsx(CameraViewportProvider, { children })
|
|
3420
3566
|
] });
|
|
3421
3567
|
}
|
|
3422
3568
|
var MujocoCanvas = forwardRef(
|
|
@@ -3641,7 +3787,8 @@ function resolveOptions(opts) {
|
|
|
3641
3787
|
tolerance: opts?.tolerance ?? DEFAULTS.tolerance,
|
|
3642
3788
|
epsilon: opts?.epsilon ?? DEFAULTS.epsilon,
|
|
3643
3789
|
posWeight: opts?.posWeight ?? DEFAULTS.posWeight,
|
|
3644
|
-
rotWeight: opts?.rotWeight ?? DEFAULTS.rotWeight
|
|
3790
|
+
rotWeight: opts?.rotWeight ?? DEFAULTS.rotWeight,
|
|
3791
|
+
jointLimits: opts?.jointLimits
|
|
3645
3792
|
};
|
|
3646
3793
|
}
|
|
3647
3794
|
var GenericIK = class {
|
|
@@ -3680,6 +3827,8 @@ var GenericIK = class {
|
|
|
3680
3827
|
const pertSiteMat = new Float64Array(9);
|
|
3681
3828
|
let bestQ = null;
|
|
3682
3829
|
let bestErr = Infinity;
|
|
3830
|
+
const patience = 4;
|
|
3831
|
+
let noImprove = 0;
|
|
3683
3832
|
if (n === 0) return null;
|
|
3684
3833
|
for (let iter = 0; iter < o.maxIterations; iter++) {
|
|
3685
3834
|
for (let i = 0; i < n; i++) data.qpos[qposAdr[i]] = q[i];
|
|
@@ -3705,11 +3854,15 @@ var GenericIK = class {
|
|
|
3705
3854
|
const errNorm = Math.sqrt(
|
|
3706
3855
|
error[0] * error[0] + error[1] * error[1] + error[2] * error[2] + error[3] * error[3] + error[4] * error[4] + error[5] * error[5]
|
|
3707
3856
|
);
|
|
3708
|
-
if (errNorm < bestErr) {
|
|
3857
|
+
if (errNorm < bestErr - 1e-9) {
|
|
3709
3858
|
bestErr = errNorm;
|
|
3710
3859
|
bestQ = Array.from(q);
|
|
3860
|
+
noImprove = 0;
|
|
3861
|
+
} else {
|
|
3862
|
+
noImprove++;
|
|
3711
3863
|
}
|
|
3712
3864
|
if (errNorm < o.tolerance) break;
|
|
3865
|
+
if (noImprove >= patience) break;
|
|
3713
3866
|
for (let j = 0; j < n; j++) {
|
|
3714
3867
|
const adr = qposAdr[j];
|
|
3715
3868
|
const saved = data.qpos[adr];
|
|
@@ -3865,6 +4018,12 @@ function solve6x6(A, b, x) {
|
|
|
3865
4018
|
|
|
3866
4019
|
// src/hooks/useIkController.ts
|
|
3867
4020
|
var _syncMat4 = new THREE11.Matrix4();
|
|
4021
|
+
function toIkVector3(value) {
|
|
4022
|
+
return "x" in value ? new THREE11.Vector3(value.x, value.y, value.z) : new THREE11.Vector3(value[0], value[1], value[2]);
|
|
4023
|
+
}
|
|
4024
|
+
function toIkQuaternion(value) {
|
|
4025
|
+
return "x" in value ? new THREE11.Quaternion(value.x, value.y, value.z, value.w) : new THREE11.Quaternion(value[0], value[1], value[2], value[3]);
|
|
4026
|
+
}
|
|
3868
4027
|
function syncGizmoToSite(data, siteId, target) {
|
|
3869
4028
|
if (siteId === -1) return;
|
|
3870
4029
|
const sitePos = data.site_xpos.subarray(siteId * 3, siteId * 3 + 3);
|
|
@@ -3937,22 +4096,31 @@ var useIkController = createControllerHook(
|
|
|
3937
4096
|
const ikSolveFn = useCallback(
|
|
3938
4097
|
({ position, quaternion, currentQ, context }) => {
|
|
3939
4098
|
if (!config) return null;
|
|
3940
|
-
|
|
4099
|
+
const targetPosition = toIkVector3(position);
|
|
4100
|
+
const targetQuaternion = toIkQuaternion(quaternion);
|
|
4101
|
+
const normalizedInput = {
|
|
4102
|
+
position: targetPosition,
|
|
4103
|
+
quaternion: targetQuaternion,
|
|
4104
|
+
currentQ,
|
|
4105
|
+
context
|
|
4106
|
+
};
|
|
4107
|
+
if (config.ikSolveFn) return config.ikSolveFn(normalizedInput);
|
|
3941
4108
|
const model = mjModelRef.current;
|
|
3942
4109
|
const data = mjDataRef.current;
|
|
3943
|
-
const
|
|
3944
|
-
if (!model || !data || !
|
|
4110
|
+
const controlGroup2 = controlGroupRef.current;
|
|
4111
|
+
if (!model || !data || !controlGroup2 || siteIdRef.current === -1) return null;
|
|
3945
4112
|
return genericIkRef.current.solve(
|
|
3946
4113
|
model,
|
|
3947
4114
|
data,
|
|
3948
4115
|
siteIdRef.current,
|
|
3949
|
-
|
|
3950
|
-
|
|
3951
|
-
|
|
4116
|
+
controlGroup2.qposAdr,
|
|
4117
|
+
targetPosition,
|
|
4118
|
+
targetQuaternion,
|
|
3952
4119
|
currentQ,
|
|
3953
4120
|
{
|
|
3954
4121
|
damping: config.damping,
|
|
3955
4122
|
epsilon: config.epsilon,
|
|
4123
|
+
jointLimits: config.jointLimits ?? controlGroup2.joints.map((joint) => joint.limited ? joint.range : joint.ctrlRange),
|
|
3956
4124
|
maxIterations: config.maxIterations,
|
|
3957
4125
|
posWeight: config.posWeight,
|
|
3958
4126
|
rotWeight: config.rotWeight,
|
|
@@ -3992,9 +4160,9 @@ var useIkController = createControllerHook(
|
|
|
3992
4160
|
const target = ikTargetRef.current;
|
|
3993
4161
|
if (!target) return;
|
|
3994
4162
|
ikCalculatingRef.current = true;
|
|
3995
|
-
const
|
|
3996
|
-
if (!
|
|
3997
|
-
const currentQ = Array.from(
|
|
4163
|
+
const controlGroup2 = controlGroupRef.current;
|
|
4164
|
+
if (!controlGroup2) return;
|
|
4165
|
+
const currentQ = Array.from(controlGroup2.readQpos(data));
|
|
3998
4166
|
const solution = config.ikSolveFn ? config.ikSolveFn({
|
|
3999
4167
|
position: target.position,
|
|
4000
4168
|
quaternion: target.quaternion,
|
|
@@ -4003,7 +4171,7 @@ var useIkController = createControllerHook(
|
|
|
4003
4171
|
model,
|
|
4004
4172
|
data,
|
|
4005
4173
|
siteId: siteIdRef.current,
|
|
4006
|
-
controlGroup
|
|
4174
|
+
controlGroup: controlGroup2
|
|
4007
4175
|
}
|
|
4008
4176
|
}) : ikSolveFnRef.current({
|
|
4009
4177
|
position: target.position,
|
|
@@ -4011,7 +4179,7 @@ var useIkController = createControllerHook(
|
|
|
4011
4179
|
currentQ
|
|
4012
4180
|
});
|
|
4013
4181
|
if (solution) {
|
|
4014
|
-
|
|
4182
|
+
controlGroup2.writeCtrl(data, solution);
|
|
4015
4183
|
}
|
|
4016
4184
|
});
|
|
4017
4185
|
useEffect(() => {
|
|
@@ -4058,7 +4226,7 @@ var useIkController = createControllerHook(
|
|
|
4058
4226
|
if (!ikEnabledRef.current) setIkEnabled(true);
|
|
4059
4227
|
const target = ikTargetRef.current;
|
|
4060
4228
|
if (!target) return;
|
|
4061
|
-
const targetPos = pos
|
|
4229
|
+
const targetPos = toIkVector3(pos);
|
|
4062
4230
|
const targetRot = new THREE11.Quaternion().setFromEuler(
|
|
4063
4231
|
new THREE11.Euler(Math.PI, 0, 0)
|
|
4064
4232
|
);
|
|
@@ -4848,6 +5016,69 @@ function parseNumberList(value) {
|
|
|
4848
5016
|
function addProxyVectors(a, b) {
|
|
4849
5017
|
return [a[0] + b[0], a[1] + b[1], a[2] + b[2]];
|
|
4850
5018
|
}
|
|
5019
|
+
function streamSignature(options) {
|
|
5020
|
+
return JSON.stringify({
|
|
5021
|
+
cameraName: options.cameraName,
|
|
5022
|
+
siteName: options.siteName,
|
|
5023
|
+
bodyName: options.bodyName,
|
|
5024
|
+
width: options.width,
|
|
5025
|
+
height: options.height,
|
|
5026
|
+
renderIsolation: options.renderIsolation ?? false
|
|
5027
|
+
});
|
|
5028
|
+
}
|
|
5029
|
+
function useCameraStream(canvasRef, options) {
|
|
5030
|
+
const mujoco = useMujoco();
|
|
5031
|
+
const sessionRef = useRef(null);
|
|
5032
|
+
const signatureRef = useRef("");
|
|
5033
|
+
const optionsRef = useRef(options);
|
|
5034
|
+
optionsRef.current = options;
|
|
5035
|
+
const elapsedRef = useRef(0);
|
|
5036
|
+
const inFlightRef = useRef(false);
|
|
5037
|
+
const mountedRef = useRef(true);
|
|
5038
|
+
useEffect(() => {
|
|
5039
|
+
mountedRef.current = true;
|
|
5040
|
+
return () => {
|
|
5041
|
+
mountedRef.current = false;
|
|
5042
|
+
sessionRef.current?.dispose();
|
|
5043
|
+
sessionRef.current = null;
|
|
5044
|
+
signatureRef.current = "";
|
|
5045
|
+
};
|
|
5046
|
+
}, []);
|
|
5047
|
+
useFrame((_state, delta) => {
|
|
5048
|
+
const api = mujoco.api;
|
|
5049
|
+
if (!api || !canvasRef.current) return;
|
|
5050
|
+
const opts = optionsRef.current;
|
|
5051
|
+
if (opts.paused) return;
|
|
5052
|
+
if (opts.fps && opts.fps > 0) {
|
|
5053
|
+
elapsedRef.current += delta;
|
|
5054
|
+
if (elapsedRef.current < 1 / opts.fps) return;
|
|
5055
|
+
}
|
|
5056
|
+
if (inFlightRef.current) return;
|
|
5057
|
+
elapsedRef.current = 0;
|
|
5058
|
+
const signature = streamSignature(opts);
|
|
5059
|
+
if (!sessionRef.current || signatureRef.current !== signature) {
|
|
5060
|
+
sessionRef.current?.dispose();
|
|
5061
|
+
sessionRef.current = api.createCameraFrameCaptureSession(opts);
|
|
5062
|
+
signatureRef.current = signature;
|
|
5063
|
+
}
|
|
5064
|
+
const session = sessionRef.current;
|
|
5065
|
+
inFlightRef.current = true;
|
|
5066
|
+
session.captureAsync(api.resolveCameraCaptureOptions(opts)).then((frame) => {
|
|
5067
|
+
const canvas = canvasRef.current;
|
|
5068
|
+
if (!mountedRef.current || !canvas) return;
|
|
5069
|
+
const ctx = canvas.getContext("2d");
|
|
5070
|
+
if (!ctx) return;
|
|
5071
|
+
if (canvas.width !== frame.width || canvas.height !== frame.height) {
|
|
5072
|
+
canvas.width = frame.width;
|
|
5073
|
+
canvas.height = frame.height;
|
|
5074
|
+
}
|
|
5075
|
+
ctx.drawImage(frame.canvas, 0, 0);
|
|
5076
|
+
}).catch(() => {
|
|
5077
|
+
}).finally(() => {
|
|
5078
|
+
inFlightRef.current = false;
|
|
5079
|
+
});
|
|
5080
|
+
});
|
|
5081
|
+
}
|
|
4851
5082
|
var JOINT_COLORS = {
|
|
4852
5083
|
0: 16711680,
|
|
4853
5084
|
// free - red
|
|
@@ -6526,6 +6757,73 @@ function useControlWriter(options) {
|
|
|
6526
6757
|
release
|
|
6527
6758
|
}), [canWrite, owner, read, release, write]);
|
|
6528
6759
|
}
|
|
6760
|
+
|
|
6761
|
+
// src/hooks/useControlGroup.ts
|
|
6762
|
+
function controlGroup(names) {
|
|
6763
|
+
return { keys: names };
|
|
6764
|
+
}
|
|
6765
|
+
function useControlGroup(group, options = {}) {
|
|
6766
|
+
const generatedOwner = useId();
|
|
6767
|
+
const owner = options.owner ?? `control-group:${generatedOwner}`;
|
|
6768
|
+
const { mjModelRef, mjDataRef, status } = useMujocoContext();
|
|
6769
|
+
const names = group.keys;
|
|
6770
|
+
const namesRef = useRef(names);
|
|
6771
|
+
namesRef.current = names;
|
|
6772
|
+
const namesKey = names.join("\0");
|
|
6773
|
+
const selector = useMemo(
|
|
6774
|
+
() => ({ actuators: [...names] }),
|
|
6775
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
6776
|
+
[namesKey]
|
|
6777
|
+
);
|
|
6778
|
+
const { canWrite, release } = useControlWriter({ ...options, owner, selector });
|
|
6779
|
+
const indicesRef = useRef([]);
|
|
6780
|
+
useEffect(() => {
|
|
6781
|
+
const model = mjModelRef.current;
|
|
6782
|
+
if (!model || status !== "ready") {
|
|
6783
|
+
indicesRef.current = [];
|
|
6784
|
+
return;
|
|
6785
|
+
}
|
|
6786
|
+
indicesRef.current = namesRef.current.map((name) => {
|
|
6787
|
+
const id = findActuatorByName(model, name);
|
|
6788
|
+
if (id < 0) {
|
|
6789
|
+
console.warn(`[mujoco-react] useControlGroup: actuator "${name}" was not found.`);
|
|
6790
|
+
}
|
|
6791
|
+
return id;
|
|
6792
|
+
});
|
|
6793
|
+
}, [mjModelRef, status, namesKey]);
|
|
6794
|
+
const set = useCallback(
|
|
6795
|
+
(values, setOptions = {}) => {
|
|
6796
|
+
const data = mjDataRef.current;
|
|
6797
|
+
if (!data) return false;
|
|
6798
|
+
if (!setOptions.force && !canWrite()) return false;
|
|
6799
|
+
const groupNames = namesRef.current;
|
|
6800
|
+
const indices = indicesRef.current;
|
|
6801
|
+
for (let i = 0; i < groupNames.length; i += 1) {
|
|
6802
|
+
const value = values[groupNames[i]];
|
|
6803
|
+
if (value === void 0) continue;
|
|
6804
|
+
const adr = indices[i];
|
|
6805
|
+
if (adr >= 0) data.ctrl[adr] = value;
|
|
6806
|
+
}
|
|
6807
|
+
return true;
|
|
6808
|
+
},
|
|
6809
|
+
[canWrite, mjDataRef]
|
|
6810
|
+
);
|
|
6811
|
+
const read = useCallback(() => {
|
|
6812
|
+
const data = mjDataRef.current;
|
|
6813
|
+
const groupNames = namesRef.current;
|
|
6814
|
+
const indices = indicesRef.current;
|
|
6815
|
+
const result = {};
|
|
6816
|
+
for (let i = 0; i < groupNames.length; i += 1) {
|
|
6817
|
+
const adr = indices[i];
|
|
6818
|
+
result[groupNames[i]] = data && adr >= 0 ? data.ctrl[adr] ?? 0 : 0;
|
|
6819
|
+
}
|
|
6820
|
+
return result;
|
|
6821
|
+
}, [mjDataRef]);
|
|
6822
|
+
return useMemo(
|
|
6823
|
+
() => ({ owner, set, read, canWrite, release }),
|
|
6824
|
+
[owner, set, read, canWrite, release]
|
|
6825
|
+
);
|
|
6826
|
+
}
|
|
6529
6827
|
var geomNameCacheByModel2 = /* @__PURE__ */ new WeakMap();
|
|
6530
6828
|
var bodyNameCacheByModel = /* @__PURE__ */ new WeakMap();
|
|
6531
6829
|
function getCachedName(cacheByModel, model, id, address) {
|
|
@@ -7822,6 +8120,130 @@ function usePolicyCameraFramesFromMountedStreams(defaultOptions) {
|
|
|
7822
8120
|
reset
|
|
7823
8121
|
};
|
|
7824
8122
|
}
|
|
8123
|
+
function sessionSignature(stream) {
|
|
8124
|
+
return JSON.stringify({
|
|
8125
|
+
width: stream.width,
|
|
8126
|
+
height: stream.height,
|
|
8127
|
+
channels: stream.channels,
|
|
8128
|
+
renderIsolation: stream.renderIsolation ?? false,
|
|
8129
|
+
cameraName: stream.cameraName,
|
|
8130
|
+
siteName: stream.siteName,
|
|
8131
|
+
bodyName: stream.bodyName
|
|
8132
|
+
});
|
|
8133
|
+
}
|
|
8134
|
+
function addTensorAliases(tensors, stream, tensor, includeObservationImageAliases) {
|
|
8135
|
+
const keys = /* @__PURE__ */ new Set([stream.key, ...stream.aliases ?? []]);
|
|
8136
|
+
if (includeObservationImageAliases) {
|
|
8137
|
+
for (const base of [stream.key, ...stream.aliases ?? []]) {
|
|
8138
|
+
keys.add(`observation.images.${base}`);
|
|
8139
|
+
}
|
|
8140
|
+
}
|
|
8141
|
+
for (const key of keys) tensors[key] = tensor;
|
|
8142
|
+
}
|
|
8143
|
+
function usePolicyCameraTensors(options) {
|
|
8144
|
+
const mujoco = useMujoco();
|
|
8145
|
+
const [status, setStatus] = useState("idle");
|
|
8146
|
+
const [error, setError] = useState(null);
|
|
8147
|
+
const sessionsRef = useRef(/* @__PURE__ */ new Map());
|
|
8148
|
+
const disposeSessions = useCallback(() => {
|
|
8149
|
+
for (const { session } of sessionsRef.current.values()) session.dispose();
|
|
8150
|
+
sessionsRef.current.clear();
|
|
8151
|
+
}, []);
|
|
8152
|
+
useEffect(() => disposeSessions, [disposeSessions]);
|
|
8153
|
+
const reset = useCallback(() => {
|
|
8154
|
+
setStatus("idle");
|
|
8155
|
+
setError(null);
|
|
8156
|
+
}, []);
|
|
8157
|
+
const capture = useCallback(() => {
|
|
8158
|
+
const api = mujoco.api;
|
|
8159
|
+
if (!api) {
|
|
8160
|
+
throw new Error("MuJoCo scene is not ready for policy camera tensor capture.");
|
|
8161
|
+
}
|
|
8162
|
+
setStatus("capturing");
|
|
8163
|
+
setError(null);
|
|
8164
|
+
try {
|
|
8165
|
+
const sessions = sessionsRef.current;
|
|
8166
|
+
const seen = /* @__PURE__ */ new Set();
|
|
8167
|
+
const tensors = {};
|
|
8168
|
+
const sourceParts = [];
|
|
8169
|
+
for (const stream of options.streams) {
|
|
8170
|
+
seen.add(stream.key);
|
|
8171
|
+
const resolved = {
|
|
8172
|
+
...api.resolveCameraCaptureOptions(stream),
|
|
8173
|
+
channels: stream.channels,
|
|
8174
|
+
layout: stream.layout,
|
|
8175
|
+
range: stream.range
|
|
8176
|
+
};
|
|
8177
|
+
const signature = sessionSignature(stream);
|
|
8178
|
+
let entry = sessions.get(stream.key);
|
|
8179
|
+
if (!entry || entry.signature !== signature) {
|
|
8180
|
+
entry?.session.dispose();
|
|
8181
|
+
entry = {
|
|
8182
|
+
session: api.createCameraFrameCaptureSession(resolved),
|
|
8183
|
+
signature
|
|
8184
|
+
};
|
|
8185
|
+
sessions.set(stream.key, entry);
|
|
8186
|
+
}
|
|
8187
|
+
const tensor = entry.session.captureTensor(resolved);
|
|
8188
|
+
addTensorAliases(
|
|
8189
|
+
tensors,
|
|
8190
|
+
stream,
|
|
8191
|
+
tensor,
|
|
8192
|
+
options.includeObservationImageAliases ?? false
|
|
8193
|
+
);
|
|
8194
|
+
sourceParts.push(`${stream.key}:${tensor.source.kind}`);
|
|
8195
|
+
}
|
|
8196
|
+
for (const key of [...sessions.keys()]) {
|
|
8197
|
+
if (!seen.has(key)) {
|
|
8198
|
+
sessions.get(key)?.session.dispose();
|
|
8199
|
+
sessions.delete(key);
|
|
8200
|
+
}
|
|
8201
|
+
}
|
|
8202
|
+
setStatus("captured");
|
|
8203
|
+
return {
|
|
8204
|
+
tensors,
|
|
8205
|
+
sourceSummary: sourceParts.join(" + ") || "not used by policy",
|
|
8206
|
+
capturedAt: Date.now()
|
|
8207
|
+
};
|
|
8208
|
+
} catch (nextError) {
|
|
8209
|
+
const captureError = nextError instanceof Error ? nextError : new Error("Unable to capture policy camera tensors.");
|
|
8210
|
+
setError(captureError);
|
|
8211
|
+
setStatus("error");
|
|
8212
|
+
throw captureError;
|
|
8213
|
+
}
|
|
8214
|
+
}, [mujoco.api, options.includeObservationImageAliases, options.streams]);
|
|
8215
|
+
return {
|
|
8216
|
+
status,
|
|
8217
|
+
error,
|
|
8218
|
+
isCapturing: status === "capturing",
|
|
8219
|
+
capture,
|
|
8220
|
+
reset
|
|
8221
|
+
};
|
|
8222
|
+
}
|
|
8223
|
+
function usePolicyCameraTensorsFromMountedStreams(options) {
|
|
8224
|
+
const mujoco = useMujoco();
|
|
8225
|
+
const tensorOptions = options.tensor;
|
|
8226
|
+
const mountedOptions = useMemo(() => {
|
|
8227
|
+
const api = mujoco.api;
|
|
8228
|
+
if (!api) {
|
|
8229
|
+
return {
|
|
8230
|
+
streams: [],
|
|
8231
|
+
includeObservationImageAliases: options.includeObservationImageAliases ?? false
|
|
8232
|
+
};
|
|
8233
|
+
}
|
|
8234
|
+
const plan = createPolicyCameraFrameCapturePlanFromApi(api, options);
|
|
8235
|
+
return {
|
|
8236
|
+
streams: plan.streams.map(({ key, aliases, ...stream }) => ({
|
|
8237
|
+
...stream,
|
|
8238
|
+
...tensorOptions,
|
|
8239
|
+
key,
|
|
8240
|
+
aliases
|
|
8241
|
+
})),
|
|
8242
|
+
includeObservationImageAliases: plan.includeObservationImageAliases ?? false
|
|
8243
|
+
};
|
|
8244
|
+
}, [mujoco.api, options, tensorOptions]);
|
|
8245
|
+
return usePolicyCameraTensors(mountedOptions);
|
|
8246
|
+
}
|
|
7825
8247
|
function useCameraSequenceRecorder() {
|
|
7826
8248
|
const mujoco = useMujoco();
|
|
7827
8249
|
const [status, setStatus] = useState("idle");
|
|
@@ -8126,6 +8548,19 @@ function useCameraAnimation() {
|
|
|
8126
8548
|
* @license
|
|
8127
8549
|
* SPDX-License-Identifier: Apache-2.0
|
|
8128
8550
|
*/
|
|
8551
|
+
/**
|
|
8552
|
+
* @license
|
|
8553
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
8554
|
+
*
|
|
8555
|
+
* Live on-screen camera viewports for MuJoCo scenes. Each view renders the
|
|
8556
|
+
* shared scene from a named MuJoCo camera/site/body into a `gl.scissor` region
|
|
8557
|
+
* tracking a DOM element — no GPU readback, no PNG encoding.
|
|
8558
|
+
*
|
|
8559
|
+
* While at least one viewport is mounted the canvas switches from R3F's
|
|
8560
|
+
* automatic render to a managed render loop (main scene full-frame, then each
|
|
8561
|
+
* viewport). This is incompatible with `EffectComposer`/postprocessing or other
|
|
8562
|
+
* custom render loops; use the offscreen capture APIs in those setups instead.
|
|
8563
|
+
*/
|
|
8129
8564
|
/**
|
|
8130
8565
|
* @license
|
|
8131
8566
|
* SPDX-License-Identifier: Apache-2.0
|
|
@@ -8174,6 +8609,21 @@ function useCameraAnimation() {
|
|
|
8174
8609
|
* light_type: 0 = directional, 1 = spot (maps to mjLIGHT_DIRECTIONAL/mjLIGHT_SPOT)
|
|
8175
8610
|
* Note: light_directional does NOT exist in WASM — use light_type instead.
|
|
8176
8611
|
*/
|
|
8612
|
+
/**
|
|
8613
|
+
* @license
|
|
8614
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
8615
|
+
*
|
|
8616
|
+
* Stream a live MuJoCo camera into a DOM `<canvas>`. Each frame the scene is
|
|
8617
|
+
* rendered offscreen from the selected camera and blitted into the canvas, so
|
|
8618
|
+
* it composites normally in the DOM (works inside opaque panels) and does NOT
|
|
8619
|
+
* take over the render loop. Prefer this over `useCameraViewport` for camera
|
|
8620
|
+
* tiles embedded in HTML UI; use `useCameraViewport` for transparent overlays
|
|
8621
|
+
* on a full-bleed canvas.
|
|
8622
|
+
*
|
|
8623
|
+
* Uses the async capture path so Gaussian-splat environments render through
|
|
8624
|
+
* their dedicated capture renderer — streaming a splat scene at full rate does
|
|
8625
|
+
* not disturb the main view's splat sort.
|
|
8626
|
+
*/
|
|
8177
8627
|
/**
|
|
8178
8628
|
* @license
|
|
8179
8629
|
* SPDX-License-Identifier: Apache-2.0
|
|
@@ -8259,6 +8709,14 @@ function useCameraAnimation() {
|
|
|
8259
8709
|
*
|
|
8260
8710
|
* Cooperative actuator/control ownership for policies, IK, teleop, and replay.
|
|
8261
8711
|
*/
|
|
8712
|
+
/**
|
|
8713
|
+
* @license
|
|
8714
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
8715
|
+
*
|
|
8716
|
+
* Typed, named control groups. Define the group once (like a zod schema or a
|
|
8717
|
+
* tanstack route), then read/set actuators by name with inferred keys — no
|
|
8718
|
+
* positional arrays, no `as const`, no owner bookkeeping.
|
|
8719
|
+
*/
|
|
8262
8720
|
/**
|
|
8263
8721
|
* @license
|
|
8264
8722
|
* SPDX-License-Identifier: Apache-2.0
|
|
@@ -8331,6 +8789,15 @@ function useCameraAnimation() {
|
|
|
8331
8789
|
*
|
|
8332
8790
|
* React wrapper for capturing policy image payloads from Three/MuJoCo cameras.
|
|
8333
8791
|
*/
|
|
8792
|
+
/**
|
|
8793
|
+
* @license
|
|
8794
|
+
* SPDX-License-Identifier: Apache-2.0
|
|
8795
|
+
*
|
|
8796
|
+
* Capture policy observation tensors directly from Three/MuJoCo cameras,
|
|
8797
|
+
* skipping the data-URL/PNG round-trip. Sessions are created once per camera
|
|
8798
|
+
* and reused every step, so live inference and dataset recording read straight
|
|
8799
|
+
* from the GPU into Float32 tensors.
|
|
8800
|
+
*/
|
|
8334
8801
|
/**
|
|
8335
8802
|
* @license
|
|
8336
8803
|
* SPDX-License-Identifier: Apache-2.0
|
|
@@ -8379,6 +8846,6 @@ function useCameraAnimation() {
|
|
|
8379
8846
|
* useCameraAnimation — composable camera animation hook.
|
|
8380
8847
|
*/
|
|
8381
8848
|
|
|
8382
|
-
export { Body, ContactListener, ContactMarkers, Debug, DragInteraction, FlexRenderer, IkGizmo, InstancedGeomRenderer, MountedCameraFrameSequenceManifestStatus, MountedCameraFrameSequenceReadinessStatus, MountedCameraFrameSourceSuggestionMatch, MujocoCanvas, MujocoPhysics, MujocoProvider, MujocoSimProvider, SceneLights, SplatCollisionProxyPreview, TendonRenderer, TrajectoryPlayer, applyPolicyActionToControls, bodyPositionField, buildObservation, canFetchSplatCollisionProxyXml, captureFrame, captureFrameBlob, capturePolicyCameraFrames, capturePolicyCameraFramesFromMountedStreams, clampPolicyActionValue, createContiguousControlGroup, createController, createControllerHook, createMountedCameraFrameSequenceManifest, createMountedCameraFrameSequencePlan, createMountedCameraFrameSequencePlanFromApi, createMountedCameraFrameSequenceReadiness, createMountedCameraFrameSourceSuggestions, createNamedObservationBuilder, createPolicyCameraFrameCapturePlan, createPolicyCameraFrameCapturePlanFromApi, ctrlField, fetchSplatCollisionProxyXml, findActuatorByName, findBodyByName, findGeomByName, findJointByName, findKeyframeByName, findSensorByName, findSiteByName, findTendonByName, geomPositionField, getActuatedJoints, getCameraFrameCaptureSourceTarget, getControlMap, getMountedCameraFrameCaptureSource, getName, imagePointToNdc, isMountedCameraFrameCaptureSource, loadScene, parseSplatCollisionProxyGeoms, projectImagePointTo3D, qposField, qvelField, readNamedObservation, recordMountedCameraFrameSequence, resolveControlGroup, resolveMountedCameraFrameSource, sitePositionField, useActuators, useAfterPhysicsStep, useBeforePhysicsStep, useBodyMeshes, useBodyPose, useBodyState, useCameraAnimation, useCameraFrameCapture, useCameraSequenceRecorder, useContactEvents, useContactHistory, useContacts, useControlWriter, useCtrl, useCtrlNoise, useFrameCapture, useGamepad, useGeomPose, useGravityCompensation, useIkController, useJointState, useKeyboardIkTarget, useKeyboardTeleop, useMountedCameraSequenceRecorder, useMujoco, useMujocoWasm, useNamedObservation, useObservation, usePolicy, usePolicyCameraFrames, usePolicyCameraFramesFromMountedStreams, useRemotePolicy, useSceneLights, useSelectionHighlight, useSensor, useSensors, useSitePose, useSitePosition, useSplatCollisionProxyGeoms, useTrajectoryPlayer, useTrajectoryRecorder, useVideoRecorder };
|
|
8849
|
+
export { Body, CameraView, ContactListener, ContactMarkers, Debug, DragInteraction, FlexRenderer, GenericIK, IkGizmo, InstancedGeomRenderer, MountedCameraFrameSequenceManifestStatus, MountedCameraFrameSequenceReadinessStatus, MountedCameraFrameSourceSuggestionMatch, MujocoCanvas, MujocoPhysics, MujocoProvider, MujocoSimProvider, SceneLights, SplatCollisionProxyPreview, TendonRenderer, TrajectoryPlayer, applyPolicyActionToControls, bodyPositionField, buildObservation, canFetchSplatCollisionProxyXml, captureFrame, captureFrameBlob, capturePolicyCameraFrames, capturePolicyCameraFramesFromMountedStreams, clampPolicyActionValue, controlGroup, createContiguousControlGroup, createController, createControllerHook, createMountedCameraFrameSequenceManifest, createMountedCameraFrameSequencePlan, createMountedCameraFrameSequencePlanFromApi, createMountedCameraFrameSequenceReadiness, createMountedCameraFrameSourceSuggestions, createNamedObservationBuilder, createPolicyCameraFrameCapturePlan, createPolicyCameraFrameCapturePlanFromApi, ctrlField, fetchSplatCollisionProxyXml, findActuatorByName, findBodyByName, findGeomByName, findJointByName, findKeyframeByName, findSensorByName, findSiteByName, findTendonByName, geomPositionField, getActuatedJoints, getCameraFrameCaptureSourceTarget, getControlMap, getMountedCameraFrameCaptureSource, getName, imagePointToNdc, isMountedCameraFrameCaptureSource, loadScene, parseSplatCollisionProxyGeoms, projectImagePointTo3D, qposField, qvelField, readNamedObservation, recordMountedCameraFrameSequence, resolveControlGroup, resolveMountedCameraFrameSource, sitePositionField, useActuators, useAfterPhysicsStep, useBeforePhysicsStep, useBodyMeshes, useBodyPose, useBodyState, useCameraAnimation, useCameraFrameCapture, useCameraSequenceRecorder, useCameraStream, useCameraViewport, useContactEvents, useContactHistory, useContacts, useControlGroup, useControlWriter, useCtrl, useCtrlNoise, useFrameCapture, useGamepad, useGeomPose, useGravityCompensation, useIkController, useJointState, useKeyboardIkTarget, useKeyboardTeleop, useMountedCameraSequenceRecorder, useMujoco, useMujocoWasm, useNamedObservation, useObservation, usePolicy, usePolicyCameraFrames, usePolicyCameraFramesFromMountedStreams, usePolicyCameraTensors, usePolicyCameraTensorsFromMountedStreams, useRemotePolicy, useSceneLights, useSelectionHighlight, useSensor, useSensors, useSitePose, useSitePosition, useSplatCollisionProxyGeoms, useTrajectoryPlayer, useTrajectoryRecorder, useVideoRecorder };
|
|
8383
8850
|
//# sourceMappingURL=index.js.map
|
|
8384
8851
|
//# sourceMappingURL=index.js.map
|