Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Image segmentation by background color - OpenCV Android

Tags:

android

opencv

I'm trying to segment business cards and split them by background color to treat them as different regions of interest.

For example a card of this sort: Sample business card

should be able to be to be split into two images as there are 2 background colors. Are there any suggestions on how to tackle this? I've tried doing some contour analysis which didn't turn out too successful.

Other example cards: enter image description here

This card should give 3 segmentations, as there are three portions even though it's only 2 colors (though 2 colors will be okay).

enter image description here

The above card should give just one segmentation as it is just one background color.

I'm not trying to think of gradient backgrounds just yet.

like image 952
SalGad Avatar asked Jan 08 '13 18:01

SalGad


1 Answers

It depends on how the other cards look, but if the images all are in that great quality, it should not be too hard.

In the example you posted, you could just collect the colors of the border pixels (most left column, most right column, first row, last row) and treat what you find as possible background colors. Perhaps check if there are enough pixels with roughly the same color. You need some kind of distance measuring. One easy solution is to just use the euclidean distance in RGB color space.

A more generic solution would be to find clusters in the color histograms of the whole image and treat every color (again with tolerance) that has more than x% of the overall pixel amount as a background color. But what you define as background depends on what you want to achieve and how your images look.

If you need further suggestions, you could post more images and tag what parts of the images you want to be detected as a background color and what parst not.

-

Edit: Your two new images also show the same pattern. Background colors occupy a big part of the image, there is no noise and there are no color gradients. So a simple approach could look like the following:

  • Calculate the histogram of the image: see http://docs.opencv.org/modules/imgproc/doc/histograms.html#calchist and http://docs.opencv.org/doc/tutorials/imgproc/histograms/histogram_calculation/histogram_calculation.html

  • Find the most prominent colors in the histogram. If you do not want to iterate over the Mat yourself you can use minMaxLoc ( http://docs.opencv.org/modules/core/doc/operations_on_arrays.html#minmaxloc) as shown in the calchist documentation (see above), and if the color takes up enough percentage of the pixel count save it and set the according bin in the histogram to zero. Repeat until your percentage is not reached any more. You will then have saved a list of the most prominent colors, your background colors.

  • Threshold the image for every background color you have. See: http://docs.opencv.org/doc/tutorials/imgproc/threshold/threshold.html

  • On the resulting threadholded images find the corresponding region to every background color. See: http://docs.opencv.org/doc/tutorials/imgproc/shapedescriptors/find_contours/find_contours.html

If you have examples that do not work with this approach, just post them.

like image 69
Tobias Hermann Avatar answered Nov 02 '22 01:11

Tobias Hermann