我有一个我已设法使用openCV提取的仪表 Image of the meter in different positions中间的白色东西是指针,可以从0到360。
我的代码:
void readAngleOfMeter(Mat image, int number)
{
cvtColor(image, image, COLOR_BGR2GRAY);
inRange(image, Scalar(255, 255, 255), Scalar(255, 255, 255), image);
vector<Vec2f> lines;
HoughLines(tmp, lines, 1, CV_PI / 360, 30, 0, 0);
if (lines.size() == 0) {
cout << "No lines found" << endl;
return;
}
float thetasum = 0;
for (size_t i = 0; i < lines.size(); i++)
{
float theta = lines[i][1];
thetasum += theta;
}
thetasum = thetasum / static_cast<int>(lines.size());
cout << "Theta " << thetasum << endl;
}
我现在的问题是我想读取仪表的角度。所以我考虑使用每条线的平均角度,但问题是它不起作用,因为一条线可以用两种方式解释(例如90与270相同),也可以从360到0时解释
有什么想法吗?
答案 0 :(得分:0)
你甚至不需要使用Hough变换。编写一个循环,以1度为增量从0到360度迭代,查看以图像中心为中心的圆圈中的像素。记住第一个白色像素的角度,当你发现围绕圆圈的下一个黑色像素时,取其角度和平均值与起始角度。
您可能需要首先模糊一点或扩大仪表针以填补任何间隙。
使用半径进行实验 - 较小的半径将使您的分辨率降低,因为针在那里看起来更厚。较大的半径将为您提供更高的分辨率,但您可能会丢失针,因为它距离中心更远。
答案 1 :(得分:0)
Hough函数确实会留下不可恢复的180°不确定性。
您可以计算交点,即中心点的估计值并检查其所在ROI的哪一侧(如有必要,沿平分线采样以找到指针的方向。
答案 2 :(得分:0)
解决了,这是我使用的代码。
float radius = 50;
bool found = false;
float startv = 0;
float endv = 0;
for (float v = 0; v < 360; v++)
{
int x = center.x + cos(v * CV_PI / 180.0) * radius;
int y = center.y + sin(v * CV_PI / 180.0) * radius;
Point p{x,y};
if (!found && gray.at<uchar>(x, y) != 255) {
startv = v;
found = true;
}
if (found && gray.at<uchar>(x, y) == 255) {
endv = v;
break;
}
}