Hi, i' m a college student, and i need your help. I have some images of white dices (with black points) on red background and i need to recognize the value on visible face of dices. I tried to convert image on black-white but the result is really wrong...can someone recommend some links about those problems?
thanks!

 채택된 답변

Image Analyst
Image Analyst 2011년 6월 19일

2 개 추천

Well now that you posted an image, and I see you have black spots not only on the dice but also on the red background, I need to modify my answer to have you threshold on the blue or green channel:
clc; % Clear the command window.
close all; % Close all figures (except those of imtool.)
imtool close all; % Close all imtool figures.
clear; % Erase all existing variables.
workspace; % Make sure the workspace panel is showing.
fontSize = 20;
folder = 'C:\Documents and Settings\user\My Documents\Temporary stuff';
% Read in a color demo image.
baseFileName = 'IMG_0584.JPG';
fullFileName = fullfile(folder, baseFileName);
% Get the full filename, with path prepended.
fullFileName = fullfile(folder, baseFileName);
if ~exist(fullFileName, 'file')
% Didn't find it there. Check the search path for it.
fullFileName = baseFileName; % No path this time.
if ~exist(fullFileName, 'file')
% Still didn't find it. Alert user.
errorMessage = sprintf('Error: %s does not exist.', fullFileName);
uiwait(warndlg(errorMessage));
return;
end
end
rgbImage = imread(fullFileName);
% Get the dimensions of the image. numberOfColorBands should be = 3.
[rows columns numberOfColorBands] = size(rgbImage);
% Display the original color image.
subplot(2, 2, 1);
imshow(rgbImage, []);
title('Original color Image', 'FontSize', fontSize);
% Enlarge figure to full screen.
set(gcf, 'Position', get(0,'Screensize'));
% Extract the individual red, green, and blue color channels.
redChannel = rgbImage(:, :, 1);
greenChannel = rgbImage(:, :, 2);
blueChannel = rgbImage(:, :, 3);
spots = blueChannel < 128;
subplot(2, 2, 2);
imshow(spots, []);
title('Thresholded Blue Channel', 'FontSize', fontSize);
spots = imclearborder(spots);
subplot(2, 2, 3);
imshow(spots, []);
title('Border Cleared', 'FontSize', fontSize);
% Fill holes
spots = imfill(spots, 'holes');
subplot(2, 2, 4);
imshow(spots, []);
title('Final Spots Image', 'FontSize', fontSize);
% Count them
[labeledImage numberOfSpots] = bwlabel(spots);
message = sprintf('Done!\nThe number of spots (total on both dice) is %d', numberOfSpots);
msgbox(message);

댓글 수: 6

Ignazioc calo
Ignazioc calo 2011년 6월 19일
i'm crying ;( you solved in 10 minuts...i have spent all day...
Image Analyst
Image Analyst 2011년 6월 19일
Cheer up - in a few months or year or so from now, you'll be able to solve this in a few minutes also.
raviraja
raviraja 2013년 12월 30일
Some of functions used in the code is useful to my project thank u
Image Analyst
Image Analyst 2013년 12월 30일
raviraja, check out my File Exchange for other color segmentation applications.
Sapir
Sapir 2015년 10월 3일
I realize it's very old, but worth a shot. I'm using your algorithm to identify dots on two dice, but I'm struggling to identify how many dots in each dice. Any advice?
Image Analyst
Image Analyst 2015년 10월 3일
Advice is to post your image and code in a new question.

댓글을 달려면 로그인하십시오.

추가 답변 (1개)

Walter Roberson
Walter Roberson 2011년 6월 19일

1 개 추천

You are not clear about what "the result is really wrong" means ?
Threshold your image based upon either the blue or green channels. bwlabel() the image. regionprops() and look at the hole count of each region: it will be the number of dots (unless the shadows are fairly deep.)

댓글 수: 9

Ignazioc calo
Ignazioc calo 2011년 6월 19일
thanks four your answer and sorry for my english.
i tried this steps:
load image:
dado = imread('dado.tiff');
convert in grayscale:
dadogray = rgb2gray(dado);
found level for threshold:
level = graythresh(dadogray);
convert image in black/white
dadobw = im2bw(dadogray,level);
found region with 8-connectivity:
[labeled,numObjects] = bwlabel(dadobw,8);
but numObjects = 3...why black dot are "skipped" ?
these are two image: the original image and bw image.
wath do you mean with "Threshold your image based upon either the blue or green channels." ?? i calculate threshold level on entirely grayscale image..
thanks!
Image Analyst
Image Analyst 2011년 6월 19일
If the image is good (contiguous blobs and no spurious isolated noise pixels), you don't even need regionprops() - bwlabel() returns the number of blobs as the second (optional) output argument. You can threshold on the red channel - that way you won't have to worry about calling imclearborder.
redChannel = rgbImage(:,:,1);
spotsImage = redChannel < someThreshold;
[labeledImage numberOfSpots] = bwlabel(spotsImage);
He should post the actual image somewhere if he wants any more precise advice.
Image Analyst
Image Analyst 2011년 6월 19일
You won't get the best contrast if you convert to grayscale. You should pick one of the color channels. Post your image on your favorite free file hosting website such as tinypic.com.
Ignazioc calo
Ignazioc calo 2011년 6월 19일
thanks very much, these are three sample image:
http://dl.dropbox.com/u/792862/Archive%202.zip
i'm going to read your advices...
Image Analyst
Image Analyst 2011년 6월 19일
When you threshold like this:
dadobw = im2bw(dadogray,level);
you're getting the bright things, not the dark spots like you want. You'd have to invert your image and then possibly call imclearborder depending on if you got any of the red background with that threshold. Like I said, thresholding on the red channel would probably be best and easiest. Of course even that can have problems if you have a varying light intensity over the background.
Walter Roberson
Walter Roberson 2011년 6월 19일
If you threshold on green or blue, then you would be masking out the red background and you would detect the blue or green component that goes to make up the white. The resulting binary image would be set (logical 1) where there were die faces, so bwlabel() would label the individual faces (imagine there being more than one die in a picture.) Then the "holes" in the faces would correspond to the black dots on the faces, and counting the holes within the individual objects (which regionprops will do for you) tells you the number of pips on the face. No border clearing needed, and no confusing the red of the background with the red component of the white faces.
Ignazioc calo
Ignazioc calo 2011년 6월 19일
awesome :)
i have a last question for you...
i read documentation for regionprops() but i cannot find "hole" property...mybe i can evaluate 'area'? black dots have always the same small area...
Walter Roberson
Walter Roberson 2011년 6월 19일
Indeed, the sample pictures do turn out to have two dice -- and a number of black spots on the red background. The algorithm I suggest would not have any difficulty with the black spots on the background.
Walter Roberson
Walter Roberson 2011년 6월 19일
EulerNumber is the regionprops() value you want. It will be 0 or negative, being one (1) object minus the number of holes (dots).
Depending on how distinct the dots are and whether there is any significant noise, it is possible that you might need to use imdilate() to fill in speckles or trim irregular shadows.

댓글을 달려면 로그인하십시오.

카테고리

도움말 센터File Exchange에서 Image Processing Toolbox에 대해 자세히 알아보기

질문:

2011년 6월 19일

댓글:

2015년 10월 3일

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by