python OpenCV學習筆記(九):圖片的幾何變形
縮放
import numpy as np
import cv2 as cv
img = cv.imread('test.jpg')
res = cv.resize(img, None, fx=2, fy=2, interpolation=cv.INTER_CUBIC)
# OR
height, width = img.shape[:2]
res = cv.resize(img, (2*width, 2*height), interpolation=cv.INTER_CUBIC)
cv.resize(src, dsize[, dst[, fx[, fy[, interpolation]]]])
dsize:輸出圖片的大小,如果為None,
dsize = Size(round(fx*src.cols), round(fy*src.rwos))
fx:沿x軸的比例因子,當其等於0時,
fx = (double)dsize.width / src.cols
fy:沿y軸的比例因子,當其等於0時,
fy = (double)dsize.height / src.rows
dsize和fx、fy不能同時為0;當dsize和fx、fy都定義時,以dsize為準
interpolation:插值方式,預設為cv.INTER_LINEAR;詳見cv::InterpolationFlags
位移
import cv2 as cv
import numpy as np
img = cv.imread('opencv.jpg' , 0)
rows, cols = img.shape
M = np.float32([[1,0,100], [0,1,50]])
dst = cv.warpAffine(img, M, (cols+100, rows+50))
cv.imshow('img', dst)
cv.waitKey(0)
cv.destroyAllWindows()
cv.warpAffine(src, M, dsize[, dst[, flags[, borderMode[, borderValue]]]])
M:變換矩陣
dsize:輸出圖片的大小,格式為(width,height),width=cols,height=rows
位移變換矩陣為:
如果知道位移方向(x,y),就是(tx,ty),用np.float32()
,建立矩陣,然後傳入cv.warpAffine()
函式中。上例為x軸平移100,y軸平移50,(100,50)。
旋轉
img = cv.imread('test.jpg', 0)
rows, cols = img.shape
M = cv.getRotationMatrix2D((cols/2, rows/2), 90, 1)
dst = cv.warpAffine(img, M, (cols, rows))
旋轉矩陣為:
OpenCV也提供了縮放旋轉,通過調節旋轉點,你可以在任意你喜歡的位置旋轉,修改旋轉矩陣為下列矩陣:
其中
OpenCV提供了這個變換矩陣的方法:
cv.getRotationMatrix2D(center, angle, scale)
計算出一個二維旋轉的仿射矩陣
center:旋轉中心座標
angle:旋轉角度,正值意味著逆時針旋轉,座標原點為左上角
scale:縮放比例
仿射變換
在仿射變換中,原始影象中的所有平行線在輸出影象中仍然是平行的。為了找到變換矩陣,我們需要從輸入影象中得到三個點,以及它們在輸出影象中的對應位置。然後cv.getAffineTransform
將會建立一個2x3矩陣,它將被傳遞給cv.warpAffine
。
cv.getAffineTransform(src, dst)
cv.warpAffine(src, M, dsize[, dst[, flags[, borderMode[, borderValue]]]])
下面的示例,並檢視我選擇的點(以綠色表示):
import cv2 as cv
import numpy as np
from matplotlib import pyplot as plt
img = cv.imread('opencv.jpg')
rows, cols = img.shape[:2]
pts1 = np.float32([[50,50], [200,50], [50,200]])
pts2 = np.float32([[10,100], [200,50], [100,250]])
M = cv.getAffineTransform(pts1, pts2)
dst = cv.warpAffine(img, M, (cols, rows))
plt.subplot(121), plt.imshow(img), plt.title('Input')
plt.subplot(122), plt.imshow(dst), plt.title('Output')
plt.show()
視角轉換
視角轉換,需要一個3x3的矩陣。即使在轉換之後,直線仍然是直的。建立這個矩陣,你需要在輸入圖中找四個點,和輸出圖中對應的四個點。在這4個點中,有3個不應該是共線的。然後通過
cv.getPerspectiveTransform
建立矩陣,然後提供給cv.warpPerspective
cv.getPerspectiveTransform(src, dst)
cv.warpPerspective(src, M, dsize[, dst[, flags[, borderMode[, borderValue]]]])
示例:
import cv2 as cv
import numpy as np
from matplotlib import pyplot as plt
img = cv.imread('sudoku.png')
rows,cols,ch = img.shape
pts1 = np.float32([[56,65], [368,52], [28,387], [389,390]])
pts2 = np.float32([[0,0], [300,0], [0,300], [300,300]])
M = cv.getPerspectiveTransform(pts1, pts2)
dst = cv.warpPerspective(img, M, (300,300))
plt.subplot(121),plt.imshow(img),plt.title('Input')
plt.subplot(122),plt.imshow(dst),plt.title('Output')
plt.show()