[html5 (JS)] WASM Ammo.js + WebWorker
See original GitHub issueHi all, there is a way to speed up Armory3D when exporting to html5.
The speed up will come from the physic module. The physic module ammo.js can be used as a JS-compiled WASM module and sync physics info using a webWorker. The module then run in its own thread and the 3D objects properties are then updated using the webWorker. Meaning that for each frame there is no need to wait anymore for the physics to be calculated. (no slow FPS due to Physics) in theory : ! Examples : with only Javascript Ammo.js with WASM Ammo.js + WebWorker
-
To run the ammo.js module as a WASM module you need first to compile ammo.js to WASM. More info about compiling it yourself here : https://github.com/kripken/ammo.js/#building
Here is the compiled file : ammo.wasm.wasm
-
You first need to launch a webWorker using javascript that will load our module, something like :
var physicsWorker = null;
var nextPhysicsWorker = new Worker('worker.wasm.js');
if (physicsWorker) physicsWorker.terminate();
physicsWorker = nextPhysicsWorker;
nextPhysicsWorker = null;
if (!physicsWorker) physicsWorker = new Worker('worker.wasm.js');
-
Here is what a WebWorker will look like : worker.wasm.js We probably need to rewrite the “Bullet-interfacing code” for Armory.
-
Armory is loading the normal JS ammo.js inside the kha.js script by calling this function here : https://github.com/armory3d/armory/blob/58e4744aa10b197c34c5e929578fce4c76427003/Sources/armory/system/Starter.hx#L77
and it seems that Krom at line 80 is already using the WASM version of ammo.js - so we just need to rewrite this function for the html5 export.
- Finally : we need to sync 3D objects using the worker. We need to access and update all 3D objects with their transforms generated by the worker and get them update in the 3D canvas. The function will look like this :
physicsWorker.onmessage = function(event) {
var data = event.data;
if (data.objects.length != TotalNumberOfObjectsWithPhysics) return;
for (var i = 0; i < TotalNumberOfObjectsWithPhysics; i++) {
var physicsObject = data.objects[i];
renderObject.position[0] = physicsObject[0];
renderObject.position[1] = physicsObject[1];
renderObject.position[2] = physicsObject[2];
quaternion.x = physicsObject[3];
quaternion.y = physicsObject[4];
quaternion.z = physicsObject[5];
quaternion.w = physicsObject[6];
renderObject.rotation = quaternion.toEuler();
}
};
physicsWorker.postMessage(TotalNumberOfObjectsWithPhysics);
Also here is a 3D scene with cube and added physics that can be used as a benchmark. https://github.com/onelsonic/armory_tests/raw/master/mesh_generate.7z
Issue Analytics
- State:
- Created 3 years ago
- Reactions:5
- Comments:5 (4 by maintainers)
Top GitHub Comments
I’ve added add/remove cubes option to the
mesh_generate
example for benchmarking. https://disktree.net/app/armory_examples_browser/#examples-mesh_generateSource in pending pr: https://github.com/armory3d/armory_examples/pull/28/files#diff-9451dba57586c2efa810d775e2c692f5ce2bd887fb2cdc1596f16643fb4fe2c8
I see that Kha has an HTML5 backend with workers which might work for this : https://github.com/Kode/Kha/tree/master/Backends/HTML5-Worker/kha