通过画线检测线
Line detection through drawn line
我需要通过在线条之间画一条线来检测线条:)
行数未知,并且因图像而异。
线条的方向也可以不同。
但是对于下面的示例,我有 6 条垂直线。
然后我想在六条线上画一条线,我画的线应该检测这些线并通过添加一个颜色的圆圈来精确定位找到的线。目标是接收一个包含找到的行的整数,以便我可以继续进行计算。
我有一个封装在 canvas 中的图像。
<Canvas x:Name="Cnv" Width="640" Height="480"
PreviewMouseUp="Image_MouseLeftButtonUp"
PreviewMouseMove="MapImg_MouseMove">
<Image x:Name="MapImg" Width="640" Height="480" Source="/images/test.png"/>
</Canvas>
我已经设法创建了函数,所以我可以画一条线,但我已经搜索了很多,试图找到检测的解决方案。我使用 AForge 框架成功检测到形状,但根据我的理解,这是针对整个图像的。
非常感谢您的帮助。
编辑:
绘制应检测线条的线条,其他线条来自图像/位图。有什么可以通过对比检测线条(检测白色)吗?
编辑 2:
用更准确的图片替换图片试图解释。
提供此类解决方案的高级概述。
首先您需要访问 pixel-Values,具体操作方式取决于您拥有的图像类型。对于 bitmapSource,推荐的方法似乎是使用 CopyPixels.
然后你需要处理沿线的每个像素。最简单的方法是将线转换为起始位置和标准化方向,并使用它沿线进行采样。假设像素坐标,类似于:
for(var d = 0; d < myLine.Length ; d++){
var samplePos = myLine.StartPosition + myLine.Direction * d;
...
}
然后可以使用此样本位置来提取该像素的值,我将假设图像是灰度图像,否则您可能想要 convert the color value。这种非常简单的方法可能会对一个像素进行多次采样,但这应该不是问题。然后,您可以使用阈值来确定像素是否是直线的一部分。一旦你找到一个足够大的像素值,你就可以保存那个位置,下次你找到一个低值时,你可以平均这些位置,return 它作为一条线的中心点。 IE。你会发现“黑色”和“白色”之间的过渡,以及两个这样的过渡的平均对。
像这样的伪代码:
int previousValue = 0;
Point startPos ;
for(var d = 0; d < myLine.Length ; d++){
var samplePos = myLine.StartPosition + myLine.Direction * d;
var pixelValue = myImage[samplePos];
if(pixelValue > myThreshold && previousValue < myThreshold){
startPos = samplePos;
}
if( pixelValue < myThreshold && previousValue > myThreshold){
yield return (startPos + samplePos)/2;
}
previousValue = pixelValue;
}
这省略了一些细节,例如如何在某个特定位置对像素值进行采样,以及您有合适的 类 来处理像素坐标和方向等。它还假设第一个像素将始终为黑色,如果不是这种情况,您可能需要一些特殊处理,具体取决于您要执行的操作。
这应该适用于像二值图像这样的情况。更高级的算法可能会更快 and/or 更好地处理有问题的情况。
我需要通过在线条之间画一条线来检测线条:)
行数未知,并且因图像而异。 线条的方向也可以不同。 但是对于下面的示例,我有 6 条垂直线。
然后我想在六条线上画一条线,我画的线应该检测这些线并通过添加一个颜色的圆圈来精确定位找到的线。目标是接收一个包含找到的行的整数,以便我可以继续进行计算。
我有一个封装在 canvas 中的图像。
<Canvas x:Name="Cnv" Width="640" Height="480"
PreviewMouseUp="Image_MouseLeftButtonUp"
PreviewMouseMove="MapImg_MouseMove">
<Image x:Name="MapImg" Width="640" Height="480" Source="/images/test.png"/>
</Canvas>
我已经设法创建了函数,所以我可以画一条线,但我已经搜索了很多,试图找到检测的解决方案。我使用 AForge 框架成功检测到形状,但根据我的理解,这是针对整个图像的。
非常感谢您的帮助。
编辑: 绘制应检测线条的线条,其他线条来自图像/位图。有什么可以通过对比检测线条(检测白色)吗?
编辑 2: 用更准确的图片替换图片试图解释。
提供此类解决方案的高级概述。
首先您需要访问 pixel-Values,具体操作方式取决于您拥有的图像类型。对于 bitmapSource,推荐的方法似乎是使用 CopyPixels.
然后你需要处理沿线的每个像素。最简单的方法是将线转换为起始位置和标准化方向,并使用它沿线进行采样。假设像素坐标,类似于:
for(var d = 0; d < myLine.Length ; d++){
var samplePos = myLine.StartPosition + myLine.Direction * d;
...
}
然后可以使用此样本位置来提取该像素的值,我将假设图像是灰度图像,否则您可能想要 convert the color value。这种非常简单的方法可能会对一个像素进行多次采样,但这应该不是问题。然后,您可以使用阈值来确定像素是否是直线的一部分。一旦你找到一个足够大的像素值,你就可以保存那个位置,下次你找到一个低值时,你可以平均这些位置,return 它作为一条线的中心点。 IE。你会发现“黑色”和“白色”之间的过渡,以及两个这样的过渡的平均对。
像这样的伪代码:
int previousValue = 0;
Point startPos ;
for(var d = 0; d < myLine.Length ; d++){
var samplePos = myLine.StartPosition + myLine.Direction * d;
var pixelValue = myImage[samplePos];
if(pixelValue > myThreshold && previousValue < myThreshold){
startPos = samplePos;
}
if( pixelValue < myThreshold && previousValue > myThreshold){
yield return (startPos + samplePos)/2;
}
previousValue = pixelValue;
}
这省略了一些细节,例如如何在某个特定位置对像素值进行采样,以及您有合适的 类 来处理像素坐标和方向等。它还假设第一个像素将始终为黑色,如果不是这种情况,您可能需要一些特殊处理,具体取决于您要执行的操作。
这应该适用于像二值图像这样的情况。更高级的算法可能会更快 and/or 更好地处理有问题的情况。