我想将简单的拼接代码程序从python转移到c ++。我是初学者,我找不到c ++的这个功能。 python代码在这里:
import cv2
import numpy as np
def find_overlap_start(left_img, right_img):
assert left_img.shape == right_img.shape
height, width = left_img.shape[:2]
haystack = left_img
needle = right_img[:,0:width/2]
res = cv2.matchTemplate(haystack, needle, cv2.TM_CCORR_NORMED)
min_val, max_val, min_loc, max_loc = cv2.minMaxLoc(res)
return max_loc[0]
def find_overlaps(images):
overlap_starts = []
for i in range(len(images) - 1):
overlap_starts.append(find_overlap_start(images[i], images[i+1]))
# And the last image is used whole
overlap_starts.append(images[-1].shape[1])
return overlap_starts
# Simple stitch, no blending, right hand slice overlays left hand slice
def stitch_images(images, overlap_starts):
height, width = images[0].shape[:2]
total_width = sum(overlap_starts)
result = np.zeros((height, total_width), np.uint8)
current_column = 0
for i,start in enumerate(overlap_starts):
result[:,current_column:current_column+width] = images[i]
current_column += start
return result
images = [cv2.imread("slice_%d.png" % i, 0) for i in range(4)]
overlap_starts = find_overlaps(images)
cv2.imwrite("slices_out.png", stitch_images(images, overlap_starts))
到目前为止,我转移了第一个功能,但我不知道它是否正常,也不知道下一步该怎么做。这是c ++代码的开头:
#include <iostream>
#include <fstream>
#include "opencv2/highgui/highgui.hpp"
#include <opencv2/stitching.hpp>
using namespace std;
using namespace cv;
// Global variables.
int height;
int width;
// Create function that finds point where overlap starts.
Point find_overlap_start(Mat left_img, Mat right_img)
{
if (left_img.size() == right_img.size())
{
// Get rows columns of left image.
height = left_img.rows;
width = left_img.cols;
// Copy left image to new variable.
Mat haystack = left_img;
// Create variable niddle = cropped right image.
roi.width = (left_img.size().width) / 2;
roi.height = left_img.size().height;
Mat needle = right_img(roi);
// Apply template matching and store result in res.
matchTemplate(haystack, needle, res, TM_CCORR_NORMED);
minMaxLoc(res, &minval, &maxval, &minloc, &maxloc);
return maxloc;
}
}
// Create vector of points where images start to overlap.
vector<Point> find_overlaps(vector<Mat> images)
{
// Create vector of overlaps coordinates.
vector<Point> overlap_starts;
// Loop trought all images and get top-left points where imgages ovelap.
for (int i = 0; i != images.size() - 1; i++)
{
// Find overlap start between two images.
Point overlap = find_overlap_start(images[i], images[i + 1]);
overlap_starts.push_back(overlap);
}
// And the last image is used whole:
Don't know how to do that...
return overlap_starts;
}
// And then the main fucntion
int main(int argc, char* argv[])
{
Mat img1 = imread("image1.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img2 = imread("image2.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Point max_loc = find_overlap_start(img1, img2);
waitKey(0);
return 0;
}
我想将所有python程序转移到c ++。如果有人可以评论一下Python代码,我也会很高兴,因为我现在还不知道它是如何工作的......
答案 0 :(得分:3)
解决我自己的问题
由于没有答案我已经找到了使用matchTemplate()
函数进行简单图像拼接的c ++代码。我想与您分享我的结果,以便您可以发表评论,添加一些内容或当然可以使用它。代码是使用this引用从python转移的。
代码在这里:
#include <iostream>
#include <fstream>
#include "opencv2/highgui/highgui.hpp"
#include <opencv2/stitching.hpp>
using namespace std;
using namespace cv;
// Global variables.
int height;
int width;
double minval, maxval;
Point minloc, maxloc;
Rect roi;
Mat res;
// Create function that finds point where overlap between two images starts.
// Images "left_img" and "right_img" are passed in by find_overlaps function.
Point find_overlap_start(Mat left_img, Mat right_img)
{
// Check if the sizes of images are the same.
if (left_img.size() == right_img.size())
{
// Get rows columns of left image.
height = left_img.rows;
width = left_img.cols;
// Copy left image to new variable.
Mat haystack = left_img;
// Create matrix "neddle" to be used as our "template".
roi.width = (left_img.size().width) / 2;
roi.height = left_img.size().height;
Mat needle = right_img(roi);
// Apply template matching and store result in res.
matchTemplate(haystack, needle, res, TM_CCORR_NORMED);
minMaxLoc(res, &minval, &maxval, &minloc, &maxloc);
// Return top-left coordinate where the matching starts.
return maxloc;
}
}
// Create vector of points where images start to overlap.
vector<Point> find_overlaps(vector<Mat> images)
{
// Create vector of overlaps coordinates.
vector<Point> overlap_starts;
for (int i = 0; i != images.size() - 1; i++)
{
// Find overlap start between two images.
Point overlap = find_overlap_start(images[i], images[i + 1]);
// Add overlap point to vector of points.
overlap_starts.push_back(overlap);
}
// Return vector of "overlaping points" (top-left).
return overlap_starts;
}
// Simple stitch, no blending, right hand slice overlays left hand slice.
Mat stitch_images(vector<Mat> images, vector<Point> overlap_starts)
{
// Define variable to store width of the composite image.
int total_width = 0;
// Loop trought vector of overlaped points and calculate total_width.
for (int i = 0; i < images.size() - 1; i++)
{
// overlap_starts[i, 0].x -> x coordinates of Point in overlap_starts vector.
total_width += overlap_starts[i, 0].x;
}
// Now add width of image to the total width.
int img_width = images[0].cols;
total_width = total_width + img_width;
// Create matrix that is of the size ( height, total_width -> depends on the number of images).
Mat result = Mat::zeros(Size(total_width, height), CV_8UC1);
// Put images next to each other on the result matrix.
int current_column = 0;
for (int i = 0; i < images.size(); i++)
{
// Where to copy current image?
images[i].copyTo(result.rowRange(0,400).colRange(current_column,( current_column+600 ) ));
// The next image should be moved right for:
current_column += overlap_starts[i, 0].x;
}
// Display composite image.
namedWindow("result", WINDOW_AUTOSIZE);
imshow("result", result);
return result;
}
int main(int argc, char* argv[])
{
// Load images from HD.
Mat img1 = imread("pos1.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img2 = imread("pos2.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img3 = imread("pos3.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img4 = imread("pos4.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img5 = imread("pos5.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img6 = imread("pos6.bmp", CV_LOAD_IMAGE_GRAYSCALE);
Mat img7 = imread("pos7.bmp", CV_LOAD_IMAGE_GRAYSCALE);
// Create vector of images.
vector<Mat> various_images;
various_images.push_back(img1);
various_images.push_back(img2);
various_images.push_back(img3);
various_images.push_back(img4);
various_images.push_back(img5);
various_images.push_back(img6);
various_images.push_back(img7);
// Display loaded images if you want.
namedWindow("img1", WINDOW_AUTOSIZE);
imshow("img1", img1);
namedWindow("img2", WINDOW_AUTOSIZE);
imshow("img2", img2);
namedWindow("img3", WINDOW_AUTOSIZE);
imshow("img3", img3);
namedWindow("img4", WINDOW_AUTOSIZE);
imshow("img4", img4);
namedWindow("img5", WINDOW_AUTOSIZE);
imshow("img5", img5);
namedWindow("img6", WINDOW_AUTOSIZE);
imshow("img6", img6);
namedWindow("img6", WINDOW_AUTOSIZE);
imshow("img6", img6);
// Call function find_overlaps ( find top-left points of overlaping).
vector<Point> overlap_starts = find_overlaps(various_images);
// Call stitch_function and stitch images together.
stitch_images(various_images, overlap_starts);
waitKey(0);
return 0;
}
该代码可用于快速拼接如下图像:
结果给了我们这个: