voxcity.importer.voxelize ========================= .. py:module:: voxcity.importer.voxelize .. autoapi-nested-parse:: Voxelize a mesh into a VoxCity voxel grid via column z-ray casting. The mesh is first mapped into voxel-index space (i, j, k) using the caller's placement ``transform`` (e.g. produced by ``build_placement_transform`` in ``transform.py``). Occupancy is then determined per (i, j) column by casting a single vertical ray through the column center and pairing up the ray's hit z-values under the even-odd rule: sorted hits -> (z0, z1), (z2, z3), ... fill voxel k in [floor(z0 + 0.5), floor(z1 + 0.5)) for each pair A non-watertight mesh can produce an odd number of hits for some column; in that case we fall back to filling the single span from the first to the last hit and log a warning, since this is the best approximation available for a degenerate/open mesh. Functions --------- .. autoapisummary:: voxcity.importer.voxelize.voxelize_mesh voxcity.importer.voxelize.voxelize_mesh_meshlib Module Contents --------------- .. py:function:: voxelize_mesh(mesh, transform, grid_shape) Voxelize *mesh* into occupied (i, j, k) voxel indices. :param mesh: a ``trimesh.Trimesh`` (or compatible) in original model coordinates. Not mutated. :param transform: 4x4 numpy affine mapping model coordinates -> voxel-index space (i, j, k), as produced by ``build_placement_transform``. :param grid_shape: ``(nx, ny, nz)`` voxel grid bounds used to clip results. :returns: ``(N, 3)`` numpy ``int64`` array of unique, sorted occupied (i, j, k) voxel indices. Empty ``(0, 3)`` array if there are no candidate columns or no ray hits anywhere. .. py:function:: voxelize_mesh_meshlib(mesh, transform, grid_shape) Voxelize *mesh* via the optional MeshLib SDF backend. .. warning:: **Untested / version-sensitive.** This function is a best-effort transcription of the MeshLib-based voxelization approach from the design plan. The ``meshlib`` package is NOT installed in the environment this was implemented and tested in, so the exact API calls below (``mr.meshFromFacesVerts``, ``mr.MeshToVolumeSettings``, ``vol.dims``, ``vol.data.get(...)``) could not be empirically verified against a real MeshLib distribution. MeshLib's Python API is known to vary across versions. A maintainer who adds ``meshlib`` as an actual dependency MUST verify/adapt these calls against the installed version before relying on this path, and should run ``tests/importer/test_voxelize_meshlib.py`` (which is automatically skipped via ``pytest.importorskip("meshlib")`` when the package is absent) to confirm parity with :func:`voxelize_mesh`. :param mesh: a ``trimesh.Trimesh`` (or compatible) in original model coordinates. Not mutated. :param transform: 4x4 numpy affine mapping model coordinates -> voxel-index space (i, j, k), as produced by ``build_placement_transform``. :param grid_shape: ``(nx, ny, nz)`` voxel grid bounds used to clip results. :returns: ``(N, 3)`` numpy ``int64`` array of unique, sorted occupied (i, j, k) voxel indices, matching the return contract of :func:`voxelize_mesh` exactly. Empty ``(0, 3)`` array if there are no occupied voxels.