@babylonjs/core
Version:
Getting started? Play directly with the Babylon.js API using our [playground](https://playground.babylonjs.com/). It also contains a lot of samples to learn how to use it.
123 lines • 5.19 kB
JavaScript
import { Observable } from "../Misc/observable.js";
import { WebXRInputSource } from "./webXRInputSource.js";
import { WebXRMotionControllerManager } from "./motionController/webXRMotionControllerManager.js";
/**
* XR input used to track XR inputs such as controllers/rays
*/
export class WebXRInput {
/**
* Initializes the WebXRInput
* @param xrSessionManager the xr session manager for this session
* @param xrCamera the WebXR camera for this session. Mainly used for teleportation
* @param _options = initialization options for this xr input
*/
constructor(
/**
* the xr session manager for this session
*/
xrSessionManager,
/**
* the WebXR camera for this session. Mainly used for teleportation
*/
xrCamera, _options = {}) {
this.xrSessionManager = xrSessionManager;
this.xrCamera = xrCamera;
this._options = _options;
/**
* XR controllers being tracked
*/
this.controllers = [];
/**
* Event when a controller has been connected/added
*/
this.onControllerAddedObservable = new Observable();
/**
* Event when a controller has been removed/disconnected
*/
this.onControllerRemovedObservable = new Observable();
this._onInputSourcesChange = (event) => {
this._addAndRemoveControllers(event.added, event.removed);
};
// Remove controllers when exiting XR
this._sessionEndedObserver = this.xrSessionManager.onXRSessionEnded.add(() => {
this._addAndRemoveControllers([], this.controllers.map((c) => {
return c.inputSource;
}));
});
this._sessionInitObserver = this.xrSessionManager.onXRSessionInit.add((session) => {
session.addEventListener("inputsourceschange", this._onInputSourcesChange);
});
this._frameObserver = this.xrSessionManager.onXRFrameObservable.add((frame) => {
// Update controller pose info
for (const controller of this.controllers) {
controller.updateFromXRFrame(frame, this.xrSessionManager.referenceSpace, this.xrCamera, this.xrSessionManager);
}
});
if (this._options.customControllersRepositoryURL) {
WebXRMotionControllerManager.BaseRepositoryUrl = this._options.customControllersRepositoryURL;
}
WebXRMotionControllerManager.UseOnlineRepository = !this._options.disableOnlineControllerRepository;
if (WebXRMotionControllerManager.UseOnlineRepository) {
// pre-load the profiles list to load the controllers quicker afterwards
try {
// eslint-disable-next-line github/no-then
WebXRMotionControllerManager.UpdateProfilesList().catch(() => {
WebXRMotionControllerManager.UseOnlineRepository = false;
});
}
catch (e) {
WebXRMotionControllerManager.UseOnlineRepository = false;
}
}
}
_addAndRemoveControllers(addInputs, removeInputs) {
// Add controllers if they don't already exist
const sources = this.controllers.map((c) => {
return c.inputSource;
});
for (const input of addInputs) {
if (sources.indexOf(input) === -1) {
const controller = new WebXRInputSource(this.xrSessionManager.scene, input, {
...(this._options.controllerOptions || {}),
forceControllerProfile: this._options.forceInputProfile,
doNotLoadControllerMesh: this._options.doNotLoadControllerMeshes,
disableMotionControllerAnimation: this._options.disableControllerAnimation,
});
this.controllers.push(controller);
this.onControllerAddedObservable.notifyObservers(controller);
}
}
// Remove and dispose of controllers to be disposed
const keepControllers = [];
const removedControllers = [];
for (const c of this.controllers) {
if (removeInputs.indexOf(c.inputSource) === -1) {
keepControllers.push(c);
}
else {
removedControllers.push(c);
}
}
this.controllers = keepControllers;
for (const c of removedControllers) {
this.onControllerRemovedObservable.notifyObservers(c);
c.dispose();
}
}
/**
* Disposes of the object
*/
dispose() {
for (const c of this.controllers) {
c.dispose();
}
this.xrSessionManager.onXRFrameObservable.remove(this._frameObserver);
this.xrSessionManager.onXRSessionInit.remove(this._sessionInitObserver);
this.xrSessionManager.onXRSessionEnded.remove(this._sessionEndedObserver);
this.onControllerAddedObservable.clear();
this.onControllerRemovedObservable.clear();
// clear the controller cache
WebXRMotionControllerManager.ClearControllerCache();
}
}
//# sourceMappingURL=webXRInput.js.map