基于特征的全景图像拼接
这个例子展示了如何使用基于特征的图像配准技术自动创建全景图。
概述
特征检测和匹配是许多计算机视觉应用中使用的强大技术,如图像配准,跟踪和目标检测。在这个例子中,基于特征的技术被用来自动拼接一组图像。图像拼接过程是基于特征的图像配准的扩展。不同于配准单对图像,多对图像相对地依次配准形成全景图像。
步骤1 -加载图像
本例中使用的图像集包含建筑物的图片。这些照片是用未校准的智能手机相机拍摄的,相机沿着地平线从左到右扫视,捕捉到建筑物的所有部分。
如下图所示,图像相对不受任何镜头畸变的影响,因此不需要相机校准。然而,如果镜头失真,相机应该校准和图像不失真之前创建全景。你可以使用相机校准器应用程序校准相机,如果需要的话。
%加载图像。buildingDir = fullfile(toolboxdir =“愿景”),“visiondata”,“建筑”);buildscene = imageDatastore(builddir);%显示要缝合的图像。蒙太奇(buildingScene.Files)
步骤2 -注册图像对
要创建全景,首先使用以下程序注册连续的图像对:
检测和匹配之间的特征 和 .
估计几何变换, ,那是地图 来 .
计算映射的转换 进入全景图像为 .
从映像集中读取第一个映像。I = readimage(buildingScene,1);%初始化I(1)的特性grayImage = im2gray(I);points = detectsurfeatures (grayImage);[features, points] = extractFeatures(grayImage,points);初始化单位矩阵的所有转换。请注意投影变换在这里使用,因为建筑图像是公平的靠近相机。对于从较远距离拍摄的场景,您可以使用%仿射变换。numImages = nummel (buildingScene.Files);tforms(numImages) = projtform2d;初始化变量来保存图像大小。imageSize = 0 (numImages,2);%迭代剩余的图像对为n = 2:numImages%存储I(n-1)的点数和特征。pointsPrevious = points;featuresPrevious = features;%读I(n)。I = readimage(buildingScene, n);%将图像转换为灰度。grayImage = im2gray(I);%保存图像大小。imageSize(n,:) = size(grayImage);%检测并提取I(n)的SURF特征。points = detectsurfeatures (grayImage);[features, points] = extractFeatures(grayImage, points);找出I(n)和I(n-1)之间的对应关系。indexPairs = matchFeatures(features, featuresPrevious,“独特的”,真正的);matchedPoints = points(indexPairs(:,1),:);matchedPointsPrev = pointsPrevious(indexPairs(:,2),:);估计I(n)和I(n-1)之间的变换。tforms(n) = estgeotform2d(matchedPoints, matchedPointsPrev,...“射影”,“信心”, 99.9,“MaxNumTrials”, 2000);%计算T(1) * T(2) *…* T(n-1) * T(n)tforms (n)。A = tforms(n-1)A *变换(n) A;结束
在这一点上,所有的变换tforms
是相对于第一个图像的。这是编码图像配准过程的一种方便的方法,因为它允许对所有图像进行顺序处理。然而,使用第一张图像作为全景图的开始并不能产生最美观的全景图,因为它往往会扭曲构成全景图的大多数图像。一个更好的全景可以通过修改变换来创建,这样场景的中心是最小扭曲的。这是通过对中心图像进行反变换并将该变换应用于所有其他图像来实现的。
首先使用projtform2d
outputLimits
方法查找每个转换的输出限制。然后使用输出限制来自动找到大致位于场景中心的图像。
计算每个转换的输出限制。为i = 1:元素个数(tforms) [xlim(我,:),ylim(我,:)]= outputLimits (tforms(我),(1)图象尺寸(我,2)]、[1图象尺寸(我,1)));结束
接下来,计算每个变换的平均X极限,并找到位于中心的图像。这里只使用X限制,因为已知场景是水平的。如果使用另一组图像,则可能需要使用X和Y限制来查找中心图像。
avgXLim = mean(xlim, 2);[~,idx] = sort(avgXLim);centerIdx = floor((numel(tforms)+1)/2);centerImageIdx = idx(centerIdx);
最后,将中心图像的逆变换应用于所有其他图像。
Tinv = invert(tforms(centerImageIdx));为I = 1: nummel (tforms) tforms(I)。A = Tinv。A *表示(i) A;结束
步骤3 -初始化全景
现在,创建一个初始的、空的全景图,所有图像都映射到其中。
使用outputLimits
方法来计算所有转换的最小和最大输出限制。这些值用于自动计算全景的大小。
为i = 1:元素个数(tforms) [xlim(我,:),ylim(我,:)]= outputLimits (tforms(我),(1)图象尺寸(我,2)]、[1图象尺寸(我,1)));结束maxImageSize = max(imageSize);找出最小和最大输出限制。xMin = min([1;xlim (:)));xMax = max([maxImageSize(2);xlim (:)));yMin = min([1;ylim (:)));yMax = max([maxImageSize(1);ylim (:)));%全景图的宽度和高度。width = round(xMax - xMin);height = round(yMax - yMin);初始化“空”全景图。全景= 0([高度宽度3],“喜欢”,我);
步骤4 -创建全景图
使用imwarp
将图像映射到全景图中并使用愿景。alphablend
将图像叠加在一起。
搅拌机=视野。alphablend (“操作”,“二元掩模”,...“MaskSource”,输入端口的);创建一个定义全景图大小的二维空间参考对象。xLimits = [xMin xMax];yLimits = [yMin = yMax];panoramaView = imref2d([height width], xLimits, yLimits);%创建全景图。为i = 1:numImages i = readimage(buildingScene, i);将I变换为全景。warpedImage = imwarp(I, tforms(I),“OutputView”, panoramaView);%生成二进制掩码。mask = imwarp(true(size(I,1),size(I,2)), tforms(I),“OutputView”, panoramaView);将warpeimage叠加到全景图上。panorama = step(blender, panorama, warpeimage, mask);结束图imshow(全景)
结论
这个例子向您展示了如何使用基于特征的图像配准技术自动创建全景。可以将其他技术合并到示例中,以改进全景图像[1]的混合和对齐。
参考文献
[1]马修·布朗和大卫·g·洛威。2007。使用不变特征的自动全景图像拼接。Int。j .第一版。异象74,1(2007年8月),59-73。