Introducing Pmetra: Parametric Modelling for Bevy with Truck CAD


3 min read

Introducing Pmetra: Parametric Modelling for Bevy with Truck CAD

A few weeks ago, I released "Pmetra" - a parametric modelling plugin for the Bevy Engine using the Truck CAD kernel.

Pmetra allows developers to generate 3D models parametrically using Truck's CAD APIs. In short, you define a set of parameters (e.g., side_length, array_count), connect them with CAD logic (generating BREP Shells), and Pmetra will generate the meshes for you in real-time! (Check out this ๐Ÿ‘‰ simple cube example)

Additionally, you can set up "sliders" that let you manipulate the model in a smooth and continuous way. These sliders simply adjust the underlying parameters. They allow developers to experiment and also provide this feature to their users, unlocking different workflows or mechanics.

Building this was quite a journey! It all began with my desire to ship games with 3D models on the web. I realised that downloading 3D assets during page load would be too much for a reasonably sized game. Introduced to procedural generation, I was inspired by games like "Tiny Glade" (for the smooth interactions) and more recently "Satisfactory" (which would be an ideal use case for this)! My obsession with building using pure code was longing for something like this. bevy_mesh_drawing was my first attempt at it. I finally found Truck and it was a holy grail. An open source CAD kernel?! This was it, time to build!

I started with a few goals in mind: smooth and continuous interactions, and automation with a few parameters. I began working on a proof of concept. The first version of "Parametric CAD Modelling", which I almost abandoned after a month of development, was synchronous, blocking, and slow, and it would never scale. From its ashes, rose a phoenix; an entirely rewritten, smooth, asynchronous, non-blocking version emerged: "Pmetra" that you see today!

The first proof-of-concept version of the plugin had the mesh generation written in a single function call at the top level. It would return the resulting shells, meshes and sliders. This setup was necessary to ensure predictability and synchronicity, allowing for smooth model manipulation and interactive sliders. Once it worked as expected, I decided to improve performance. I discovered that the biggest bottleneck was the tessellation (algorithm/module that converts BREP Shells/Solids to triangle meshes). Since this process was happening synchronously, I began exploring ways to make it run in the background.

But this was not as easy as I had thought. Some of my previous decisions, like using sliders, relied on meshes being generated beforehand in a predictable way. I decided to change the architecture so that sliders were generated purely based on the BREP shell and parameters, with no dependency on meshes. This allowed them to be generated in parallel and in the background using an Async Task Pool. This change boosted the overall FPS while manipulating meshes, leaving it unaffected at times! It was a key learning experience!

Now it all came down to my ability to demonstrate this. I created a few more examples, as you can see in the demo, and set up compiling to WASM for web deployment. A readme with a simple example to get started, along with more sophisticated ones in the demo, was all that was needed for the first release. It was ready to go! ๐Ÿš€

I finally open-sourced it after some initial testing and posted about it on Twitter. It turned out to be my most liked post ever! I received support from key players in the Bevy community and top folks in the 3D space, like mrdoob, the creator of ThreeJS!

A pet project has led people to me with ideas for building a CAD software/parametric engine! Big shoutout to Truck for becoming one of the underrated yet upcoming open-source CAD kernels!

I'm not an expert, and I'm sure mistakes have been made. I would love feedback and suggestions to improve this! Let's work together to make CAD accessible and building an even more exciting version of Satisfactory easier! ๐Ÿป

๐ŸŒ Pmetra live demo:
๐Ÿ‘‰ Github: