I am currently teaching myself Rust + Bevy with the intent of shipping some proof-of-concept game following the ECS paradigm rendered using WebGPU. This is going fine and I am excited to learn the tech, but my bread-and-butter is JavaScript and I only desire targeting the web. At time of writing, Bevy's (WebGL) examples don't run on Android devices which is a bit concerning.
There is some compelling JS tooling out there for rendering - Babylon, AFrame, UseGPU, etc, but they all have their issues.
Babylon: not designed with ECS in mind, same as ThreeJS, declarative programming can be achieved through plugins, but it's fragile and significantly less performant than if built natively into the framework.
AFrame: powered by Three, but ECS-first and I assume it does a good job at it. Not practical for 2D rendering and really intends to be VR-first with a nod to non-VR 3d.
UseGPU: truly what I would like to be using as it's declarative by design, but it's so new that 2D Sprite is still on the TODO list. I'm not skillful enough in low-level graphics programming (yet!) to assist in the development.
I really want to be ready for this technological shift. I fully intend to build something as complex as RimWorld that runs in your browser. I'm taking baby steps, as quickly as I can, to get there, but am not sure what tools to be adopting to best prepare.
At the moment I'm betting on Bevy because it has a lot of wind behind its sails, its all-in on ECS, and I suspect avoiding GC for compute-heavy gaming will be beneficial. I don't know what interfacing to WebGPU via JS gets me aside from a potentially more rapid prototyping environment. I'd love to hear others' takes on this to ensure I don't burn months looking in the wrong direction.
In general WASM vs (well-written) JS shouldn't matter much for most scenarios, but there's one important drawback when using WebGPU via WASM: any buffer mapping operation needs to do an extra copy to get the data in and out of the WASM heap (e.g. there's currently no way to directly access (another) JS ArrayBuffer object from WASM). It's not a show stopper of course, but something to keep in mind when shuffling a lot of data between the CPU side and WebGPU.
PS: IMHO the biggest downside of using WebGPU natively is that it comes with a builtin shader compiler and/or cross-compiler to translate either WGSL or SPIRV to the shader dialects used by the various backend APIs. This adds a couple of complex dependencies and quite a bit of binary size (much more than "just" the WebGPU implementation). It would be nice if the native WebGPU implementations would allow to move all that shader compile/transpile stuff offline, and feed the WebGPU API with backend-specific shader blobs.
- better for compute heavy workloads which don’t need to interop with JS and JS-only APIs
- roughly the same or worse for mixed workloads with highly optimized interop
- worse for JS heavy workloads, no matter how much you optimize
Partly this is because interop has a steep cost that negates the perf benefits in such workloads. Mostly it’s because JS runtimes have very good performance characteristics, beating that is a big feat.
There are certainly performance focused mixed native/JS projects with great potential. Almost all of them are either very light on interop or very heavy on deep understanding of both the native language’s performance advantages and that of the JS runtime (which is often itself very runtime specific).
If you have a lucky workload that doesn’t need to cross interop boundaries much, the world is your oyster. If you have any other workload, you’re probably better off working with whatever you feel most comfortable to deliver and optimize for your use case.
I'm basically trying to build something that's like a colony sim meets idleRPG. You define a strategy once per day, submit it, and the colony sim chews on the instructions and plays forward. The user can just observe and devise a plan for adjusting their strategy the next day. I think this makes it an especially good candidate for WASM as I can simulate hundreds of semi-intelligent entities and don't ask for responsive user input.
I think there's also benefits with garbage collecting, right? I can avoid GC entirely with WASM but would inherently be subject to it with JS which then pushes me into a more imperative/mutable style of coding in an effort to preserve object lifetimes. I'd really rather stick to a declarative style if I can get away with the performance.
I've been working on a realtime softbody simulation in WebGPU for a while. After trying it in JS, C++ and Rust, wgpu is by far the best experience I got with WebGPU
ECS based game engine in Rust, wgpu rendering, and I've been really impressed with the code quality. I've been trying to find something to inspire me to really go all in with Rust, and I think I found it with Veloren
At first glance, this does look like it will be a great resource. Even just having high-quality examples of how to configure Cargo and etc. boilerplate will save me a lot of hours.
Doesn't look like they target WASM at all, though. I wonder what the main concerns were/are?
- Dwarf Fortress has existed since forever and neither DF nor RimWorld nor anything remotely similar seems to exist as browser-first software. Clearly it's not due to graphics limitations, but perhaps market economics?
- WebGPU isn't just about graphical performance. It's also about GPGPU. I was thinking some of the in-game algorithms would become more viable to run in this environment.
I'm learning a few pieces of tech at the same time, though. It might be the case that I find that avoiding GC with Rust/WASM and gaining memory locality perf benefits with ECS address the main limiting factors. I think I'm just a bit caught up in the hype of WebGPU coming out, too, and so am assuming it must be relevant to my solution. It might not be!
WebGL 2.0 is locked into OpenGL ES 3.0, when they rebooted work to finally catch up with OpenGL ES 3.1 set of APIs, and already existing protoytpe from Intel[0] for compute, Google dropped their support for WebGPU because anyone that cares should migrate to WebGPU instead [1]. Two years later still no WebGPU.
So WebGL 2.0 is stuck in what we could consider iPhone 5S 3D capabilities, with no known game that is capable of matching Infinity Blade 3 [2].
In similar vein when WebGPU finally comes out this year (they were targeting 2022), we will have an API designed as MVP 1.0, with the capabilities from Metal/DirectX 12/Vulkan when they were at version 1.0 in 2015, while asking everyone to rewrite their GLSL shaders into WGSL.
No wonder that with fast Internet connections, game studios are more interested into adopting pixel streaming technologies using latest 3D APIs than investing into pure Web technologies.
Usually the community talks are all about 3D models for ecommerce shops, tile rendering for online maps and the return of Flash like tooling.
Something like Nanite or mesh shaders on WebGPU? It will never happen.
[0] - https://registry.khronos.org/webgl/specs/latest/2.0-compute/ [1] - https://bugs.chromium.org/p/chromium/issues/detail?id=113199... [2] - https://www.polygon.com/2013/9/10/4715534/infinity-blade-3-c...
For WebGPU it was the right decision to select the base feature set for the biggest possible reach. Desktop-GPU extensions can still be added on top when the need arises.
For instance the WebGL2 compute extension was put on hold exactly because WebGPU solves this better and is "just around the corner".
"WebGPU was first published in mid-2021 (super new!), so it isn’t fully supported on browsers (also shows how you can enable it) yet".
My main goal is to bring this new technology into attention, I don't intend nor do I have any incentive to recommend people using it in production. Sorry if that wasn't completely clear.
Edit: I imagine it comes from here: https://www.w3.org/standards/history/webgpu - the first time a working draft was published on the w3c site, instead of only at the github repo, was then. But is it a meaningful date to mention?
https://groups.google.com/a/chromium.org/g/blink-dev/c/VomzP...
The euphemisms also are questionable.
> Everything seems to be moving to the web; I can see how many desktop-related headaches (like installing software) will become irrelevant over time
I've heard this since dial up days.
We GPU may be a natural progression sure. But it's not the game changer. (Bad pun)
There’s also a whole universe of Web based names (see facebook). In the VR niche I maintain https://moonrider.xyz/ that has had 100k MAUs sustained for 2+ years. Not sure if it qualifies as large scale but definitely non negligible.
I was hoping for a bit of discussion about the trade-offs that WebGPU had to accept to create an as-thin-as-possible wrapper around Vulkan, D3D12 and Metal, while at the same time catering to web developers and guaranteeing the safety requirements of the web.
I would also suggest https://web.dev/gpu-compute/ which is a good intro to WebGPU compute, but it was out of date and had broken APIs the last time I tried it. But it has useful theory if you've never used GPU compute before.
In Rust land a 0.x version number only really suggests that the library has an unstable API (expect breaking changes on version bumps). Plenty of very battle tested libraries that are being used in production at huge scale (like the `hyper` HTTP crate for example) still have 0.x versions.
I'm not an expert in graphics programming, but my understanding is that wgpu is solid and ready for production if it covers your use case, but there are still things it can't do yet. As long as you're willing to deal with breaking changes, I'd say go for it.
Ps Unzip is a summary/intro not an "in indepth article". I try to summarize concepts. But thanks to whoever posted, appreciated either way.
AMA
Which means that someone who wanted to write a graphics API and/or graphics API abstraction layer --
would do well to study WebGPU...
(in addition to other graphics APIs and graphics API abstraction layers...)