opencv 最大內接矩形筆記

專注的阿熊發表於2021-11-03

#include<opencv2\opencv.hpp>

#include <iostream>

#include<vector>

using namespace cv;

using namespace std;

/**

* @brief expandEdge 擴充套件邊界函式

* @param img: 輸入影像,單通道二值圖,深度為 8

* @param edge   邊界陣列,存放 4 條邊界值

* @param edgeID 當前邊界號

* @return 布林值 確定當前邊界是否可以擴充套件

*/

bool expandEdge(const Mat & img, int edge[], const int edgeID)

{

//[1] -- 初始化引數

int nc = img.cols;

int nr = img.rows;

switch (edgeID) {

case 0:

if (edge[0]>nr)

return false;

for (int i = edge[3]; i <= edge[1]; ++i)

{

if (img.at<uchar>(edge[0], i) == 255)// 遇見 255 畫素表明碰到邊緣線

return false;

}

edge[0]++;

return true;

break;

case 1:

if (edge[1]>nc)

return false;

for (int i = edge[2]; i <= edge[0]; ++i)

{

if (img.at<uchar>(i, edge[1]) == 255)// 遇見 255 畫素表明碰到邊緣線

return false;

}

edge[1]++;

return true;

break;

case 2:

if (edge[2]<0)

return false;

for (int i = edge[3]; i <= edge[1]; ++i)

{

if (img.at<uchar>(edge[2], i) == 255)// 遇見 255 畫素表明碰到邊緣線

return false;

}

edge[2]--;

return true;

break;

case 3:

if (edge[3]<0)

return false;

for (int i = edge[2]; i <= edge[0]; ++i)

{

if (img.at<uchar>(i, edge[3]) == 255)// 遇見 255 畫素表明碰到邊緣線

return false;

}

edge[3]--;

return true;

break;

default:

return false;

break;

}

}

/**

* @brief 求取連通區域內接矩

* @param img: 輸入影像,單通道二值圖,深度為 8

* @param center: 最小外接矩的中心

* @return   最大內接矩形

* 基於中心擴充套件演算法

*/

cv::Rect InSquare(Mat &img, const Point center)

{

// --[1] 引數檢測

if (img.empty() ||img.channels()>1|| img.depth()>8)

return Rect();

// --[2] 初始化變數

int edge[4];

edge[0] = center.y + 1;//top

edge[1] = center.x + 1;//right

edge[2] = center.y - 1;//bottom

edge[3] = center.x - 1;//left

    //[2]

    // --[3] 邊界擴充套件 ( 中心擴散法 )

bool EXPAND[4] = { 1,1,1,1 };// 擴充套件標記位

int n = 0;

while (EXPAND[0] || EXPAND[1] || EXPAND[2] || EXPAND[3])

{

int edgeID = n % 4;

EXPAND[edgeID] = expandEdge(img, edge, edgeID);

n++;

}

//[3]

//qDebug() << edge[0] << edge[1] << edge[2] << edge[3];

Point tl = Point(edge[3], edge[0]);

Point br = Point(edge[1], edge[2]);

return Rect(tl, br);

}

int main()

{

bool isExistence = false;

float first_area = 0;

/// 載入源影像

Mat src;

src = imread("cen.bmp", 1);

//src =外匯跟單gendan5.com imread("C:\\Users\\Administrator\\Desktop\\ 測試圖片 \\xxx\\20190308152516.jpg",1);

//src = imread("C:\\Users\\Administrator\\Desktop\\ 測試圖片 \\xx\\20190308151912.jpg",1);

//src = imread("C:\\Users\\Administrator\\Desktop\\ 測試影像 \\2\\BfImg17(x-247 y--91 z--666)-(492,280).jpg",1);

cvtColor(src, src, CV_RGB2GRAY);

threshold(src, src, 100, 255, THRESH_BINARY);

Rect ccomp;

Point center(src.cols / 2, src.rows / 2);

//floodFill(src, center, Scalar(255, 255, 55), &ccomp, Scalar(20, 20, 20), Scalar(20, 20, 20));

if (src.empty())

{

cout << "fali" << endl;

}

//resize(src, src, cv::Size(496, 460), cv::INTER_LINEAR);

imshow("src", src);

Rect rr = InSquare(src, center);

rectangle(src, rr, Scalar(255), 1, 8);

imshow("src2", src);

waitKey(0);

getchar();

return 0;

}


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/69946337/viewspace-2840460/,如需轉載,請註明出處,否則將追究法律責任。

相關文章