Webgpu render for Manim - #4968
Conversation
Now, if OpenGL renderer is not used then OpenGL classes are also not loaded. For OpenGL rednerer, there is no change in logic. Just wanted to ensure clear separation from OpenGL code for other renderers.
Using ``typing.Protocol`` (rather than an ABC) means the existing ``CairoRenderer`` and ``OpenGLRenderer`` satisfy the interface automatically without any inheritance changes.
All Protocol methods of WebGPURender (as defined in manim/renderer/base_renderer.py) is defined. Camera (both 2D and 3D prospective) and Loop-Blinn fill anti-aliasing for Cubic Bezeir Curves are implemented. Phong Shader is implemented for rendering surfaces.
Concatenate all fill vertices into one buffer, all stroke vertices into another. Results in lower number of call to shader and faster execution.
The reference Slug implementation is available at https://github.com/EricLengyel/Slug authored by Eric Lengyel. A fill shader based on Slug algorithm is implemented in this commit.
Added initial differentiation between camera and lighting. Right now Camera only uses orthographic projection.
The behavior now matches with Cairo's.
Having separate fill and stroke shaders was complicating design regarding drawing order. Combining them for planar object has reduced the CPU computation also.
Cairo and OpenGL composite a static background image with only the moving_mobjects each frame. For scenes with many static elements this is a major perf win — only the animated subset is re-drawn.
Now, four different kind of light source exist: ambient, point, directional and spot. A scene can have only one ambient light but it can have multiple light sources of other kind. Right now, support for different light sources is wired for WebGPU renderer only.
Initial step towards material modeling of surface. Right three reflection
parameters are set:
diffuse_strength
Strength of the diffuse (Lambertian) lighting component, in [0, 1].
Defaults to 0.8.
specular_strength
Strength of the specular (Phong) highlight, in [0, ∞].
Defaults to 0.9.
specular_exponent
Phong shininess exponent — higher values produce a tighter, sharper
specular highlight; lower values produce a broad, soft one.
Defaults to 16.0.
We can implement MeshPhongMaterial (from three.js) like class in future if
needed.
for more information, see https://pre-commit.ci
There was a problem hiding this comment.
CodeQL found more than 20 potential problems in the proposed changes. Check the Files changed tab for more details.
|
Hi! This is very cool; thanks for your effort! I can look through the API and various decisions made here a bit closer later (I am particularly interested in how your approach compares to the recent 3b1b/manim migration to wgpu rendering) -- however, it is unfortunately a bit too early for introducing a new renderer. As you might have noticed, we just introduced #4916 as a first concrete step towards improving and disentangling the render flow; the next step is already up in form of #4966 (opinions are welcome!), and I've got more refactors like that coming over the next days. Once the render flow is cleaned up (including the introduction of a proper RendererProtocol) and the timeline is owned by the new Manager, then I'm excited to get this in. In the current state of the render flow, this would make the refactor more complicated though, and I can't have that, sorry. (I'm confident that the implementation then will actually be easier than what you had to do here, and I'll happily work with you to get this merged once we are there!) |
|
Can you made the import of the specific opengl backend dependencies lazy ? |
Overview: What does this pull request change?
This adds a new WebGPURenderer (manim/renderer/webgpu/), selectable via --renderer webgpu, built on top of wgpu-py. It is a from-scratch renderer implementation that reaches rough feature parity with the existing OpenGL renderer:
Motivation and Explanation: Why and how do your changes improve the library?
Manim currently ships two renderers, Cairo (CPU) and OpenGL, neither of which map well onto modern, cross-platform GPU APIs or the web/WASM target. WebGPU is the emerging cross-platform graphics/compute standard (native via wgpu-py, and eventually browsers), and adding a WebGPU backend lays the groundwork for faster rendering and future in-browser Manim playback, while reusing Manim's existing scene/mobject model through the new shared renderer interface.
The implementation intentionally avoids geometry shaders (unsupported in WebGPU) by using compute-shader/SDF-based techniques for stroke expansion and anti-aliasing instead of the geometry-shader-heavy path used by the classic OpenGL pipeline.
Further Information and Comments
This is an early-stage, experimental renderer (Phase 1–5 per the internal implementation plan: minimum viable VMobject rendering → full VMobject support → 3D/surfaces/textures → video output/preview window → feature parity with the OpenGL renderer). Feedback on API shape (especially base_renderer.py's shared interface) and on scope for an initial merge vs. further splitting into smaller PRs is very welcome.