How to obtain homography for metric measurements from an image

I have an image of a post-it with a line mark and I’d like to calculate the horionzal position of the line in real world units (cm). The size of the image is 3456 x 3456 px and the post-it dimension is 9 x 9 cm

Input image

I manually picked the 4 pixel coordinates of the post-it corners [[1769, 353], [3199, 835], [2683, 2145], [983,1409]] and then I tried to estimate the homography matrix using OpenCV getPerspectiveTransform(src, dst). This is the snippet:

import cv2 as cv
import numpy as np

src_bbox = [[0,0], [9, 0], [9, 9], [0, 9]] # [cm]
dst_bbox = [[1769, 353], [3199, 835], [2683, 2145], [983,1409]] # [px]

H = cv.getPerspectiveTransform(np.array(src_bbox).astype(np.float32),
                               np.array(dst_bbox).astype(np.float32))

H_inv = np.linalg.inv(H)

image = cv.imread("sheet.jpg")
if image is None:
    exit("Could not read the image.")

mod = cv.warpPerspective(image, H_inv, image.shape[:2])

cv.namedWindow("sheet", cv.WINDOW_NORMAL)
cv.resizeWindow("sheet", 400, 400)

cv.namedWindow("sheet_warped", cv.WINDOW_NORMAL)
cv.resizeWindow("sheet_warped", 400, 400)

cv.imshow("sheet", image)
cv.imshow("sheet_warped", mod)
cv.waitKey(0)
cv.destroyAllWindows()

This is the output:

Output images

The rectified image (right) is there but is so small that you cannot see it so I cannot use it to detect the line mark and obtain its position in cm.

Is it just a scaling issue due to the fact that the correspondence points are expressed in different units (px vs cm) and do not have similar magnitude or I am doing something wrong?
How should I select a scaling factor anyway?

  • You will have to specify your source box in pixels too. OpenCV doesn’t know you’re using cm, or what the size of a pixel is in cm. It just knows pixels.

    – 




  • You have to specify the pixels per cm. For example if you want 100 pixels per cm use coordinates 0 to 900 in your src points

    – 

  • @Micka Thanks a lot! So it is a scaling issue, how can I choose a scaling factor that is optimal in some sense? Are there any appropriate criteria?

    – 

  • if you just want to measure (in values) you dont need a scaling at all. You can transform from camera image to mm and from mm to camera image with floating point precision. For visualization (warping your image to some rectified image) it fully depends on your vosualization needs. Just scale it so that the final object in your image has the desired pixel size.

    – 

Leave a Comment