-
Notifications
You must be signed in to change notification settings - Fork 3.8k
Add native OpenCV lens-distortion cameras for OVRTX #6608
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: develop
Are you sure you want to change the base?
Changes from 3 commits
a5910d5
c1e2f95
c2499de
5600329
f65bb70
d1d7974
4234bfd
98bbb9c
2814b49
e46ea2b
f6b9305
419f789
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| Added | ||
| ^^^^^ | ||
|
|
||
| * Added :class:`~isaaclab.sim.spawners.sensors.OpenCvPinholeDistortionCfg` and | ||
| :class:`~isaaclab.sim.spawners.sensors.OpenCvFisheyeDistortionCfg` and a ``distortion`` field on | ||
| :class:`~isaaclab.sim.spawners.sensors.PinholeCameraCfg`, letting a camera carry an OpenCV | ||
| ``fx/fy/cx/cy`` + distortion-coefficient calibration. The model is authored on the camera prim as | ||
| the ``omni:lensdistortion:*`` USD API, which the RTX/OVRTX renderer honors natively. | ||
|
|
||
| Changed | ||
| ^^^^^^^ | ||
|
|
||
| * Changed :meth:`~isaaclab.sensors.camera.Camera._update_intrinsic_matrices` to read the authored | ||
| ``fx/fy/cx/cy`` when an OpenCV lens-distortion model is present, so | ||
| :attr:`~isaaclab.sensors.camera.Camera.data` intrinsics reflect a real calibration (non-square | ||
| pixels or an off-center principal point) instead of assuming ``fx == fy`` and a centered principal | ||
| point. |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -204,6 +204,8 @@ def __init__(self, cfg: CameraCfg): | |
|
|
||
| # UsdGeom Camera prim for the sensor | ||
| self._sensor_prims: list[UsdGeom.Camera] = list() | ||
| # Guard so the lens-distortion image-size mismatch warning is emitted at most once. | ||
| self._warned_distortion_image_size: bool = False | ||
| # Allocated in :meth:`_create_buffers` once the renderer's output contract is known. | ||
| self._data: CameraData | None = None | ||
| # Renderer and render data — assigned in _initialize_impl. | ||
|
|
@@ -651,18 +653,43 @@ def _update_intrinsic_matrices(self, env_ids: Sequence[int] | wp.array | None = | |
| for matrix_id, i in enumerate(env_ids_np): | ||
| # Get corresponding sensor prim | ||
| sensor_prim = self._sensor_prims[int(i)] | ||
| # get camera parameters | ||
| # currently rendering does not use aperture offsets or vertical aperture | ||
| focal_length = sensor_prim.GetFocalLengthAttr().Get() | ||
| horiz_aperture = sensor_prim.GetHorizontalApertureAttr().Get() | ||
|
|
||
| # get viewport parameters | ||
| height, width = self.image_shape | ||
| # extract intrinsic parameters | ||
| f_x = (width * focal_length) / horiz_aperture | ||
| f_y = f_x | ||
| c_x = width * 0.5 | ||
| c_y = height * 0.5 | ||
| # Prefer an authored OpenCV lens-distortion model when present: it carries the | ||
| # authoritative fx/fy/cx/cy that the RTX/OVRTX renderer projects through. These may be | ||
| # non-square (fx != fy) or off-center, unlike the focal-length/aperture readback which | ||
| # assumes square pixels and a centered principal point. | ||
| raw_prim = sensor_prim.GetPrim() | ||
| distortion_model = raw_prim.GetAttribute("omni:lensdistortion:model").Get() | ||
| if distortion_model: | ||
| prefix = f"omni:lensdistortion:{distortion_model}" | ||
| f_x = float(raw_prim.GetAttribute(f"{prefix}:fx").Get()) | ||
| f_y = float(raw_prim.GetAttribute(f"{prefix}:fy").Get()) | ||
| c_x = float(raw_prim.GetAttribute(f"{prefix}:cx").Get()) | ||
| c_y = float(raw_prim.GetAttribute(f"{prefix}:cy").Get()) | ||
| # the intrinsics are reported in the calibrated pixel space; warn once if the render | ||
| # resolution differs, since the reported matrix will not match the rendered pixels. | ||
| image_size = raw_prim.GetAttribute(f"{prefix}:imageSize").Get() | ||
| if image_size is not None and (int(image_size[0]), int(image_size[1])) != (width, height): | ||
| if not self._warned_distortion_image_size: | ||
| logger.warning( | ||
| "Camera lens-distortion 'imageSize' %s does not match the render resolution" | ||
| " (%d, %d). The reported intrinsic matrix is in the calibrated pixel space.", | ||
| (int(image_size[0]), int(image_size[1])), | ||
| width, | ||
| height, | ||
| ) | ||
| self._warned_distortion_image_size = True | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Note: If this suggestion doesn't match your team's coding style, reply to this and let me know. I'll remember it for next time! |
||
| else: | ||
| # get camera parameters | ||
| # currently rendering does not use aperture offsets or vertical aperture | ||
| focal_length = sensor_prim.GetFocalLengthAttr().Get() | ||
| horiz_aperture = sensor_prim.GetHorizontalApertureAttr().Get() | ||
| # extract intrinsic parameters | ||
| f_x = (width * focal_length) / horiz_aperture | ||
| f_y = f_x | ||
| c_x = width * 0.5 | ||
| c_y = height * 0.5 | ||
| # create intrinsic matrix for depth linear | ||
| intrinsic_matrices[matrix_id, 0, 0] = f_x | ||
| intrinsic_matrices[matrix_id, 0, 2] = c_x | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nonefrom missing distortion intrinsic attrsGetAttribute(...).Get()returnsNonewhen the attribute is not authored on the prim;float(None)then raisesTypeErroron every subsequent update step. TheimageSizeread two lines below is alreadyNone-checked, butfx/fy/cx/cyare not. A USD scene that carriesomni:lensdistortion:modelwithout the matching intrinsic attributes (e.g., a hand-authored prim or a third-party export that only writes the schema token) will crash the camera sensor continuously from the first update call.