hybridgroup / gocv

Go package for computer vision using OpenCV 4 and beyond. Includes support for DNN, CUDA, and OpenCV Contrib.
https://gocv.io
Other
6.42k stars 853 forks source link

cannot range over contours (variable of type gocv.PointsVector) #1135

Open liushuai05 opened 6 months ago

liushuai05 commented 6 months ago

Description

When I use gocv.FindContours to get content and traverse through the error: cannot range over contours (variable of type gocv.PointsVector)

I am a beginner, I am very sorry, this problem may be related to my lack of experience, my need is to find a card in a low contrast reading picture (membership card or other cards can be), and then cut out to generate a new picture, but I have been stuck in the contour line to obtain, hope to get help from the big guys, thank you very much.

Steps to Reproduce

1.Here's my code

    package main

    import (
     "fmt"
     "image"
     "image/color"

     "gocv.io/x/gocv"
    )

    func main() { 
     filename := "./input.jpg"
     window := gocv.NewWindow("Hello")
     img := gocv.IMRead(filename, gocv.IMReadColor)
     grayImage := gocv.NewMat()
     defer grayImage.Close()

     gocv.CvtColor(img, &grayImage, gocv.ColorBGRToGray)
     destImage := gocv.NewMat()
     gocv.Threshold(grayImage, &destImage, 100, 255, gocv.ThresholdBinaryInv)
     resultImage := gocv.NewMatWithSize(500, 400, gocv.MatTypeCV8U)

     gocv.Resize(destImage, &resultImage, image.Pt(resultImage.Rows(), resultImage.Cols()), 0, 0, gocv.InterpolationCubic)
     gocv.Dilate(resultImage, &resultImage, gocv.NewMat())
     gocv.GaussianBlur(resultImage, &resultImage, image.Pt(5, 5), 0, 0, gocv.BorderWrap)
     imageForShowing := gocv.NewMatWithSize(resultImage.Rows(), resultImage.Cols(), gocv.MatChannels4)

        contours := gocv.FindContours(resultImage, gocv.RetrievalExternal, gocv.ChainApproxSimple) 
        for index, element := range contours { 
     fmt.Println(index)
     gocv.DrawContours(&imageForShowing, contours, index, color.RGBA{R: 0, G: 0, B: 255, A: 255}, 1)
     gocv.Rectangle(&imageForShowing,
     gocv.BoundingRect(element),
     color.RGBA{R: 0, G: 255, B: 0, A: 100}, 1)
     }

     if img.Empty() {
     fmt.Println("Error reading image from: %v", filename)
     return
     }

     for {
     window.IMShow(imageForShowing)
     if window.WaitKey(1) >= 0 {
     break
     }
     }
    }

Your Environment

marrasen commented 6 months ago

Use contours.Size() to iterate using a standard for loop

for i := 0; i < contours.Size(); i++ {
}

Then you can draw each contour. You can also get a PointVector using contours.At(i) which then also has a Size() and an At() function to get individual coordinates.