SECAD-Net Inference (Initial)
Voxels in, rough CAD mesh out (and a latent you must keep)
- model
- voxels
- mesh
- latent_code
- status
SECADNetInference is where the SECAD-Net pipeline earns its name: it takes a 64³ voxel grid and reconstructs a CAD-style mesh from it. The README calls it the "Initial" pass, and that word matters - the mesh it hands you is the starting point, not the final product. The node even labels the fine-tune step "(Required!)". Treat this as the encoder half of the workflow.
How it works
The pipeline is straight out of the SECAD-Net paper, and the code follows it four steps deep:
- The encoder compresses the 64³ voxels into a 256-dim latent code.
- The decoder turns that latent into primitive parameters - quaternions, translations, and heights for up to four sketch-extrude primitives.
- The generator (a "neural sketch head") evaluates the occupancy field at every point of a
grid_resolution³ query grid. It walks the grid in chunks of 100,000 points to keep VRAM sane, then applies a sigmoid with sharpness 150 to get hard-ish occupancy values. - Marching cubes (PyMCubes) extracts a surface at
threshold, and the vertices are scaled back into the (-0.5, 0.5) unit cube.
So the resolution knobs don't touch the input at all - your voxel grid is always 64³, and grid_resolution only controls how finely the output occupancy field is sampled.
Inputs and outputs
model(SECADNET_MODEL) - fromLoadSECADNetModel.voxels(VOXEL_GRID) - fromMeshToVoxel, which fills the interior so the network sees solid shapes, not hollow shells.grid_resolution(default 128, 64–256) - output mesh detail. 128 is a good middle ground; 256 gets you more surface but noticeably slower occupancy evaluation.threshold(default 0.5) - the marching cubes surface level. Leave it unless your mesh comes out blobby or holey; slightly lower values recover thin features.
Outputs are the important part:
mesh(TRIMESH) - wire this into a mesh preview/export node. This pack ships no viewer, so you need a TRIMESH consumer (the example workflow uses CADabra's GeomPack preview nodes).latent_code(SECADNET_LATENT) - keep this. It's the 256-dim code plus primitive params, andSECADNetFinetuneneeds it. Forgetting to wire it through is the classic newbie mistake.status(STRING) - a text summary of the vertex/face counts.
Gotchas
If you get a hard error mentioning PyMCubes, it's not installed - the requirements file lists it, but if you installed the pack before that landed, run pip install PyMCubes. The bigger conceptual trap: don't judge the workflow by this node's output alone. SECAD-Net's whole trick is that the encoder gives a decent initialization and per-shape fine-tuning makes it good. Feed this mesh into a preview, see something rough, and you might think it's broken. It isn't - that's the design. Run it through SECADNetFinetune and then SECADNetLatentToMesh, and judge then.
Inputs (4)
| Name | Type | Default | Description |
|---|---|---|---|
| model | SECADNET_MODEL | — | |
| voxels | VOXEL_GRID | — | |
| grid_resolutionopt | INT | 12864–256 | Output mesh sampling resolution. Higher = more detailed mesh but slower. This is independent of input voxel resolution (always 64³). Queries the occupancy field at N³ points before marching cubes. |
| thresholdopt | FLOAT | 0.500.1–0.9 | Marching cubes threshold for surface extraction. |
Outputs (3)
| Name | Type | Description |
|---|---|---|
| mesh | TRIMESH | — |
| latent_code | SECADNET_LATENT | — |
| status | STRING | — |