joinedPhysicsEngineComponent.js 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. import { Logger } from "../Misc/logger.js";
  2. import { Observable } from "../Misc/observable.js";
  3. import { SceneComponentConstants } from "../sceneComponent.js";
  4. import { Scene } from "../scene.js";
  5. import { PhysicsEngine as PhysicsEngineV1 } from "./v1/physicsEngine.js";
  6. import { PhysicsEngine as PhysicsEngineV2 } from "./v2/physicsEngine.js";
  7. /**
  8. * Gets the current physics engine
  9. * @returns a IPhysicsEngine or null if none attached
  10. */
  11. Scene.prototype.getPhysicsEngine = function () {
  12. return this._physicsEngine;
  13. };
  14. /**
  15. * Enables physics to the current scene
  16. * @param gravity defines the scene's gravity for the physics engine
  17. * @param plugin defines the physics engine to be used. defaults to CannonJS.
  18. * @returns a boolean indicating if the physics engine was initialized
  19. */
  20. Scene.prototype.enablePhysics = function (gravity = null, plugin) {
  21. if (this._physicsEngine) {
  22. return true;
  23. }
  24. // Register the component to the scene
  25. let component = this._getComponent(SceneComponentConstants.NAME_PHYSICSENGINE);
  26. if (!component) {
  27. component = new PhysicsEngineSceneComponent(this);
  28. this._addComponent(component);
  29. }
  30. try {
  31. if (!plugin || plugin?.getPluginVersion() === 1) {
  32. this._physicsEngine = new PhysicsEngineV1(gravity, plugin);
  33. }
  34. else if (plugin?.getPluginVersion() === 2) {
  35. this._physicsEngine = new PhysicsEngineV2(gravity, plugin);
  36. }
  37. else {
  38. throw new Error("Unsupported Physics plugin version.");
  39. }
  40. this._physicsTimeAccumulator = 0;
  41. return true;
  42. }
  43. catch (e) {
  44. Logger.Error(e.message);
  45. return false;
  46. }
  47. };
  48. /**
  49. * Disables and disposes the physics engine associated with the scene
  50. */
  51. Scene.prototype.disablePhysicsEngine = function () {
  52. if (!this._physicsEngine) {
  53. return;
  54. }
  55. this._physicsEngine.dispose();
  56. this._physicsEngine = null;
  57. };
  58. /**
  59. * Gets a boolean indicating if there is an active physics engine
  60. * @returns a boolean indicating if there is an active physics engine
  61. */
  62. Scene.prototype.isPhysicsEnabled = function () {
  63. return this._physicsEngine !== undefined;
  64. };
  65. /**
  66. * Deletes a physics compound impostor
  67. * @param compound defines the compound to delete
  68. */
  69. Scene.prototype.deleteCompoundImpostor = function (compound) {
  70. const mesh = compound.parts[0].mesh;
  71. if (mesh.physicsImpostor) {
  72. mesh.physicsImpostor.dispose( /*true*/);
  73. mesh.physicsImpostor = null;
  74. }
  75. };
  76. /**
  77. * @internal
  78. */
  79. Scene.prototype._advancePhysicsEngineStep = function (step) {
  80. if (this._physicsEngine) {
  81. const subTime = this._physicsEngine.getSubTimeStep();
  82. if (subTime > 0) {
  83. this._physicsTimeAccumulator += step;
  84. while (this._physicsTimeAccumulator > subTime) {
  85. this.onBeforePhysicsObservable.notifyObservers(this);
  86. this._physicsEngine._step(subTime / 1000);
  87. this.onAfterPhysicsObservable.notifyObservers(this);
  88. this._physicsTimeAccumulator -= subTime;
  89. }
  90. }
  91. else {
  92. this.onBeforePhysicsObservable.notifyObservers(this);
  93. this._physicsEngine._step(step / 1000);
  94. this.onAfterPhysicsObservable.notifyObservers(this);
  95. }
  96. }
  97. };
  98. /**
  99. * Defines the physics engine scene component responsible to manage a physics engine
  100. */
  101. export class PhysicsEngineSceneComponent {
  102. /**
  103. * Creates a new instance of the component for the given scene
  104. * @param scene Defines the scene to register the component in
  105. */
  106. constructor(scene) {
  107. /**
  108. * The component name helpful to identify the component in the list of scene components.
  109. */
  110. this.name = SceneComponentConstants.NAME_PHYSICSENGINE;
  111. this.scene = scene;
  112. this.scene.onBeforePhysicsObservable = new Observable();
  113. this.scene.onAfterPhysicsObservable = new Observable();
  114. // Replace the function used to get the deterministic frame time
  115. this.scene.getDeterministicFrameTime = () => {
  116. if (this.scene._physicsEngine) {
  117. return this.scene._physicsEngine.getTimeStep() * 1000;
  118. }
  119. return 1000.0 / 60.0;
  120. };
  121. }
  122. /**
  123. * Registers the component in a given scene
  124. */
  125. register() { }
  126. /**
  127. * Rebuilds the elements related to this component in case of
  128. * context lost for instance.
  129. */
  130. rebuild() {
  131. // Nothing to do for this component
  132. }
  133. /**
  134. * Disposes the component and the associated resources
  135. */
  136. dispose() {
  137. this.scene.onBeforePhysicsObservable.clear();
  138. this.scene.onAfterPhysicsObservable.clear();
  139. if (this.scene._physicsEngine) {
  140. this.scene.disablePhysicsEngine();
  141. }
  142. }
  143. }
  144. //# sourceMappingURL=joinedPhysicsEngineComponent.js.map