检测出物体轮廓
std::vector <std::vector<cv::Point>> contours;
std::vector <Vec4i> hierarchy;
cv::findContours(canny, contours, hierarchy, cv::RETR_LIST, cv::CHAIN_APPROX_NONE);
霍夫圆检测
std::vector<cv::Vec3f> pcircles;
cv::HoughCircles(__CircleGrayImage, pcircles, cv::HOUGH_GRADIENT, 1, 5, 100, 100, 0, 0);
for (size_t i = 0; i < pcircles.size(); i++)
{
Vec3f c = pcircles[i];
circle(inputImage, Point(c[0], c[1]), c[2], Scalar(0, 0, 255), 3, LINE_AA);
circle(inputImage, Point(c[0], c[1]), 2, Scalar(0, 255, 0), 3, LINE_AA);
}
测试代码
#include
#include
#include
#include
using namespace std;
int main()
{
cv::Mat inputImage = imread("test.png", cv::IMREAD_COLOR);
cv::Mat __inputImage;
cv::Mat __tmpImage;
cvtColor(inputImage, __tmpImage, cv::COLOR_BGRA2RGB);
__tmpImage.convertTo(__inputImage, CV_8UC1);
cv::Mat __useCircleImage = __inputImage.clone();
cv::Mat __useOtherImage = __inputImage.clone();
cv::Mat __resultImage = __inputImage.clone();
cv::Mat __CircleGaussianBlurImage;
cv::GaussianBlur(__useCircleImage, __CircleGaussianBlurImage, cv::Size(3, 3), 0);
cv::Mat __CircleGrayImage;
cv::cvtColor(__CircleGaussianBlurImage, __CircleGrayImage, cv::COLOR_BGR2GRAY);
cv::Mat __CircleCannyImage;
cv::Canny(__CircleGrayImage, __CircleCannyImage, 100, 200);
std::vector<cv::Vec3f> pcircles;
cv::Mat __OtherGrayImage;
cv::cvtColor(__useOtherImage, __OtherGrayImage, cv::COLOR_BGR2GRAY);
cv::Mat __OtherThresholdImage;
cv::threshold(__OtherGrayImage, __OtherThresholdImage, 0, 255, cv::THRESH_BINARY_INV | cv::THRESH_OTSU);
std::vector<std::vector<cv::Point>> __contours;
std::vector<cv::Vec4i> __hierarchy;
cv::findContours(__OtherThresholdImage, __contours, __hierarchy, cv::RETR_EXTERNAL, cv::CHAIN_APPROX_SIMPLE);
std::vector<std::vector<cv::Point>> __contourPloy(__contours.size());
for (size_t i = 0; i < __contours.size(); i++)
{
double __epsion = 0.02 * cv::arcLength(__contours[i], true);
cv::approxPolyDP(cv::Mat(__contours[i]), __contourPloy[i], __epsion, true);
cv::Moments moment = cv::moments(__contours[i]);
int x = (int)(moment.m10 / moment.m00);
int y = (int)(moment.m01 / moment.m00);
const cv::Scalar blue = cv::Scalar(255, 0, 0);
const cv::Scalar green = cv::Scalar(0, 255, 0);
const cv::Scalar red = cv::Scalar(0, 0, 255);
const cv::Scalar orange = cv::Scalar(255, 128, 0);
const cv::Scalar violet = cv::Scalar(255, 0, 255);
const cv::Scalar cyan = cv::Scalar(128, 138, 135);
if (__contourPloy[i].size() == 3)
{
string tempText = "triangle";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
drawContours(__resultImage, __contours, i, blue, 2);
}
else if (__contourPloy[i].size() == 4)
{
string tempText = "quadrangle";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
drawContours(__resultImage, __contours, i, green, 2);
}
else if (__contourPloy[i].size() == 5)
{
string tempText = "pentagon";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
drawContours(__resultImage, __contours, i, red, 2);
}
else if (__contourPloy[i].size() == 6)
{
string tempText = "hexagon";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
drawContours(__resultImage, __contours, i, orange, 2);
}
else if (__contourPloy[i].size() >= 10)
{
drawContours(__resultImage, __contours, i, violet, 2);
double P = cv::arcLength(__contourPloy[i], true);
double A = cv::contourArea(__contourPloy[i]);
double K = pow(P, 2) / (4 * A * 3.1415926);
if (K < 1.2)
{
string tempText = "circle";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
}
else
{
string tempText = "star";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
}
}
else
{
drawContours(__resultImage, __contours, i, cyan, 2);
double P = cv::arcLength(__contourPloy[i], true);
double A = cv::contourArea(__contourPloy[i]);
double K = pow(P, 2) / (4 * A * 3.1415926);
if (K < 1.2)
{
string tempText = "circle";
putText(__resultImage, tempText, cv::Point(x - 20, y), cv::FONT_HERSHEY_PLAIN, 0.7, cv::Scalar(0, 0, 0), 1, 8, false);
}
}
}
imshow("边缘检测结果", __resultImage);
cv::waitKey();
return 0;
}
效果图