作业:
思路:
1、转化成HSV,找出相应颜色对应的范围,用inRange函数提取出来。(这个一定要注意,不同的颜色的范围,我也是刚开始做,在找范围(scalar(a,b,c)时不断尝试才提取出来。)
2、找出相应轮廓并将轮廓画出。
3、用最小外接矩形,找出要提取的矩阵。
4、将找出矩形的四个顶点按照顺时针顺序排除。
5、运用三点法的仿射变换,找出变化前和变化后的坐标位置。
#include
#include
#include
using namespace std;
using namespace cv;
int main()
{
Mat srcImage = imread("D://RM//OpenCv的学习//图像中提取一特定矩形//test2.png");
if (!srcImage.data)
{
cout << "读取图片错误,请重新输入正确路径!\n";
system("pause");
return -1;
}
Mat srcHSV;
cvtColor(srcImage, srcHSV, COLOR_BGR2HSV);
Mat dstImage;
int ZYW;
cout << "如果提取蓝色牌子请输入1 ,如果提取绿色牌子请输入2" << endl;
cin >> ZYW;
if(ZYW==1){ inRange(srcHSV, Scalar(100, 120, 125), Scalar(124, 220, 255), dstImage); }
else if(ZYW==2){ inRange(srcHSV, Scalar(56, 90, 80), Scalar(90, 255, 200), dstImage); }
imshow("【利用inRange()函数实现阈值化】", dstImage);
Mat element = getStructuringElement(MORPH_RECT, Size(1, 2));
vector> contours;
vector contour;
vector hierarchy;
findContours(dstImage, contours, hierarchy, RETR_EXTERNAL, CHAIN_APPROX_SIMPLE, Point());
//轮廓绘制
Mat drawImage;
double width = srcImage.cols;
double height = srcImage.rows;
Mat dst = Mat::zeros(srcImage.size(), CV_8UC3);
cout << contours.size() << endl;
for (int t = 0; t < contours.size(); t++)
{
double length2 = arcLength(contours[t], true);
cout << "第" << t << "个轮廓长度=" << length2 << endl;
if (length2 > 800) {
contour = contours[t];
Scalar color = Scalar(250, 120, 220);
drawContours(srcImage, contours, t, color, 2, 8, hierarchy, 0, Point(0, 0));
}
}
namedWindow("output", WINDOW_AUTOSIZE);
imshow("output", srcImage);
RotatedRect rr = minAreaRect(contour);
Point2f points[4];
rr.points(points);
Point2f points2[4];
cout << "center.x = " << rr.center.x << "center.y = " << rr.center.y << endl;
for (int i = 0; i < 4; i++) {
if (points[i].x < rr.center.x) {
if (points[i].y < rr.center.y) {
points2[0] = points[i];
}
else if (points[i].y > rr.center.y) {
points2[3] = points[i];
}
}
else if (points[i].x > rr.center.x) {
if (points[i].y > rr.center.y) {
points2[2] = points[i];
}
else if (points[i].y < rr.center.y) {
points2[1] = points[i];
}
}
}
for (int i = 0; i < 4; i++) {
cout << points2[i].x << " " << points2[i].y << endl;
}
double chang = sqrt((points2[1].y - points2[0].y) * (points2[1].y - points2[0].y) + (points2[1].x - points[0].x) * (points2[1].x - points[0].x));
double kuan = sqrt((points2[3].y - points2[0].y) * (points2[3].y - points2[0].y) + (points2[3].x - points2[0].x) * (points2[3].x - points2[0].x));
Point2f srcPoints[3];
Point2f dstPoints[3];
srcPoints[0] = points2[0];
srcPoints[1] = points2[1];
srcPoints[2] = points2[3];
dstPoints[0] = Point2f(points2[0].x, points2[0].y);
dstPoints[1] = Point2f(points2[0].x + chang, points2[0].y);
dstPoints[2] = Point2f(points2[0].x, points2[0].y + kuan);
Mat M1 = getAffineTransform(srcPoints, dstPoints);
warpAffine(srcImage, srcImage, M1, srcImage.size());
imshow("正", srcImage);
Rect rect1(points[1].x, points[1].y, chang, kuan);
Mat after_1;
srcImage(rect1).copyTo(after_1);
imshow("蓝色指示牌1", after_1);
imwrite("result3.png", after_1);
waitKey(0);
return 0;
}
运行结果如下:
第一次学,方法可能不是很好,若有不足请大家指正!!!