计算机视觉随笔(全景图实战)

计算机视觉随笔(全景图实战)_第1张图片
封面

全景图

全景图功能已经成为手机厂家和相机软件必备的功能,我们根据友好的提示很容易就能拍摄出一张不错的全景照片。
不过对于这些特定需求我们需要通过自己制作全景图。当然我们可以用PS 来弄。那么我们还有必要学吗,当然有了,商场卖袜子,那么路边就不摆摊了。
我们需要什么技术呢, opencv, 需要了解特征点。

1对1特征匹配

计算机视觉随笔(全景图实战)_第2张图片
1对1的特征匹配

k对最佳匹配

计算机视觉随笔(全景图实战)_第3张图片
k对最佳匹配

随机抽样一致算法 RANSAC

基本思路是我们找到特征点,也就是两张图共同特征点。然后我们通过筛选得到几对特征点来计算出相机模型,最后就可以进拼合。

import cv2
import numpy as np
class Stitcher:
    # 
    def stitch(self,images,ratio=0.75,reprojThresh=4.0,showMatches=False):
        (imageA, imageB) = images
        print imageA

        (kpsA,featuresA) = self.detectAndDescribe(imageA)
        (kpsB,featuresB) = self.detectAndDescribe(imageB)

        M = self.matchKeypoints(kpsA,kpsB,featuresA,featuresB,ratio,reprojThresh)

        if M is None:
            return None

        (matches, H, status) = M
        result = cv2.warpPerspective(imageA,H,(imageA.shape[1] + imageB.shape[1],imageA.shape[0]))
        cv2.imshow("res",result)
        cv2.waitKey(1)
        cv2.destroyAllWindows()
        result[0:imageB.shape[0],0:imageB.shape[1]] = imageB

        if showMatches:
            pass
            # vis = self.drawMatches(imageA,imageB,kpsA,kpsB,matches,status)

        return result

    def detectAndDescribe(self,image):
        gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)

        sift = cv2.xfeatures2d.SIFT_create()

        (kps,features) = sift.detectAndCompute(gray,None)

        kps = np.float32([kp.pt for kp in kps])

        return (kps,features)

    
    def matchKeypoints(self,kpsA,kpsB,featuresA,featuresB,ratio,reprojThresh):
        matcher = cv2.BFMatcher()
        rawMatches = matcher.knnMatch(featuresA,featuresB,2)

        matches = []
        for m in rawMatches:
            if len(m) == 2 and m[0].distance < m[1].distance * ratio:
                matches.append((m[0].trainIdx,m[0].queryIdx))
        
        if len(matches) > 4:
            ptsA = np.float32([kpsA[i] for (_,i) in matches])
            ptsB = np.float32([kpsB[i] for (i,_) in matches])

            (H,status) = cv2.findHomography(ptsA,ptsB,cv2.RANSAC,reprojThresh)

            return (matches, H, status)

这里有三个方法 stitch 负责缝合图片,这里我们提取特征点使用 SIFT 这个。注意在新版的 opencv 这些功能因为一些技术专利的问题,不再免费提供了。我们需要使用较早的版本来使用 SIFT功能。

(kps,features) = sift.detectAndCompute(gray,None)

这里分为两个部分检测计算。我们也可以使用单独使用检测。

            (H,status) = cv2.findHomography(ptsA,ptsB,cv2.RANSAC,reprojThresh)

这里需要一些计算机几何知识,只有理解单应变相机模型的只是

你可能感兴趣的:(计算机视觉随笔(全景图实战))