C# 如何使用FindChessboardCorners

C# 如何使用FindChessboardCorners,c#,emgucv,opencv3.0,C#,Emgucv,Opencv3.0,我正在使用新的EmguCV 3.0.0 alpha通过网络摄像头检测棋盘,并且对角点矩阵存在理解问题 Size patternSize = new Size(5, 4); Matrix<float> corners = new Matrix<float>(1, 2); bool find = CvInvoke.FindChessboardCorners(grayFrame, patternSize, corners, Ca

我正在使用新的EmguCV 3.0.0 alpha通过网络摄像头检测棋盘,并且对角点矩阵存在理解问题

        Size patternSize = new Size(5, 4);
        Matrix<float> corners = new Matrix<float>(1, 2);

        bool find = CvInvoke.FindChessboardCorners(grayFrame, patternSize, corners, CalibCbType.AdaptiveThresh | CalibCbType.FilterQuads);
        CvInvoke.DrawChessboardCorners(grayFrame, patternSize, corners, find);
        if (find)
        {
            Console.Write(corners.Size);
        }
Size patternSize=新尺寸(5,4);
矩阵角=新矩阵(1,2);
bool find=CvInvoke.FindChessboardCorners(灰框、图案大小、角点、CalibCbType.AdaptiveThresh | CalibCbType.FilterQuads);
CvInvoke.DrawChessboardCorners(灰框、图案大小、角、查找);
如果(查找)
{
控制台。写入(角落。大小);
}
棋盘将被检测并正确显示

但是,角点矩阵的大小必须有多大?如何提取角点位置

我在互联网上找到的所有样本都使用了EmguCV的旧版本,现在有了完全不同的语法。我会使用较旧的版本,但较新的alpha要快得多,而且计时是我应用程序中的一个大问题。

具有以下特征1:

第三个参数的类型为2。我不明白他们为什么引入这些超级通用的输入/输出接口,这些接口由各种不能互换使用的类实现

您是对的,该类确实实现了该接口(通过超类),因此您的代码可以编译。 但是,
CvInvoke.FindChessboardCorners
应该返回几个点(取决于模式的大小)。我在谷歌上搜索实现
IOutputArray
的类,找到了。这对我来说是有意义的,比使用
矩阵
更有意义

我拼凑了一个用于校准的小控制台应用程序,它从一个目录中读取所有图像文件并检测其中的角点,因为对我来说,事先捕获图像更有意义

这应该给你一个起点:

public class Calibration
{
    static void Main(string[] args)
    {
        // chessboard pattern size
        Size patternSize = new Size(9, 7);

        // for each image, have one Image object and one VectorOfPoints
        // for many images have a List of each
        List<VectorOfPoint> corners = new List<VectorOfPoint>();
        List<Image<Gray, Byte>> images = new List<Image<Gray, byte>>();

        // get paths to image files
        string[] imageFiles = Directory.GetFiles(@"C:\your\directory", "*.jpg");

        // for every image
        foreach (string imageFile in imageFiles)
        {
            // create new image object from file path
            var image = new Image<Gray, byte>(imageFile);
            images.Add(image);

            // create new list of corner points
            var cornerPoints = new VectorOfPoint();
            corners.Add(cornerPoints);

            // find chessboard corners
            bool result = CvInvoke.FindChessboardCorners(image, patternSize, cornerPoints);

            // some debug output
            Console.WriteLine("=== " + Path.GetFileName(imageFile) + " === " + result);

            if (!result)
            {
                continue;
            }

            // list points
            foreach (Point cornerPoint in cornerPoints.ToArray())
            {
                Console.WriteLine(cornerPoint.X + ", " + cornerPoint.Y);
            }
        }

        Console.ReadLine();
    }
}
公共类校准
{
静态void Main(字符串[]参数)
{
//棋盘图案尺寸
尺寸图案尺寸=新尺寸(9,7);
//对于每个图像,有一个图像对象和一个点矢量
//对于许多图像,每个图像都有一个列表
列表角点=新列表();
列表图像=新列表();
//获取图像文件的路径
字符串[]imageFiles=Directory.GetFiles(@“C:\your\Directory”,“*.jpg”);
//每一张图片
foreach(imageFiles中的字符串imageFile)
{
//从文件路径创建新的图像对象
var图像=新图像(图像文件);
图片。添加(图片);
//创建新的角点列表
var cornerPoints=点的新向量();
角点。添加(角点);
//寻找棋盘角
bool result=CvInvoke.FindChessboardCorners(图像、图案大小、角点);
//一些调试输出
Console.WriteLine(“==”+Path.GetFileName(imageFile)+“==”+result);
如果(!结果)
{
继续;
}
//列出要点
foreach(cornerPoints.ToArray()中的点cornerPoint)
{
控制台写入线(cornerPoint.X+“,”+cornerPoint.Y);
}
}
Console.ReadLine();
}
}
由于某种原因,我无法执行
CvInvoke.DrawChessboardCorners
。它没有在合理的时间内完成函数的执行。这就是为什么我将结果打印到
控制台
,在我看来是这样的:

我在图像编辑器中直观地验证了一些,它们似乎是正确的

tl;博士 选择一个适当的类型,该类型可以表示点列表,并实现
ioutputary
,例如
VectorOfPoints


1有人说返回类型不包含在签名中,因此将上面的签名称为签名可能完全是胡说八道,但当我说“签名”时,您仍然明白了这一点


2这是一些有用的文档

嗨,请原谅我。我是新来的。
public class Calibration
{
    static void Main(string[] args)
    {
        // chessboard pattern size
        Size patternSize = new Size(9, 7);

        // for each image, have one Image object and one VectorOfPoints
        // for many images have a List of each
        List<VectorOfPoint> corners = new List<VectorOfPoint>();
        List<Image<Gray, Byte>> images = new List<Image<Gray, byte>>();

        // get paths to image files
        string[] imageFiles = Directory.GetFiles(@"C:\your\directory", "*.jpg");

        // for every image
        foreach (string imageFile in imageFiles)
        {
            // create new image object from file path
            var image = new Image<Gray, byte>(imageFile);
            images.Add(image);

            // create new list of corner points
            var cornerPoints = new VectorOfPoint();
            corners.Add(cornerPoints);

            // find chessboard corners
            bool result = CvInvoke.FindChessboardCorners(image, patternSize, cornerPoints);

            // some debug output
            Console.WriteLine("=== " + Path.GetFileName(imageFile) + " === " + result);

            if (!result)
            {
                continue;
            }

            // list points
            foreach (Point cornerPoint in cornerPoints.ToArray())
            {
                Console.WriteLine(cornerPoint.X + ", " + cornerPoint.Y);
            }
        }

        Console.ReadLine();
    }
}