diff --git a/modules/stitching/include/opencv2/stitching/detail/matchers.hpp b/modules/stitching/include/opencv2/stitching/detail/matchers.hpp index 1a71de51c6..0dbd14f9ab 100644 --- a/modules/stitching/include/opencv2/stitching/detail/matchers.hpp +++ b/modules/stitching/include/opencv2/stitching/detail/matchers.hpp @@ -133,7 +133,9 @@ public: void operator ()(const ImageFeatures &features1, const ImageFeatures &features2, MatchesInfo& matches_info) { match(features1, features2, matches_info); } - void operator ()(const std::vector &features, std::vector &pairwise_matches); + + void operator ()(const std::vector &features, std::vector &pairwise_matches, + const cv::Mat &mask = cv::Mat()); bool isThreadSafe() const { return is_thread_safe_; } diff --git a/modules/stitching/include/opencv2/stitching/stitcher.hpp b/modules/stitching/include/opencv2/stitching/stitcher.hpp index 1616b3d2c2..775c0cdb61 100644 --- a/modules/stitching/include/opencv2/stitching/stitcher.hpp +++ b/modules/stitching/include/opencv2/stitching/stitcher.hpp @@ -95,6 +95,13 @@ public: void setFeaturesMatcher(Ptr features_matcher) { features_matcher_ = features_matcher; } + const cv::Mat& matchingMask() const { return matching_mask_; } + void setMatchingMask(const cv::Mat &mask) + { + CV_Assert(mask.type() == CV_8U && mask.cols == mask.rows); + matching_mask_ = mask.clone(); + } + Ptr bundleAdjuster() { return bundle_adjuster_; } const Ptr bundleAdjuster() const { return bundle_adjuster_; } void setBundleAdjuster(Ptr bundle_adjuster) @@ -130,6 +137,7 @@ private: double conf_thresh_; Ptr features_finder_; Ptr features_matcher_; + cv::Mat matching_mask_; Ptr bundle_adjuster_; bool do_wave_correct_; detail::WaveCorrectKind wave_correct_kind_; diff --git a/modules/stitching/src/matchers.cpp b/modules/stitching/src/matchers.cpp index 187423fea6..5875342336 100644 --- a/modules/stitching/src/matchers.cpp +++ b/modules/stitching/src/matchers.cpp @@ -45,6 +45,7 @@ using namespace std; using namespace cv; using namespace cv::detail; + #ifndef ANDROID using namespace cv::gpu; #endif @@ -340,14 +341,20 @@ const MatchesInfo& MatchesInfo::operator =(const MatchesInfo &other) ////////////////////////////////////////////////////////////////////////////// -void FeaturesMatcher::operator ()(const vector &features, vector &pairwise_matches) +void FeaturesMatcher::operator ()(const vector &features, vector &pairwise_matches, + const Mat &mask) { const int num_images = static_cast(features.size()); + CV_Assert(mask.empty() || (mask.type() == CV_8U && mask.cols == num_images && mask.rows)); + Mat_ mask_(mask); + if (mask_.empty()) + mask_ = Mat::ones(num_images, num_images, CV_8U); + vector > near_pairs; for (int i = 0; i < num_images - 1; ++i) for (int j = i + 1; j < num_images; ++j) - if (features[i].keypoints.size() > 0 && features[j].keypoints.size() > 0) + if (features[i].keypoints.size() > 0 && features[j].keypoints.size() > 0 && mask_(i, j)) near_pairs.push_back(make_pair(i, j)); pairwise_matches.resize(num_images * num_images); diff --git a/modules/stitching/src/stitcher.cpp b/modules/stitching/src/stitcher.cpp index cefbacb4f2..1fbfe4c564 100644 --- a/modules/stitching/src/stitcher.cpp +++ b/modules/stitching/src/stitcher.cpp @@ -165,7 +165,7 @@ Stitcher::Status Stitcher::matchImages() LOG("Pairwise matching"); t = getTickCount(); - (*features_matcher_)(features_, pairwise_matches_); + (*features_matcher_)(features_, pairwise_matches_, matching_mask_); features_matcher_->collectGarbage(); LOGLN("Pairwise matching, time: " << ((getTickCount() - t) / getTickFrequency()) << " sec");