I'm trying to perform basic affine transformation using pivot points.
import cv2
import numpy as np
import PIL
import matplotlib.pyplot as plt
img = cv2.imread('earth.png')
img_pivots = cv2.imread('earth_keys.png')
map_img = cv2.imread('earth2.png')
map_pivots = cv2.imread('earth2_keys.png')
pts_img_R = np.transpose(np.where(img_pivots[:, :, 2] > 0 ))
pts_img_G = np.transpose(np.where(img_pivots[:, :, 1] > 0 ))
pts_img_B = np.transpose(np.where(img_pivots[:, :, 0] > 0 ))
pts_img = np.vstack([pts_img_R, pts_img_G, pts_img_B])
pts_map_R = np.transpose(np.where(map_pivots[:, :, 2] > 0 ))
pts_map_G = np.transpose(np.where(map_pivots[:, :, 1] > 0 ))
pts_map_B = np.transpose(np.where(map_pivots[:, :, 0] > 0 ))
pts_map = np.vstack([pts_map_R, pts_map_G, pts_map_B])
M = cv2.estimateRigidTransform(pts_map.astype(np.float32), pts_img.astype(np.float32), True)
dst = cv2.warpAffine(map_img,M,(img.shape[1], img.shape[0]))
plt.subplot(121),plt.imshow(img),plt.title('earth.png')
plt.subplot(122),plt.imshow(dst),plt.title('earth2.png transrofmed')
plt.show()
On both images I made 3 points (R, G & B) and saved them in separate images ('earth_keys.png' for 'earth.png' and 'earth2_keys.png' for 'earth2.png'). All I want is to match pivot points on 'earth2.png' with pivot points on 'earth.png'.
Still, all I get after transformation is this
I'm assuming that I misplaced some arguments or something like this, but I tried all combinations and got all types of wrong results, but still can't spot it.
Example images (with pivots)
Edit: Changed pivots number to 6
Still wrong transformation
M is now equal to
array([[ 4.33809524e+00, 8.28571429e-01, -5.85633333e+02],
[ -6.22380952e+00, -1.69285714e+00, 1.03468333e+03]])
Example with 6 pivots
OpenCV provides a function cv2. warpAffine() that applies an affine transformation to an image. You just need to provide the transformation matrix (M). The basic syntax for the function is given below.
An affine transformation is a geometric transformation that preserves points, straight lines, and planes.
Rotation of an image for an angle \theta is achieved by the transformation matrix of the form. M = \begin{bmatrix} cos\theta & -sin\theta \\ sin\theta & cos\theta \end{bmatrix} But OpenCV provides scaled rotation with adjustable center of rotation so that you can rotate at any location you prefer.
How confident are you in your pivot points ?
If I plot them on your images, I obtain this:
Which gives, after manual superposition, something that looks like your result:
If I define points manually for 3 correspondences, I get this:
pts_img = np.vstack([[68,33], [22,84], [113,87]] )
pts_map = np.vstack([[115,101], [30,199], [143,198]])
It's still not perfect, but it may be closer to what you want to achieve.
To conclude, I'd recommend you to check how you compute your keypoints, and, in case of doubt, to do a manual superposition.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With