[feat] Add support for rotated coordinate systems and coordinate system SPZ extension#82
[feat] Add support for rotated coordinate systems and coordinate system SPZ extension#82raymondyfei wants to merge 38 commits intomainfrom
Conversation
* remove sh min-max scaling * move extensions to a separate folder * move emscripten extensions into a separate folder * move extended pack option handlers into separate file * add extension support notifier * move bindings also to the extensions folder * move extra pack options also to extensions * clean up emscripten bindings * fix tests * use CMAKE_CXX_STANDARD value if set * fix SH epsilons in tests * move quantization into core * add comments about quantization * clean up pack options binding --------- Co-authored-by: Raymond Fei <yfei@Raymonds-MacBook-Pro.local> Co-authored-by: angudavi <angudavi@adobe.com>
* modify the code according to comments * minor fix * refactor extensions * fix comments * fix tests
| - RDF: Standard PLY file format (right-handed, Y-down, Z-forward) | ||
| - RUB: Three.js coordinate system (right-handed, Y-up, Z-backward) | ||
| - LUF: glTF/GLB format (left-handed, Y-up, Z-forward) | ||
| - LUF: glTF/GLB format (right-handed, Y-up, Z-forward) |
There was a problem hiding this comment.
GLTF is right-handed, which is explicitly written in its doc: https://registry.khronos.org/glTF/specs/2.0/glTF-2.0.html#coordinate-system-and-units
Also it has L- vs. R- compared with Unity below, which is left-handed.
| .value("LUF", spz::CoordinateSystem::LUF, "Left Up Front - left-handed, Y-up, Z-forward (GLB format)") | ||
| .value("RUF", spz::CoordinateSystem::RUF, "Right Up Front - right-handed, Y-up, Z-forward (Unity)") | ||
| .value("LUF", spz::CoordinateSystem::LUF, "Left Up Front - right-handed, Y-up, Z-forward (GLB format)") | ||
| .value("RUF", spz::CoordinateSystem::RUF, "Right Up Front - left-handed, Y-up, Z-forward (Unity)") |
There was a problem hiding this comment.
To be consistent with the docstrings above, where Unity is left-handed, and GLTF/GLB is right-handed.
|
Congrats on the progress! This is a major cross-cutting change affecting both extension governance and coordinate handling across the ecosystem. As maintainer of neutral SPZ ecosystem tooling (spz_gatekeeper and spz2glb), I have two clarifying questions to align future compliance rules:
Thanks again for driving the SPZ ecosystem forward. |
The rotation logic and code itself are in the base implementation. We only put the tag about the orientation of the asset in the extension to record the asset's native orientation.
No, it's not mandatory. The rotated SH coefficients are baked into assets. That's the purpose of the rotation logic. A rotated asset has no difference from the original one in the sense of formatting, other than that the geometry (including the position, quaternion, SH coefficients) itself is rotated. We provide a native tool to rotate the asset in the base implementation. Only the orientation tag is in the extension. |
Thanks for the clear and detailed clarification! This will help us accurately align the compliance validation rules of spz_gatekeeper with the official SPZ specification. Looking forward to the final landing of this update. |
This PR adds support for rotated coordinate systems. In particular, we have:
Y-up / Z-up coordinate system conversion
SPZ previously only supported 8 Y-up coordinate systems (e.g. RUB for Three.js, RDF for PLY, LUF for glTF, RUF for Unity). This PR adds support for 8 Z-up coordinate systems (e.g. RBU, LFD) used by DCC tools such as Blender, 3ds Max, AutoCAD, Rhino, Unreal Engine, and other Adobe internal tools. Converting between Y-up and Z-up applies a 90-degree rotation about the X-axis: including correctly rotating spherical-harmonic coefficients via the Wigner D-matrices for bands l=1–4, in addition to any axis sign flips.
SPZ_ADOBE_coordinate_system extension (
0xADBE0003)A new SPZ extension that embeds the storage coordinate system in the file is added. When present,
packGaussiansconverts to the extension's coordinate system instead of the default RUB, andunpackGaussiansuses it as the source frame, enabling lossless round-trips without relying on the caller to track the storage orientation.All 16 coordinate systems are exposed with consistent ordering, correct handedness labels, and matching documentation across the C++, Python, and Emscripten APIs.
We also added more unit tests for this new feature. We have:
test_coordinate_system.py— enum values, PackOptions/UnpackOptions mutability, Y-up and Z-up convert_coordinates, SPZ/PLY round-trips with Y-up and Z-up from_coord/to_coordtest_spherical_harmonics.py— degree-1 SH flip under Y-up/Z-up conversion, orthogonality and 4-cycle tests for bands l=2–4Extension tests— SPZ_ADOBE_coordinate_system overrides pack/unpack destination, UNSPECIFIED extension falls back to RUB, Z-up storage round-tripsIn addition, we extend the CI coverage to the Emscripten build of this library, as well as to the SPZ extensions.