|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
import torch |
|
|
from .rotation import quat_to_mat, mat_to_quat |
|
|
|
|
|
|
|
|
def extri_intri_to_pose_encoding( |
|
|
extrinsics, |
|
|
intrinsics, |
|
|
image_size_hw=None, |
|
|
pose_encoding_type="absT_quaR_FoV", |
|
|
min_focal_length=0.1, |
|
|
max_focal_length=10, |
|
|
): |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if pose_encoding_type == "absT_quaR_FoV": |
|
|
R = extrinsics[:, :, :3, :3] |
|
|
T = extrinsics[:, :, :3, 3] |
|
|
|
|
|
quat = mat_to_quat(R) |
|
|
|
|
|
|
|
|
H, W = image_size_hw |
|
|
fov_h = 2 * torch.atan((H / 2) / intrinsics[..., 1, 1]) |
|
|
fov_w = 2 * torch.atan((W / 2) / intrinsics[..., 0, 0]) |
|
|
pose_encoding = torch.cat([T, quat, fov_h[..., None], fov_w[..., None]], dim=-1).float() |
|
|
else: |
|
|
raise NotImplementedError |
|
|
|
|
|
return pose_encoding |
|
|
|
|
|
|
|
|
def pose_encoding_to_extri_intri( |
|
|
pose_encoding, |
|
|
image_size_hw=None, |
|
|
min_focal_length=0.1, |
|
|
max_focal_length=10, |
|
|
pose_encoding_type="absT_quaR_FoV", |
|
|
build_intrinsics=True, |
|
|
): |
|
|
|
|
|
intrinsics = None |
|
|
|
|
|
if pose_encoding_type == "absT_quaR_FoV": |
|
|
T = pose_encoding[..., :3] |
|
|
quat = pose_encoding[..., 3:7] |
|
|
fov_h = pose_encoding[..., 7] |
|
|
fov_w = pose_encoding[..., 8] |
|
|
|
|
|
R = quat_to_mat(quat) |
|
|
extrinsics = torch.cat([R, T[..., None]], dim=-1) |
|
|
|
|
|
if build_intrinsics: |
|
|
H, W = image_size_hw |
|
|
fy = (H / 2.0) / torch.tan(fov_h / 2.0) |
|
|
fx = (W / 2.0) / torch.tan(fov_w / 2.0) |
|
|
intrinsics = torch.zeros(pose_encoding.shape[:2] + (3, 3), device=pose_encoding.device) |
|
|
intrinsics[..., 0, 0] = fx |
|
|
intrinsics[..., 1, 1] = fy |
|
|
intrinsics[..., 0, 2] = W / 2 |
|
|
intrinsics[..., 1, 2] = H / 2 |
|
|
intrinsics[..., 2, 2] = 1.0 |
|
|
else: |
|
|
raise NotImplementedError |
|
|
|
|
|
return extrinsics, intrinsics |
|
|
|