dioxus icon indicating copy to clipboard operation
dioxus copied to clipboard

Creating and spawning WebWorkers

Open serzhiio opened this issue 2 years ago • 7 comments

Any ideas how to create, spawn and work with WebWorkers inside Dioxus? I am referring to this Using web workers

serzhiio avatar Sep 23 '23 18:09 serzhiio

(This was answered on the discord yesterday)

You can use gloo_worker

I want to transfer canvas created by Dioxus to worker, how could i do it?

You will need to use an offscreen canvas to communicate with the real canvas through the web worker. You can use the onmounted event to run some code when an element is mounted and from there use an unique id with use_eval or get the element through get_raw_element

ealmloff avatar Sep 24 '23 13:09 ealmloff

An example of web workers would be great to add to the cookbook! There isn't too much that is specific to Dioxus here, but it is a fairly common library. A link to the libraries documentation, and a simple example would be enough. We can show how to use a web worker with the use_coroutine hook to communicate with channels

ealmloff avatar Sep 24 '23 13:09 ealmloff

It would be nice to have special compilation stage for web-workers in dioxus-cli. And declare webworker like in Trunk:

index.html
--snip--
    <link data-trunk rel="rust" href="Cargo.toml" data-wasm-opt="z" data-bin="app" data-type="main" />
    <link data-trunk rel="rust" href="Cargo.toml" data-wasm-opt="z" data-bin="worker" data-type="worker" />
--snip--

serzhiio avatar Sep 29 '23 17:09 serzhiio

And is it possible to obtain web_sys::HtmlCanvasElement from .get_raw_element() result?

serzhiio avatar Sep 30 '23 14:09 serzhiio

And is it possible to obtain web_sys::HtmlCanvasElement from .get_raw_element() result?

let raw_el = e.get_raw_element().unwrap().downcast_ref::<web_sys::Element>().unwrap();
let canvas: HtmlCanvasElement = raw_el.clone().dyn_into().unwrap();
let offscreen = canvas.transfer_control_to_offscreen().unwrap();

looks like this is working as intended with wasm-bindgen dep

serzhiio avatar Sep 30 '23 14:09 serzhiio

There is an example implementation here, for dioxus: https://docs.rs/leptos_workers/latest/src/leptos_workers/plumbing/create_worker.rs.html#94

rambip avatar Aug 02 '24 06:08 rambip

The main difficulty is that the function you want to run in a web worker must be self-contained one way or another. That means that the source file where the function is defined must be compiled to a separate wasm module, and instantiated in the worker.

That adds a lot of complexity to the build steps, and that could even involve modifying the dioxus cli.

The other possibility is to load the webassembly module twice, once in the main thread and once in the web worker. That is what leptos_worker is doing if I understand correctly. That would involve knowing where the main wasm module is located at run time.

rambip avatar Aug 03 '24 05:08 rambip

After referring to wasm-bindgen document and the author's sample code. I manage to create a minimal code to get it working:

One thing to note is, that even if you manage to spawn the webworkers on the web, desktop and mobile might not build with wasm32 so it does not work over there. Nevertheless, this at least work on web

chunleng avatar Apr 26 '25 05:04 chunleng