Knowhow/Vision 44

Open3d를 이용한 디버깅용 camera, bbox, origin visualization

데이터를 다루다 보면 주어진 3D point와 camera pose가 좌표계가 잘 맞춰져 있는지, coordinate origin을 어디인지, 방향은 맞는지 확인하는 것이 생각보다 귀찮고 까다롭다. 수십, 수백개나 되는 xyz 값이나 se3 값을 봐서는 알 방법이 없기 때문에 보통 시각화해서 보는데, colmap 외 사용 가능한 툴들도 제한적이고 매번 포맷을 맞추는 것도 귀찮다. 나 같은 경우, 간단히 open3d를 이용해 시각화하는 식으로 해결해왔는데 매번 반복적으로 코드를 구현하는 것이 귀찮아서 여기에 내가 주로 사용하는 디버깅용 코드를 기록해두려고 한다. Helper function들 def Rt2T(R, t): T = np.eye(4) T[:3, :3] = R T[:3, -1] = t.reshap..

Knowhow/Vision 2023.12.06

Sphere 상에서 normal vector uniform sampling

sphere상에서 normal vector를 뽑는 방법이 가장 간단하게는 위, 경도 상에서 uniform sampling해서 환산하는 방법일 것이다. 하지만 이 방법은 생각해보면 Equi-rectangular projection된 이미지 상에서 뽑아내는 것과 같은 효과이기 때문에 3D 공간 측면에서 생각해보면 극점 (north pole, south pole)에서 뽑히는 샘플이 많고 적도(equator)에서 뽑히느 샘플은 적으므로 충분히 고르다고 할 수 없다. 그러면 3D 공간 상에서 고르게 normal vector를 뽑으려면 어떻게 해야하는가? 머리를 굴려보면 대충 계산할 순 있겠다만 간단한 방식이 있다. sphere에서 고르게 normal vector를 뽑아내는 수식은 정의된 바가 있다. patchma..

Knowhow/Vision 2023.11.07

이미지 회전에 맞추어 intrinsic/extrinsic calibration 값 회전시키기

실제 카메라를 설치할 때 공간적 제약 혹은 화각의 문제로 카메라를 돌려서 설치하는 경우가 있다. 시계 방향으로 90도 혹은 반시계 방향으로 90도가 가장 흔한 경우인데 이 때 이미지는 또 똑바로 보고 싶을 때도 많다. 이미지만 사용할 경우에야 간단히 cv2.rotate를 쓰든 numpy를 쓰든 돌리면 끝이지만 만약 카메라 캘리브레이션 값도 같이 써야할 경우는 귀찮은 일이 많이 생긴다. 90도 돌린 경우에 intrinsic parameter는 focal length, fx, fy를 서로 스위칭해주어야 하고 principal point는 회전 방향에 따라 값을 재계산해주어야 한다. 또한 extrinsinc parameter 역시 yaw rotation을 가해주어야 한다. 계산하는 것이 어렵지는 않다만 귀찮고..

Knowhow/Vision 2023.08.17

Torch를 이용한 matrix inverse(+속도를 빠르게 만들 수 있는 경우)

matrix inverse를 하고자 할 때 numpy든 torch든 간단하게 linalg.inv 함수를 사용하면 끝나니 크게 생각해본 적 없겠지만 matrix inverse는 연산량이 굉장히 큰 operation이다. 간단히만 봐도 O(n^3)이므로 matrix 사이즈가 커질수록 폭발적으로 연산량이 증가한다. 대략 2000 x 2000 보다 큰 크기의 matrix를 다루기 시작하면 영겁의 시간이 걸린다. 이 글에서는 matrix inverse 방식 별 소요 시간을 대충 비교해보고, matrix 크기가 클 때 조금이라도 inverse operation에 들어가는 시간을 줄일 수 있는 노하우를 공유한다. (설명 전에 미리 말하면, 모든 matrix가 가능한 것은 아니다.) 1. Gauss-Jordan eli..

Knowhow/Vision 2023.05.18

Epipolar line visualization

여러 카메라 간 상대 자세가 정확한지 판별하는 방법 중 하나로 Epipolar line을 확인하는 방법이 있다. 카메라 자세들이 정확하다면 한 카메라 이미지에서 특징점 하나를 찍었을 때 다른 카메라 이미지에서 그려지는 epipolar line은 같은 특징점을 지나가야 한다. 예를 들어 카메라 0번과 1번를 고려할 때, 카메라 0번 이미지에서 서랍 모서리를 찍었다면 카메라 1번 이미지에 그려지는 epipolar line은 같은 서랍 모서리 위를 지나가야 한다. 이 방법은 카메라 자세 정확성을 평가할 GT가 없을 때 정성적으로 평가할 수 있는 방법 중 가장 직관적이고 정확하다. 이 글에서는 위와 같은 목적으로 epipolar line을 그려보고 싶을 때 활용할 수 있는 Visualizer 코드를 기록해두고자..

