簡體   English   中英

OpenCV圈子檢測C#實現

[英]OpenCV circle detection C# implementation

我需要任何C#和/或OpenCV專家的幫助,以使我的圈子檢測腳本更加准確。

在OpenCV中,圓圈檢測是通過稱為HoughCircles算法或框架來完成的。
http://docs.opencv.org/doc/tutorials/imgproc/imgtrans/hough_circle/hough_circle.html

我正在使用OpenCV的C#包裝器(用於Unity)
OpenCVforUnity HughCircles
而這又直接基於OpenCV的官方Java包裝器。

我的圈子檢測代碼如下(當然沒有OpenCv依賴項),我還附加了2張圖像,以便您可以看到結果。 需要哪些更改來改善結果? 我還包括原始的2張圖像以供參考。

using UnityEngine;
using System.Collections;
using System;
using OpenCVForUnity;


public class HoughCircleSample : MonoBehaviour{
    Point pt;
    // Use this for initialization
    void Start ()
            {
                        Texture2D imgTexture = Resources.Load ("balls2_bw") as Texture2D;

                        Mat imgMat = new Mat (imgTexture.height, imgTexture.width, CvType.CV_8UC3);

                        Utils.texture2DToMat (imgTexture, imgMat);
                        //Debug.Log ("imgMat dst ToString " + imgMat.ToString ());

                        Mat grayMat = new Mat ();
                        Imgproc.cvtColor (imgMat, grayMat, Imgproc.COLOR_RGB2GRAY);

                        Imgproc.Canny (grayMat, grayMat, 50, 200);

                         Mat circles = new Mat();    
     int minRadius = 0;
       int maxRadius = 0;

        // Apply the Hough Transform to find the circles

        Imgproc.HoughCircles(grayMat, circles, Imgproc.CV_HOUGH_GRADIENT, 3, grayMat.rows() / 8, 200, 100, minRadius, maxRadius);

       Debug.Log ("circles toString " + circles.ToString ());
        Debug.Log ("circles dump" + circles.dump ());

        if (circles.cols() > 0)
        for (int x = 0; x < Math.Min(circles.cols(), 10); x++)

        {
                double[] vCircle = circles.get(0, x);

                if (vCircle == null)
                    break;

                pt = new Point(Math.Round(vCircle[0]), Math.Round(vCircle[1]));
                int radius = (int)Math.Round(vCircle[2]);
                // draw the found circle  
                Core.circle(imgMat, pt, radius, new Scalar(255, 0, 0), 1);

            }


 Texture2D texture = new Texture2D (imgMat.cols (), imgMat.rows (), TextureFormat.RGBA32, false);
                        Utils.matToTexture2D (imgMat, texture);

                        gameObject.GetComponent<Renderer> ().material.mainTexture = texture;

                }

        }

圓檢測樣品1

圓檢測樣品2

在此處輸入圖片說明

在此處輸入圖片說明

該代碼是C ++,但是您可以輕松轉換為C#。

我需要將HoughCircleparam2 HoughCircle為200,導致:

HoughCircles(grayMat, circles, CV_HOUGH_GRADIENT, 3, grayMat.rows / 8, 200, 200, 0, 0);

這是

圓的累加器閾值在檢測階段居中。 它越小,可能會檢測到更多的假圓圈。 與較大的累加器值相對應的圓將首先返回。

您也不應在“ HoughCircles ”中添加“ Canny-ed”圖像,因為這已經可以解決了。 使用不應用Canny邊緣檢測步驟的grayMat

結果如下所示。 由於光線條件,第二個比較棘手。

在此處輸入圖片說明

在此處輸入圖片說明

這是整個代碼。 同樣,它是C ++,但可用作參考。

#include <opencv2/opencv.hpp>
using namespace cv;

int main(){

    Mat3b src = imread("path_to_image");
    Mat1b src_gray;
    cvtColor(src, src_gray, CV_BGR2GRAY);

    vector<Vec3f> circles;
    HoughCircles(src_gray, circles, CV_HOUGH_GRADIENT, 3, src_gray.rows / 8, 200, 200, 0, 0);

    /// Draw the circles detected
    for (size_t i = 0; i < circles.size(); i++)
    {
        Point center(cvRound(circles[i][0]), cvRound(circles[i][1]));
        int radius = cvRound(circles[i][2]);
        // circle center
        circle(src, center, 3, Scalar(0, 255, 0), -1, 8, 0);
        // circle outline
        circle(src, center, radius, Scalar(0, 0, 255), 3, 8, 0);
    }

    imshow("src", src);
    waitKey();

    return 0;
}

在第四個參數中,您設置了3,但是大多數圖像的比率都接近1,這可能是一個可能的改進,還必須嘗試在參數6和7中設置另一組值,因為該值取決於Canny邊緣檢測器提取的輪廓,希望對您有所幫助。

現在,我與每個球對象有2個重疊的圓圈,彼此之間的距離越來越近。 如果我能糾正這一點,那基本上可以解決。

Imgproc.Canny (grayMat, grayMat, 500, 200);

Mat circles = new Mat();
int minRadius =50;
int maxRadius = 200;

Imgproc.HoughCircles(grayMat, circles, Imgproc.CV_HOUGH_GRADIENT, 1, grayMat.rows() / 4, 1000, 1, minRadius, maxRadius);![solution3][1]

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM