ill*_*umi 1 c++ signal-processing image-processing edge-detection
我可以成功地对图像进行阈值处理并在图像中找到边缘。我正在努力尝试准确提取黑边的角度。
我目前正在获取黑色边缘的极值点并使用 atan2 函数计算角度,但由于混叠,根据您选择的点,角度可能会出现一定程度的变化。是否有一种可靠的可编程方式来选择计算角度的点?
示例图像:

例如,Gimp Measure 工具角度为 3.12°,

如果您正在编写自己的库,那么为这个问题创建一个强大的解决方案将允许您开发几个独立的代码块,您也可以将它们串在一起来解决其他问题。我假设您想在任意旋转、不同光照条件、存在图像噪声、带有一点非线性枕形/桶形失真等情况下找到棋盘的角。
尽管有一些简单的基于内核的技术可以将整个像素作为边缘像素来查找,但在处理填充多边形时,您会希望使用能够以亚像素精度查找边缘的算法,以便您可以执行精确的线拟合。即使从暗方块到白色方块的渐变跨越了几个像素,“真实”边缘仍会在某个子像素点处找到,而且很可能不是您手动点击所猜测的点。
我试图在这篇较旧的 SO 帖子中提供边缘查找的简单摘要: 图像边缘和梯度之间的关系是什么?
对于像您这样的问题,一个可靠的解决方案是以亚像素精度沿着暗到亮过渡找到边缘点,然后将线条拟合到边缘点,并使用线条角度。如果您正在处理真实的相机图像,并且图像中存在未经校正的径向失真,则测量精度存在一些潜在问题,但我们将忽略这些问题。
如果您想找到边缘的精确拟合,那么最好在垂直于该边缘的方向上扫描子像素边缘。这假设我们开始时对边缘方向有一些合理的估计。我们可以先找到边缘方向的粗略估计,然后进行精确的线拟合。
下面的算法可能看起来步骤太多,但我的目的是指出如何提供稳健的解决方案。
然后,您将遍历 blob 列表并对每个 blob 执行以下操作:
该算法为每个黑色棋盘格独立地找到角度。对于这个应用程序来说可能有点过头了,但是如果您正在开发一个库,它可能会给您一些关于要实现哪些子算法以及如何构建它们的想法。例如,该算法将依赖于这些技术的实现:
综上所述,如果您愿意接受精度的轻微损失,并且您知道图像不会受到径向失真等的影响,并且您只需要找到由 定义的平行线的角度所有棋盘边缘,然后你可以尝试..
还有其他一些不太准确但更容易实现的技术:
等等等等。当您开发库并创建独立函数的稳健实现时,您可以将它们串在一起以创建特定于应用程序的解决方案,您可能会发现稳健的解决方案依赖的步骤比您想象的要多,但它也会更清楚每个增量步骤的故障模式是什么,以及如何解决该故障模式。