The Art of Image Contouring
27 October 2023

The Art of Image Contouring

No, not the art of changing your face shape with makeup. We’re trying to find the shapes in our object and draw around them. Why contouring? Finding shapes in an image is paramount for motion tracking, image identification, background removal. Many image manipulation processes start with contouring.

We’re specifically going to be using the Evision library for Elixir for this post, but the basics will apply to any language/library combo you may be using for contouring.

Finding contours themselves is fairly easy and can be done with one function.

 {contours, _} =
    Evision.findContours(
        image,
        Evision.Constant.cv_RETR_LIST(),
        Evision.Constant.cv_CHAIN_APPROX_NONE()
    )

This function takes several arguments. First is the image we are contouring, second is the way we want the data to be stored, and last is whether we want the contours to use approximation.

How to Store Our Contours

Let’s talk about these variables and what they mean. First let’s look closer at the way we want the data to be stored. We’re going to be using the following image to show how this variable affects our results:

Image of shapes containing other shapes with shape C and D inside shape B and shape B in shape A Next to shape A is another shape E containg shape F

In the code above we are using a list. This is the fastest way to store our contours, but it contains the least amount of information about our original image. If we are interested in each contour but not their relation to each other, this is the best method for us.

Our results would look something like: [A, B, C, D, E, F]

But there are many other options depending on the use case. Another option is Evision.Constant.RETR_EXTERNAL. This will only return the contours of outer most objects. Any objects that are contained within another object will not be returned. In the case of our image we would get back [A, E].

Another option is Evision.Constant.RETR_TREE. This will return all the contours and will have them sorted by their parent child relationships. So for out example we’d get

Image showing a tree with A and E in a list at the top. A list containing B is the child of A. This list has a child list containing C and D. A list containing F is the child of E.

The final is Evision.Constant.CV_RETR_CCOMP. This spits contours into two categories: inner and outer contours. This is mainly used if you are looking for “holes” in the image. So we would get [A, E] [B, C ,D, F].

Applying Approximation

Our second variable is the approximation for our contours. To show what these options will do we’ll look at this complicated object.

Image of a rectangle with small and large indents cut out of the sides

In the above code we used Evision.Constant.CV_CHAIN_APPROX_NONE which means we do not want to see every point in our image. Our contour list will include every point.

The retangle has all corners tracked including the indents

Another option is chain approximation simple, which will only return the main corners. This is useful to remove any unintended breaks in an image. So our resulting points would be:

Rectangle with only the main four corners tracked

The Evision.Constant.CHAIN_APPROX_TC89_KCOS Evision.Constant.CHAIN_APPROX_TC89_L1 and options both use the slightly different versions of the Teh-Chin algorithm to calculate an approximation of the object that will try to eliminate small discrepancies. So we would get something like:

Rectangle with main four corners tracked and large indents tracked, but small indents ignored

Final Thoughts

Calculating contours is a simple process, but involves a lot of thought about what the use case for the contours are. Are the objects simple or complex? Is there one object with holes and discrepancies or multiple objects? If there are multiple objects are all of them significant or just the outer objects? Also is the hierarchy relevant? Contouring provides a lot of flexibility for different use cases when it comes to object detection. If you’re interested in learning about more manipulation techniques and how to more accurately detect contours in an image, check out this video of my talk:

Motion Commotion: Motion Tracking with Bumblebee and LiveView

Related Posts

Want to learn more about the work we do?

Explore our work

Ready to start your software journey with us?

Contact Us