Knowhow/Vision 2023.03.24

Open3d manual registration (손으로 point cloud 정합하기)

Point cloud 여러개를 ICP를 이용해 registration(정합)하는 일은 생각보다 빈번하게 발생하는데, 이 때 초기 transformation을 제대로 정해주지 않으면 정합이 이상하게 된다. 특히 정합 대상인 두 point cloud가 noise point를 많이 갖고 있을수록 초기화가 어렵고 정합 성능도 떨어진다. 이럴 때 정합 성능을 높일 방법으로 RANSAC 같이 trial-and-error 접근을 할수도 있지만 경험적으로 보았을 때는 수가 많지 않다면 그냥 손으로 기준점을 잡아주는 것이 최고였다. 다른 말로, 사람이 직접 손으로 correspondence 몇 개를 잡아주고 이를 바탕으로 초기 transformation을 계산하여 사용하는 것이다. http://www.open3d.org..

Knowhow/Vision 2023.03.20

Open3d RGB/Depth image rendering 2

2022.07.01 - [Knowhow] - Open3d RGB/Depth image rendering 에서 기록한 코드와 크게 다른 것은 없으나 intrinsic, camera pose를 미리 알고 있을 때가 아니라, 그저 Open3d visualizer 상에서 손(drag)으로 돌려가며 구도를 잡은 뒤 해당 구도로 이미지를 rendering하고 싶을 때가 많길래 추가 정리한다. 다시 말하면, 구체적인 카메라 파라미터는 필요없고 대충 open3d GUI에서 손으로 구도 잡은 뒤, 그 구도의 RGB/Depth를 얻을 때 자주 썼다. 먼저 이 코드는 준비물이 필요한데, 일단 o3d.visualization.draw_geometries()를 이용해 먼저 visualizer를 켠다. 그리고 원하는 구도로 마우..

Knowhow/Vision 2023.03.20

Stereo image rectification

Stereo camera setting을 다룰 때 기본이 되는 것은 이미지의 rectification이다. 같은 기종의 카메라를 쓰더라도 intrinsic parameter가 조금씩 다르고, 정확히 조립해도 extrinsic parameter (특히 rotation)가 다르기 때문에 필수적으로 해야한다. 단순해보이지만 homography와 3d translation을 고려해야 하고 이미지 warping이 포함되기 때문에 직접 구현하는데는 번거로움이 많아 OpenCV의 함수를 활용하는 것이 일반적이다. OpenCV document를 보면 그만이라고 할 수 있지만 따로 적어 기록해두는 이유는 rectification된 이미지를 얻기까지 3개의 함수를 조합해야 하는데 매번 3개의 document를 보는 것이 ..

Knowhow/Vision 2023.03.16

Axis angle(Rodrigues notation) to Rotation matrix

Rotation을 표기하는 기법 중 axis-angle, quaternion, matrix 등 여러 형태가 존재하는데 여기서 axis-angle 표현법에서 Rotation matrix로 변환하는 코드다. scipy.spatial.transform 내 Rotation를 이용해 Rotation.from_rotvec(axis_angle_xyz).as_matrix()를 써도 되지만 간혹 축 2개만 쓰거나 하는 경우도 있어 내부 계산 순서를 기억해둘 겸 함수로 만들어 두었다. axis-angle은 x, y, z 순서로 적혀있지만 이를 rotation matrix로 조합할 때는 z y x 순서로 조합해야 한다. 행렬 연산 순서를 생각하면 같은 순서라고 할 수도 있다. (Rodrigues formula 참고) def..

Knowhow/Vision 2023.03.15

Disparity generation

자주 쓰진 않겠지만 depth로부터 disparity 데이터를 만들어두는 방법을 정리해두면 좋을 것 같아 이 글을 적게 되었다. 매번 수식 까먹고 검색하는게 귀찮다. 시뮬레이션 데이터든, realsense로 직접 취득한 데이터든 stereo setting에서 이미지와 depth를 얻는 것은 쉽지만 disparity를 얻는 것은 까다롭다. 단순히 focal length와 baseline 길이를 이용해 변환하는 것으로 끝맺을 수 있지만 left disparity와 right disparity를 맞추는 작업을 안하면 left-to-right, right-to-left warping 시 안 맞을 수 있다. 따라서 cross check를 꼭 해줘야 한다. def convert(depth, f, b): disp =..

Knowhow/Vision 2023.03.08