先跑一下示例代码:
平移:
import cv2 as cv
import numpy as np
from matplotlib import pyplot as plt
img = cv.imread('66.png')
imgInfo = img.shape
height = imgInfo[0]
width = imgInfo[1]
mode = imgInfo[2]
dst = np.zeros(imgInfo, np.uint8)
for i in range( height ):
for j in range( width - 100 ):
dst[i, j + 0] = img[i, j]
cv.imshow('image', dst)
cv.waitKey(0)
其中 dst[i, j + 0] = img[i, j]是控制平移的距离的,可以看到上面的右边黑色的一块是平移的效果,如果写成dst[i,j+100] = img[i,j]则效果为:
import cv2 as cv
import numpy as np
img=cv.imread('me1.jpg')
# 下面的 None 本应该是输出图像的尺寸,但是因为后边我们设置了缩放因子
# 因此这里为 None
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,1*height),interpolation=cv.INTER_CUBIC)
while(1):
cv.imshow('res',res)
cv.imshow('img',img)
if cv.waitKey(1) & 0xFF == 27:
break
cv.destroyAllWindows()
自己修改了一下width和height前面的系数,运行结果:
效果大概就是图片明显被拉长了。然后这个系数只能是整数,感觉有点不实用
示例代码是:
img = cv.imread('messi5.jpg',0)
rows,cols = img.shape
# cols-1 and rows-1 are the coordinate limits.
M = cv.getRotationMatrix2D(((cols-1)/2.0,(rows-1)/2.0),90,1)
dst = cv.warpAffine(img,M,(cols,rows))
我运行了以后显示:
查了一下大概是shape有三个返回值,然后我修改了其中一句话,加上了显示的代码,代码改为:
rols,cols,color = img.shape
M = cv.getRotationMatrix2D(((cols-1)/2.0,(rows-1)/2.0),90,1)
dst = cv.warpAffine(img,M,(cols,rows))
cv.imshow("ye",dst)
cv.waitKey()
介绍:
仿射变换是指在向量空间中进行一次线性变换(乘以一个矩阵)并加上一个平移(加上一个向量),变换为另一个向量空间的过程。在有限维的情况下,每个仿射变换可以由一个矩阵A和一个向量b给出,它可以写作A和一个附加的列b。**一个仿射变换对应于一个矩阵和一个向量的乘法,而仿射变换的复合对应于普通的矩阵乘法,**只要加入一个额外的行到矩阵的底下,这一行全部是0除了最右边是一个1,而列向量的底下要加上一个1.
我们能够用仿射变换来表示:
旋转 (线性变换)
平移 (向量加)
缩放操作 (线性变换)
示例代码:
import cv2 as cv
import numpy as np
from matplotlib import pyplot as plt
img = cv.imread('1.jpg')
rows,cols,ch = img.shape
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()
然后记录一下其中出现的函数和库:
1.Matplotlib 是 Python 的绘图库。 它可与 NumPy 一起使用,提供了一种有效的 MatLab 开源替代方案.
2.getAffineTransform函数
函数作用:
主要用于生成仿射变换矩阵
一个任意的仿射变换都能表示为 乘以一个矩阵 (线性变换) 接着再 加上一个向量 (平移).
3.warpAffine函数使用如下矩阵进行图像转换
4.个人觉得np.float32就是生成一个矩阵,用pts1保存
5.subplot(nrows,ncols,plot_number) 如subplot(2,3,4)可以写成sublot(234)
透视变换:
代码:
import cv2 as cv
import numpy as np
from matplotlib import pyplot as plt
img = cv.imread('1.jpg')
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()
img = cv2.imread("p7.jpg",cv2.IMREAD_UNCHANGED)
rows,cols = img.shape[:2]
msx = np.ones((rows,cols),np.float32)*200
msy = np.ones((rows,cols),np.float32)*100
dst = cv2.remap(img,msx,msy,cv2.INTER_LINEAR)
cv2.imshow("i",img)
cv2.imshow("d",dst)
mapx:用来指定列的参数均为200
mapy:用来指定行的参数均为100
在函数 cv2.remap()中,参数map1和参数map2用来说明反向映射,map1针对的是坐标x,map2针对的是坐标y。
参数map1指代的是像素点所在位置的列号,参数map2指代的是像素点所在位置的行号。
代码:
img = np.random.randint(0,256,size=[4,5],dtype=np.uint8)
i1 = np.zeros(img.shape,np.float32) #x坐标轴的值保持不变
i2 = np.zeros(img.shape,np.float32) # y坐标轴为总行号-1-当前行号
rows,cols = img.shape
for i in range(rows):
for j in range(cols):
i1.itemset((i,j),j)
i2.itemset((i,j),rows - i -1)
RST = cv2.remap(img,i1,i2,cv2.INTER_LINEAR)
print(RST)
print(img)
img = np.random.randint(0,256,size=[4,5],dtype=np.uint8)
i1 = np.zeros(img.shape,np.float32) #x坐标轴的值保持不变
i2 = np.zeros(img.shape,np.float32) # y坐标轴为总行号-1-当前行号
rows,cols = img.shape
for i in range(rows):
for j in range(cols):
i1.itemset((i,j),i)
i2.itemset((i,j),j)
RST = cv2.remap(img,i1,i2,cv2.INTER_LINEAR)
print(RST)
print(img)
结果出现了0,可见行列数不一样时运算中存在值无法映射的情况,无法完成映射的值被处理为0了
将下面纸张通过变换调节至正中央水平竖直放置,最终呈现的图片效果上要保留白纸外的区域:
代码:
import cv2 as cv
img = cv.imread('shu.png')
rows,cols,color = img.shape
# cols-1 and rows-1 are the coordinate limits.
scale_percent =100
M = cv.getRotationMatrix2D(((cols-1)/2.0,(rows-1)/2.0),-140,1)
width = int(img.shape[1] * scale_percent / 100)
height = int(img.shape[0] * scale_percent / 100)
dim = (width, height)
resized = cv.resize(img, dim, interpolation = cv.INTER_AREA);
dst = cv.warpAffine(resized,M,(cols,rows))
cv.namedWindow("enhanced",0);
#cv.resizeWindow("enhanced", 500, 480);
cv.imshow("enhanced",dst)
cv.waitKey()
其中scale_percent =100
width = int(img.shape[1] * scale_percent / 100)
height = int(img.shape[0] * scale_percent / 100)
dim = (width, height)
是用来调整图片大小的。