1.霍夫直線變換簡介
- Hough Line Transform用來做直線檢測
- 前提條件 – 邊緣檢測已經完成
- 平面空間到極座標空間轉換
- 對於任意一條直線上的所有點來說,變換到極座標中,從[0~360]空間,可以得到r的大小
- 屬於同一條直線上點在極座標空(r, theta)必然在一個點上有最強的信號出現,根據此反算到平面座標中就可以得到直線上各點的像素座標。從而得到直線。
2.相關API
2.1 標準的霍夫變換 cv::HoughLines()
- 標準的霍夫變換 cv::HoughLines從平面座標轉換到霍夫空間,最終輸出是 表示極座標空間,需反變換至平面座標,一般情況是有經驗的開發者使用。
cv::HoughLines(
InputArray src, // 輸入圖像,**必須8-bit的灰度圖像**
OutputArray lines, // 輸出的極座標來表示直線
double rho, // 生成極座標時候的像素掃描步長
double theta, //生成極座標時候的角度步長,一般取值CV_PI/180
int threshold, // 閾值,只有獲得足夠交點的極座標點才被看成是直線
double srn=0;// 是否應用多尺度的霍夫變換,如果不是設置0表示經典霍夫變換
double stn=0;//是否應用多尺度的霍夫變換,如果不是設置0表示經典霍夫變換
double min_theta=0; // 表示角度掃描範圍 0 ~180之間, 默認即可
double max_theta=CV_PI
)
2.2 霍夫變換直線概率 cv::HoughLinesP()
- 霍夫變換直線概率 cv::HoughLinesP最終輸出是直線的兩個點的座標。
cv::HoughLinesP(
InputArray src, // 輸入圖像,必須8-bit的灰度圖像
OutputArray lines, // 輸出的極座標來表示直線,一般爲一個vector<Vec4f>變量。
double rho, // 生成極座標時候的像素掃描步長
double theta, //生成極座標時候的角度步長,一般取值CV_PI/180
int threshold, // 閾值,只有獲得足夠交點的極座標點才被看成是直線
double minLineLength=0;// 最小直線長度
double maxLineGap=0;// 最大間隔
)
2.2.1注意:
須將邊緣檢測後的GRAY圖像使用cvtColor(),轉變爲BGR再進行霍夫變換。
3.例程
#include<opencv2/opencv.hpp>
#include<iostream>
#include<math.h>
using namespace cv;
using namespace std;
int Threshold = 20;
int MinLineLength = 30;
int MaxLineGap = 6;
vector<Vec4f> Plines;
Mat edges, dst;
void HoughLinesP_Demo(int,void*);
int main()
{
Mat src;
src = imread("D:/resource/images/shape.png");
if (src.empty())
printf("the image couldn't' be loading...");
//降噪後邊緣處理
Mat GBlur;
GaussianBlur(src, GBlur, Size(3, 3), 0);
Canny(GBlur, edges,0, 255);
//將灰度圖像轉爲BGR,不可少!!!
cvtColor(edges, dst, COLOR_GRAY2BGR);
namedWindow("output");
createTrackbar("Threshold", "output", &Threshold, 40, HoughLinesP_Demo);
createTrackbar("MinLineLength", "output", &MinLineLength, 30, HoughLinesP_Demo);
createTrackbar("MaxLineGap", "output", &MaxLineGap, 30, HoughLinesP_Demo);
//霍夫直線概率變換,並畫線
HoughLinesP_Demo(0, 0);
waitKey(0);
return 1;
}
void HoughLinesP_Demo(int,void*)
{
HoughLinesP(edges, Plines, 1, CV_PI / 180.0, Threshold, MinLineLength, MaxLineGap);
Scalar color = Scalar(0, 0, 255);
for (size_t i=0; i < Plines.size(); i++)
{
Vec4f HLines = Plines[i];
line(dst, Point(HLines[0], HLines[1]), Point(HLines[2], HLines[3]), color, 3, LINE_AA);
}
imshow("output", dst);
}