#include #include #include #include "opencv2/core/core.hpp" #include "opencv2/imgproc/imgproc.hpp" #include "opencv2/gpu/gpu.hpp" #include "opencv2/highgui/highgui.hpp" #include "opencv2/contrib/contrib.hpp" using namespace std; using namespace cv; using namespace cv::gpu; static Mat loadImage(const string& name) { Mat image = imread(name, IMREAD_GRAYSCALE); if (image.empty()) { cerr << "Can't load image - " << name << endl; exit(-1); } return image; } int main(int argc, const char* argv[]) { CommandLineParser cmd(argc, argv, "{ i | image | pic1.png | input image }" "{ t | template | templ.png | template image }" "{ s | scale | | estimate scale }" "{ r | rotation | | estimate rotation }" "{ | gpu | | use gpu version }" "{ | minDist | 100 | minimum distance between the centers of the detected objects }" "{ | levels | 360 | R-Table levels }" "{ | votesThreshold | 30 | the accumulator threshold for the template centers at the detection stage. The smaller it is, the more false positions may be detected }" "{ | angleThresh | 10000 | angle votes treshold }" "{ | scaleThresh | 1000 | scale votes treshold }" "{ | posThresh | 100 | position votes threshold }" "{ | dp | 2 | inverse ratio of the accumulator resolution to the image resolution }" "{ | minScale | 0.5 | minimal scale to detect }" "{ | maxScale | 2 | maximal scale to detect }" "{ | scaleStep | 0.05 | scale step }" "{ | minAngle | 0 | minimal rotation angle to detect in degrees }" "{ | maxAngle | 360 | maximal rotation angle to detect in degrees }" "{ | angleStep | 1 | angle step in degrees }" "{ | maxSize | 1000 | maximal size of inner buffers }" "{ h | help | | print help message }" ); //cmd.about("This program demonstrates arbitary object finding with the Generalized Hough transform."); if (cmd.get("help")) { cmd.printParams(); return 0; } const string templName = cmd.get("template"); const string imageName = cmd.get("image"); const bool estimateScale = cmd.get("scale"); const bool estimateRotation = cmd.get("rotation"); const bool useGpu = cmd.get("gpu"); const double minDist = cmd.get("minDist"); const int levels = cmd.get("levels"); const int votesThreshold = cmd.get("votesThreshold"); const int angleThresh = cmd.get("angleThresh"); const int scaleThresh = cmd.get("scaleThresh"); const int posThresh = cmd.get("posThresh"); const double dp = cmd.get("dp"); const double minScale = cmd.get("minScale"); const double maxScale = cmd.get("maxScale"); const double scaleStep = cmd.get("scaleStep"); const double minAngle = cmd.get("minAngle"); const double maxAngle = cmd.get("maxAngle"); const double angleStep = cmd.get("angleStep"); const int maxSize = cmd.get("maxSize"); Mat templ = loadImage(templName); Mat image = loadImage(imageName); int method = GHT_POSITION; if (estimateScale) method += GHT_SCALE; if (estimateRotation) method += GHT_ROTATION; vector position; cv::TickMeter tm; if (useGpu) { GpuMat d_templ(templ); GpuMat d_image(image); GpuMat d_position; Ptr d_hough = GeneralizedHough_GPU::create(method); d_hough->set("minDist", minDist); d_hough->set("levels", levels); d_hough->set("dp", dp); d_hough->set("maxSize", maxSize); if (estimateScale && estimateRotation) { d_hough->set("angleThresh", angleThresh); d_hough->set("scaleThresh", scaleThresh); d_hough->set("posThresh", posThresh); } else { d_hough->set("votesThreshold", votesThreshold); } if (estimateScale) { d_hough->set("minScale", minScale); d_hough->set("maxScale", maxScale); d_hough->set("scaleStep", scaleStep); } if (estimateRotation) { d_hough->set("minAngle", minAngle); d_hough->set("maxAngle", maxAngle); d_hough->set("angleStep", angleStep); } d_hough->setTemplate(d_templ); tm.start(); d_hough->detect(d_image, d_position); d_hough->download(d_position, position); tm.stop(); } else { Ptr hough = GeneralizedHough::create(method); hough->set("minDist", minDist); hough->set("levels", levels); hough->set("dp", dp); if (estimateScale && estimateRotation) { hough->set("angleThresh", angleThresh); hough->set("scaleThresh", scaleThresh); hough->set("posThresh", posThresh); hough->set("maxSize", maxSize); } else { hough->set("votesThreshold", votesThreshold); } if (estimateScale) { hough->set("minScale", minScale); hough->set("maxScale", maxScale); hough->set("scaleStep", scaleStep); } if (estimateRotation) { hough->set("minAngle", minAngle); hough->set("maxAngle", maxAngle); hough->set("angleStep", angleStep); } hough->setTemplate(templ); tm.start(); hough->detect(image, position); tm.stop(); } cout << "Found : " << position.size() << " objects" << endl; cout << "Detection time : " << tm.getTimeMilli() << " ms" << endl; Mat out; cvtColor(image, out, COLOR_GRAY2BGR); for (size_t i = 0; i < position.size(); ++i) { Point2f pos(position[i][0], position[i][1]); float scale = position[i][2]; float angle = position[i][3]; RotatedRect rect; rect.center = pos; rect.size = Size2f(templ.cols * scale, templ.rows * scale); rect.angle = angle; Point2f pts[4]; rect.points(pts); line(out, pts[0], pts[1], Scalar(0, 0, 255), 3); line(out, pts[1], pts[2], Scalar(0, 0, 255), 3); line(out, pts[2], pts[3], Scalar(0, 0, 255), 3); line(out, pts[3], pts[0], Scalar(0, 0, 255), 3); } imshow("out", out); waitKey(); return 0; }