CV Flip Axis (3D)
One minus sign, and a mirrored point cloud
- points
- points
Two coordinate systems live side by side in this pack, and they disagree about which way is up. OpenCV's world is Y down, Z into the scene - that's what cameras, depth maps, solvers and every pose in the pack produce. glTF, Three.js, the Load 3D nodes and the point-cloud viewers want Y up, Z toward the viewer. This node negates one axis of an Nx3 point cloud so you can move between them.
It's a one-line numpy node in bmad4ever's ComfyUI CV (bmad4ever/comfyui_cv, a fork of Gerold Meisinger's opencv-comfyui), and it exists mostly because the alternative was counting minus signs by hand in a graph where a wrong sign is invisible.
The inputs
points - Nx3 or Nx1x3 float. That's your cloud: from CV Depth to 3D Points, CV Triangulate Points (Two-View), a stereo reprojection, CV Mesh From 3D Model.
axis - a three-way dropdown: Y (default), X, Z. It negates that coordinate for every point: p[:, i] *= -1.
Output is the same array, points. Yes, input and output share a name; nothing downstream cares.
Where you'll see it used: the stereo and point-cloud examples (exercise_stereo_pointcloud.json, exercise_stereo_multiview.json) and the PPF pose example, all cases where a cloud reconstructed in one convention gets viewed or matched in the other. The pack's own doc note describes the practical case as fixing mirrored stereo reconstructions.
The trap, stated plainly
Negating one axis is a reflection, not a rotation. The full conversion between OpenCV and glTF conventions is a 180° turn about X - it negates Y and Z. Flip only Y and you get a cloud that is the right size, in the right place, aligned with its own scene, and mirrored: an object facing away from you, a left-handed coordinate frame dressed up as a right-handed one. Every check you'd think to run passes.
The pack knows, because it shipped that bug for a day - one flip instead of two in an example workflow, showing the far side of a truck, with nothing in the pipeline complaining. So there's a node for the pair: CV Convert Axis Convention (3D) names the two spaces (from_space, to_space) and applies Y-and-Z together, keeping the normals of an Nx6 cloud turned alongside the points. Use that whenever what you mean is "convert between OpenCV and Three.js." Reach for CV Flip Axis (3D) when you genuinely want a single-axis mirror - fixing a flipped reconstruction, matching a rig, or building a specific convention deliberately.
Install
cd ComfyUI/custom_nodes
git clone https://github.com/bmad4ever/comfyui_cv
pip install "opencv-contrib-python-headless~=5.0.0.93"
Or find ComfyUI CV in ComfyUI Manager. Python ≥ 3.12 and a ComfyUI recent enough for the V3 node API; an older build fails at import rather than showing a broken node. Point-cloud workflows pull MilkTruck.glb and friends from the pack's example_inputs/ - run workflows/01_install_example_inputs.json once and reload the page before opening them, since 3D models are copied into ComfyUI/input/3d and Load 3D only lists what's there.
Common issues
It looked right until you rendered the far side. That's the mirror. Add the second flip, or switch to CV Convert Axis Convention (3D).
Normals point into the surface. An Nx3 cloud has no normals to flip, so a downstream normal-estimation step will compute them fresh - from the mirrored geometry, which can invert their sign. Use the Nx6-aware conversion node when normals are already attached, and prefer mesh-derived normals (CV Mesh Vertex Normals) over plane-fitting when the cloud came from a closed model.
Nothing visibly changed. You may have flipped an axis that's near-zero for that cloud, or the viewer normalises the cloud into its own frame anyway. Check the numbers with an inspect node rather than trusting the viewport.
Inputs (2)
| Name | Type | Default | Description |
|---|---|---|---|
| points | NPARRAY | Nx3 or Nx1x3 float array of 3-D positions. | |
| axis | COMBO | Which axis to negate. Y-up (Three.js) vs Y-down (OpenCV) is the most common need. |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| points | NPARRAY | Nx3 points with the selected axis negated. |