Open jonlepage opened 1 year ago
It's working for me on Vite (4.3.1) but my setup is a little unconventional. Still may be helpful to Vite users but also people trying to use box2d-wasm in a worker.
My main app is Vite, but I'm building my workers with rollup and bundling them separately into IIFE format. In my worker code that wants to load box2d I have this:
import Box2DFactory from './Box2D.js'
Box2DFactory({
locateFile: (url, srcDirectory) => {
return `http://localhost:3000/box2d/${url}`
}
}).then(box2d => {
// you now have a box2d instance
})
I have created a public/ directory in my project root, which Vite will serve, then I created box2d folder with Box2D.wasm from box2d-wasm dist folder. I put Box2D.js in the same directory as my worker.
I was getting errors because the emscripten wrapper tries to access document
which doesn't exist in a worker. I am wrapping my worker code like this so I can inject dependencies and programmatically get the dependencies it returns, so I just added a way to inject a fake document object that emscripten can get the file path from:
let workerCode = `(function(__dependencies, __document) {
if (!self.isMainThread) {
globalThis.document = __document
}
let exportObject = ${actualWorkerCode} // string loaded from plain js source file
return exportObject
})`
// then when I load it I just fetch() the file and indirect eval it, passing in dependencies and the document polyfill:
const documentPolyfill = {
currentScript: {
get src() {
return `http://localhost:3000/box2d`
},
},
baseURI: 'http://localhost:3000/box2d'
}
const workerExports = eval?.(workerCode)(MyCustomModuleLoader.getProvider(), documentPolyfill)
It doesn't actually matter what you put for the URLs in your polyfill. It gets overridden by the locateFile
callback you provide, so as long as you set that up correctly it should work. Vite is serving the actual Box2D.wasm and it sends the correct headers automatically for me.
This polyfill shouldn't be necessary, but this code is causing it to be:
var _documentCurrentScript = typeof document !== 'undefined' ? document.currentScript : null;
var _scriptDir = (_documentCurrentScript && _documentCurrentScript.src || new URL('MyWorker.js', document.baseURI).href);
They check document undefined so it doesn't fail right away, but then later when it has no document script reference they just go ahead and try to access document.baseURI anyway, making it really hard to get this running in a worker. I'm not actually sure if this is emscripten, box2d-wasm or rollup causing it, but hope it helps someone!