Nodes/camera-comfyUI/ProjectAndClean
ComfyUI Node

ProjectAndClean

Cleaning a cloud by projecting it and eroding the mask

By Alexankharin·Created about a year ago·Updated about a month ago· 36
ProjectAndClean
  • pointcloud
  • matrix
  • cleaned_pointcloud
projection
fov90.00
width512
height512
modeerode
num_iterations1
kernel_size3

PointCloudCleaner removes isolated points by voxel density in cloud space. ProjectAndClean takes the other route: it projects the cloud through a 4×4 matrix into an image, looks at which pixels the cloud actually covers, erodes the coverage mask, and deletes the points that land in the eroded-away pixels. Different mechanism, complementary job.

The effect is that you can throw away points from a specific viewpoint's point of view. If you've got a cloud with stray points hanging in front of a surface (the classic speckle from depth estimates at object edges), projecting from a camera where those strays are visible and eroding the mask strips them cleanly. The cleaning happens in projection space, so it's viewpoint-aware in a way the voxel cleaner isn't - points that look like noise from one angle may be perfectly valid from another, and ProjectAndClean only kills the ones that don't survive the mask test for the matrix you gave it.

The inputs

  • pointcloud - N×7 tensor.
  • matrix - the MAT_4X4 camera transform you're projecting through. This is your viewpoint.
  • projection - PINHOLE / FISHEYE / EQUIRECTANGULAR, and fov for the view.
  • width / height - the projection resolution; higher = finer mask = more selective cleaning.
  • mode - erode (default) shrinks the mask and removes points at its boundary; open does an erode-then-dilate, which cleans small islands while keeping the overall coverage shape.
  • kernel_size - morphological kernel (odd, 1–99, default 3). Bigger kernel = more aggressive removal.
  • num_iterations - apply the whole pass repeatedly (default 1, max 10) to peel away more layers.

The output, cleaned_pointcloud, stays in the cloud's original frame - the projection is just the test, not a transformation you keep. Same N×7 format, fewer points.

How it works

Each iteration transforms the cloud by the matrix, z-buffer rasterizes it, builds a coverage mask, then morphological ops on that mask decide which pixels are "kept." Points whose pixels were cleaned away get removed from the cloud, and the loop repeats with the shrunken cloud if num_iterations is higher. Buffers are reused internally to keep peak memory down, which matters because the projection grid is width × height - an 8K test grid is a lot of floats.

Installing it

Part of camera-comfyUI. Manager → Custom Nodes Manager → camera-comfyUI → Install → restart, or:

cd ComfyUI/custom_nodes
git clone https://github.com/Alexankharin/camera-comfyUI.git
cd camera-comfyUI && python install.py

No optional dependencies.

Common issues

  • You removed geometry you wanted - the mask erodes real surfaces too, especially thin ones. Prefer open mode (it restores the original footprint) and small kernels before blaming the cloud.
  • Nothing seems to change - a cloud that already projects cleanly has nothing for the mask to erode. If your noise is inside the coverage (depth-surface bumps, not boundary strays), the voxel cleaner is the right tool instead.
  • Slow with a big cloud and high res - the per-iteration rasterize + morphology is real compute. Lower width/height or iterations.

Pick your viewpoint, sweep the floor.

CategoryCamera/PointCloud

Inputs (9)

NameTypeDefaultDescription
pointcloudTENSOR
matrixMAT_4X4
projectionCOMBO3 options: PINHOLE, FISHEYE, EQUIRECTANGULAR
fovFLOAT90.00
widthINT5121–16384
heightINT5121–16384
modeCOMBOerode2 options: erode, open
num_iterationsINT11–10
kernel_sizeINT31–99

Outputs (1)

NameTypeDescription
cleaned_pointcloudTENSOR