Why is the whole picture turning red? - image

We’ve been trying to fix this program for hours, yet nothing seems to work, we just can’t figure out what the problem is. It is supposed to make the whole picture black white, besides the red pixels. (https://imgur.com/a/gxRm3N1 should look like that afterwards)
Here is the result after the using the program, the whole picture is turning red:
https://imgur.com/a/yWYVoIx
How can I fix this?
from image_helper import *
img = load_rgb_image("ara.jpg")
w, h = img.size
pixels = load_rgb_pixels("ara.jpg")
#img.show()
for i in range(w*h):
r,g,b = pixels[i]
new_r = 2*r
new_g = g // 2
new_b = b + 10
pixels[i] = (new_r, new_g, new_b)
new_img = new_rgb_image(w, h, pixels)
new_img.show()

There is an excellent solution implemented in MATLAB.
I was tempting to translate the code from MATLAB to Python (using OpenCV).
Convert the image to HSV color space.
Select "non-red" pixels. In HSV color space, the first channel is the hue - there is a range of hue for pixels that considered to be red.
Set the selected pixel saturation channel to 0. (Pixels with zero saturation are gray).
Convert the image back from HSV to BGR color space.
Here is the Python code (conversation of the original MATLAB code):
import cv2
# The following code is a Python conversion to the following MATLAB code:
# Original MATLAB code: https://stackoverflow.com/questions/4063965/how-can-i-convert-an-rgb-image-to-grayscale-but-keep-one-color
img = cv2.imread('roses.jpg') # Load image.
hsv = cv2.cvtColor(img, cv2.COLOR_BGR2HSV) # Convert the image to HSV color space.
h = hsv[:, :, 0] # Note: in OpenCV hue range is [0,179]) The original MATLAB code is 360.*hsvImage(:, :, 1), when hue range is [0, 1].
s = hsv[:, :, 1] # Get the saturation plane.
non_red_idx = (h > 20//2) & (h < 340//2) # Select "non-red" pixels (divide the original MATLAB values by 2 due to the range differences).
s[non_red_idx] = 0 # Set the selected pixel saturations to 0.
hsv[:, :, 1] = s # Update the saturation plane.
new_img = cv2.cvtColor(hsv, cv2.COLOR_HSV2BGR) # Convert the image back to BGR space
# Show images for testing:
cv2.imshow('img', img)
cv2.imshow('new_img', new_img)
cv2.waitKey()
cv2.destroyAllWindows()
cv2.imwrite('new_img.jpg', new_img)
Result:
Notes:
For the method used for selecting the color range, refer to the original post.
The reference post has a simpler solution, using simple for loop (with inferior results), that more resembles your code.
Consider using this code as reference.

Related

When decoding a jpeg how would I reverse chrominance downsampling in matlab?

Hi trying to make a simple jpeg compressor which also decompresses the image. I use the following code to downsample the chrominance of an image for the first step of jpeg compression.
resampler = vision.ChromaResampler;
[Cb, Cr] = resampler(Cb_channel, Cr_channel);
the function is part of the computer vision toolbox for matlab.
for example before downsampling:
Y dimensions = 3024 by 4032;
Cb and Cr dimensions = 3024 by 4032
after downsampling:
Y dimensions = 3024 by 4032;
Cb and Cr dimensions = 3024 by 2016
to display the original RGB image after decompression, the dimensions of all 3 Y, Cb and Cr components need to be the same so that I can merge the channels and convert the image back to RGB. I'm using the following code to achieve this:
Cb_resized = imresize(Cb, [(size(Cb, 1)) (2*size(Cb, 2))]);
Cr_resized = imresize(Cr, [(size(Cr, 1)) (2*size(Cr, 2))]);
When I then merge the 3 channels and use imshow() to see the image it looks fine. So is the above method the correct way of reversing the downsampled chrominance when decoding a jpeg?
Using imresize for up-sampling is "almost correct".
Instead of using imresize, you better use vision.ChromaResampler for up-sampling:
up_resampler = vision.ChromaResampler();
up_resampler.Resampling = '4:2:2 to 4:4:4';
[Cb_resized, Cr_resized] = up_resampler(Cb, Cr);
The module is design such that Resampling = '4:2:2 to 4:4:4' "reverses" the result of Resampling = '4:4:4 to 4:2:2'.
The '4:4:4 to 4:2:2' ChromaResampler uses a convention that displaces the result 0.5 pixels to the right.
(I think shifting by 0.5 pixels supposes to match MPEG-1 codec standard).
The 0.5 displacement is not well documented - I had to build a short test for figuring it out.
As far as I remember, the convention of moving 0.5 a pixel is used by MPEG-1 codec, but not used by MPEG-2 and newer codecs.
I don't think it is used by JPEG, but I am not sure...
Note:
Since the human visual system is not very sensitive to the Chroma resolution, you are probably not going to see the differences if 0.5 displacement is used or not.
For getting the same result as ChromaResampler, you may use imwarp, with displacement of 1 pixel in the horizontal axis.
Understanding imwarp is a little complicated.
I am going to use imwarp for demonstrating that 1 pixel displacement, gives the same result as ChromaResampler:
The following code sample shows the equivalence:
close all
I = imread('peppers.png'); % Read sample image
YUV = rgb2ycbcr(I); % Convert RGB to Y:Cb:Cr
U = YUV(:, :, 2); % Get U color channel
V = YUV(:, :, 3); % Get V color channel
down_resampler = vision.ChromaResampler(); % 4:4:4 to 4:2:2
down_resampler.Resampling = '4:4:4 to 4:2:2';
up_resampler = vision.ChromaResampler(); % 4:2:2 to 4:4:4
up_resampler.Resampling = '4:2:2 to 4:4:4';
% Down-sample U and V using ChromaResampler
[downU, downV] = down_resampler(U, V);
%downU2 = imresize(U, [size(U, 1), size(U, 2)/2]); % Not the same as using imresize
%figure;imshow(downU);figure;imshow(downU2);
% Up-sample downU and downV using ChromaResampler
[upU, upV] = up_resampler(downU, downV);
% Result is not the same as using imresize
%resizedU = imresize(downU, [size(downU, 1), size(downU, 2)*2], 'bilinear');
%resizedV = imresize(downV, [size(downV, 1), size(downV, 2)*2], 'bilinear');
% Use transformation matrix that resize horizontally by x2 and include single pixel horizontal displacement.
tform = affine2d([ 2 0 0
0 1 0
-1 0 1]);
% Use imwarp instead of imresize (the warp includes horizontal displacement of 1 pixel)
warpU = imwarp(downU, tform, 'bilinear', 'OutputView', imref2d([size(downU, 1), size(downU, 2)*2]));
warpU(:, end) = warpU(:, end-1); % Fill the last column by duplication
%figure;imagesc(double(upU) - double(resizedU));impixelinfo
%figure;imshow(upU);figure;imshow(resizedU);
%figure;imshow(upU);figure;imshow(warpU);
% Show the differences:
figure;imagesc(double(upU) - double(warpU));title('Diff');impixelinfo
max_abs_diff = max(imabsdiff(warpU(:), upU(:)));
disp(['max_abs_diff = ', num2str(max_abs_diff)]); % Maximum absolute differenced is 1 (due to rounding).
Note: The imresize usage is kept in comments.
Note:
The default interpolation method of imresize is cubic interpolation, and the default interpolation method of ChromaResampler is linear interpolation.
Cubic interpolation is considered superior, but linear interpolation is commonly used (the visible difference is negligible).

Convert matlab.graphics.primitive.Image (output of imagesc) to rgb array

I'm using the MATLAB function
imagesc(my_gray_valued_image)
to visualize my_gray_valued_image: [1024x1024] double array with values from 0.0 - 1.0 (gray values) using colormaps like jet.
I want to store the output as a RGB image ([1024x1024x3] double array). However the output of the function is a Image object (matlab.graphics.primitive.Image) that contains the original array (Image.CData) but doesn't allow to extract the colorscaled image.
Following a similar (although confusingly cluttered) question (How to convert an indexed image to rgb image in MATLAB?) I tried the following, but that gave me a plain blue image:
RGB = ind2rgb(my_gray_valued_image, jet);
imshow(RGB);
here for arbitrary colormap:
im = rand(5); % input [0-1] image
figure;
h = imagesc(im); % imagesc handle
title('imagesc output')
cdata = h.CData; % get image data (if you don't have variable 'im')
cm = colormap(h.Parent); % get axes colormap
n = size(cm,1); % number of colors in colormap
c = linspace(h.Parent.CLim(1),h.Parent.CLim(2),n); % intensity range
ind = reshape(interp1(c,1:n,im(:),'nearest'),size(im)); % indexed image
rgb = ind2rgb(ind,cm); % rgb image
figure;
imshow(rgb,'InitialMagnification','fit');
title('rgb image')
You can use ind2rgb to convert an intensity image into RGB using a colormap of your choice; but make sure that the range of the input is from 1 to the number of colors in the colormap. This is because ind2rgb maps value 1 to the first color, 2 to the second etc.
im = rand(5,5); % example intensity image
cmap = jet(256); % desired colormap
result = ind2rgb(ceil(size(cmap,1)*im), cmap);
The reason why you are getting a blue image is that ind2rgb clips the values of the input image to the range from 1 to the number of colors in the colormap. So, if the input image has values between 0 and 1 they are all mapped to 1, that is, to the first color in the colormap.

To convert only black color to white in Matlab

I know this thread about converting black color to white and white to black simultaneously.
I would like to convert only black to white.
I know this thread about doing this what I am asking but I do not understand what goes wrong.
Picture
Code
rgbImage = imread('ecg.png');
grayImage = rgb2gray(rgbImage); % for non-indexed images
level = graythresh(grayImage); % threshold for converting image to binary,
binaryImage = im2bw(grayImage, level);
% Extract the individual red, green, and blue color channels.
redChannel = rgbImage(:, :, 1);
greenChannel = rgbImage(:, :, 2);
blueChannel = rgbImage(:, :, 3);
% Make the black parts pure red.
redChannel(~binaryImage) = 255;
greenChannel(~binaryImage) = 0;
blueChannel(~binaryImage) = 0;
% Now recombine to form the output image.
rgbImageOut = cat(3, redChannel, greenChannel, blueChannel);
imshow(rgbImageOut);
Which gives
Where seems to be something wrong in red color channel.
The Black color is just (0,0,0) in RGB so its removal should mean to turn every (0,0,0) pixel to white (255,255,255).
Doing this idea with
redChannel(~binaryImage) = 255;
greenChannel(~binaryImage) = 255;
blueChannel(~binaryImage) = 255;
Gives
So I must have misunderstood something in Matlab. The blue color should not have any black. So this last image is strange.
How can you turn only black color to white?
I want to keep the blue color of the ECG.
If I understand you properly, you want to extract out the blue ECG plot while removing the text and axes. The best way to do that would be to examine the HSV colour space of the image. The HSV colour space is great for discerning colours just like the way humans do. We can clearly see that there are two distinct colours in the image.
We can convert the image to HSV using rgb2hsv and we can examine the components separately. The hue component represents the dominant colour of the pixel, the saturation denotes the purity or how much white light there is in the pixel and the value represents the intensity or strength of the pixel.
Try visualizing each channel doing:
im = imread('http://i.stack.imgur.com/cFOSp.png'); %// Read in your image
hsv = rgb2hsv(im);
figure;
subplot(1,3,1); imshow(hsv(:,:,1)); title('Hue');
subplot(1,3,2); imshow(hsv(:,:,2)); title('Saturation');
subplot(1,3,3); imshow(hsv(:,:,3)); title('Value');
Hmm... well the hue and saturation don't help us at all. It's telling us the dominant colour and saturation are the same... but what sets them apart is the value. If you take a look at the image on the right, we can tell them apart by the strength of the colour itself. So what it's telling us is that the "black" pixels are actually blue but with almost no strength associated to it.
We can actually use this to our advantage. Any pixels whose values are above a certain value are the values we want to keep.
Try setting a threshold... something like 0.75. MATLAB's dynamic range of the HSV values are from [0-1], so:
mask = hsv(:,:,3) > 0.75;
When we threshold the value component, this is what we get:
There's obviously a bit of quantization noise... especially around the axes and font. What I'm going to do next is perform a morphological erosion so that I can eliminate the quantization noise that's around each of the numbers and the axes. I'm going to make it the mask a bit large to ensure that I remove this noise. Using the image processing toolbox:
se = strel('square', 5);
mask_erode = imerode(mask, se);
We get this:
Great, so what I'm going to do now is make a copy of your original image, then set any pixel that is black from the mask I derived (above) to white in the final image. All of the other pixels should remain intact. This way, we can remove any text and the axes seen in your image:
im_final = im;
mask_final = repmat(mask_erode, [1 1 3]);
im_final(~mask_final) = 255;
I need to replicate the mask in the third dimension because this is a colour image and I need to set each channel to 255 simultaneously in the same spatial locations.
When I do that, this is what I get:
Now you'll notice that there are gaps in the graph.... which is to be expected due to quantization noise. We can do something further by converting this image to grayscale and thresholding the image, then filling joining the edges together by a morphological dilation. This is safe because we have already eliminated the axies and text. We can then use this as a mask to index into the original image to obtain our final graph.
Something like this:
im2 = rgb2gray(im_final);
thresh = im2 < 200;
se = strel('line', 10, 90);
im_dilate = imdilate(thresh, se);
mask2 = repmat(im_dilate, [1 1 3]);
im_final_final = 255*ones(size(im), class(im));
im_final_final(mask2) = im(mask2);
I threshold the previous image that we got without the text and axes after I convert it to grayscale, and then I perform dilation with a line structuring element that is 90 degrees in order to connect those lines that were originally disconnected. This thresholded image will contain the pixels that we ultimately need to sample from the original image so that we can get the graph data we need.
I then take this mask, replicate it, make a completely white image and then sample from the original image and place the locations we want from the original image in the white image.
This is our final image:
Very nice! I had to do all of that image processing because your image basically has quantization noise to begin with, so it's going to be a bit harder to get the graph entirely. Ander Biguri in his answer explained in more detail about colour quantization noise so certainly check out his post for more details.
However, as a qualitative measure, we can subtract this image from the original image and see what is remaining:
imshow(rgb2gray(abs(double(im) - double(im_final_final))));
We get:
So it looks like the axes and text are removed fine, but there are some traces in the graph that we didn't capture from the original image and that makes sense. It all has to do with the proper thresholds you want to select in order to get the graph data. There are some trouble spots near the beginning of the graph, and that's probably due to the morphological processing that I did. This image you provided is quite tricky with the quantization noise, so it's going to be very difficult to get a perfect result. Also, these thresholds unfortunately are all heuristic, so play around with the thresholds until you get something that agrees with you.
Good luck!
What's the problem?
You want to detect all black parts of the image, but they are not really black
Example:
Your idea (or your code):
You first binarize the image, selecting the pixels that ARE something against the pixels that are not. In short, you do: if pixel>level; pixel is something
Therefore there is a small misconception you have here! when you write
% Make the black parts pure red.
it should read
% Make every pixel that is something (not background) pure red.
Therefore, when you do
redChannel(~binaryImage) = 255;
greenChannel(~binaryImage) = 255;
blueChannel(~binaryImage) = 255;
You are doing
% Make every pixel that is something (not background) white
% (or what it is the same in this case, delete them).
Therefore what you should get is a completely white image. The image is not completely white because there has been some pixels that were labelled as "not something, part of the background" by the value of level, in case of your image around 0.6.
A solution that one could think of is manually setting the level to 0.05 or similar, so only black pixels will be selected in the gray to binary threholding. But this will not work 100%, as you can see, the numbers have some very "no-black" values.
How would I try to solve the problem:
I would try to find the colour you want, extract just that colour from the image, and then delete outliers.
Extract blue using HSV (I believe I answered you somewhere else how to use HSV).
rgbImage = imread('ecg.png');
hsvImage=rgb2hsv(rgbImage);
I=rgbImage;
R=I(:,:,1);
G=I(:,:,2);
B=I(:,:,3);
th=0.1;
R((hsvImage(:,:,1)>(280/360))|(hsvImage(:,:,1)<(200/360)))=255;
G((hsvImage(:,:,1)>(280/360))|(hsvImage(:,:,1)<(200/360)))=255;
B((hsvImage(:,:,1)>(280/360))|(hsvImage(:,:,1)<(200/360)))=255;
I2= cat(3, R, G, B);
imshow(I2)
Once here we would like to get the biggest blue part, and that would be our signal. Therefore the best approach seems to first binarize the image taking all blue pixels
% Binarize image, getting all the pixels that are "blue"
bw=im2bw(rgb2gray(I2),0.9999);
And then using bwlabel, label all the independent pixel "islands".
% Label each "blob"
lbl=bwlabel(~bw);
The label most repeated will be the signal. So we find it and separate the background from the signal using that label.
% Find the blob with the highes amount of data. That will be your signal.
r=histc(lbl(:),1:max(lbl(:)));
[~,idxmax]=max(r);
% Profit!
signal=rgbImage;
signal(repmat((lbl~=idxmax),[1 1 3]))=255;
background=rgbImage;
background(repmat((lbl==idxmax),[1 1 3]))=255;
Here there is a plot with the signal, background and difference (using the same equation as #rayryang used)
Here is a variation on #rayryeng's solution to extract the blue signal:
%// retrieve picture
imgRGB = imread('http://i.stack.imgur.com/cFOSp.png');
%// detect axis lines and labels
imgHSV = rgb2hsv(imgRGB);
BW = (imgHSV(:,:,3) < 1);
BW = imclose(imclose(BW, strel('line',40,0)), strel('line',10,90));
%// clear those masked pixels by setting them to background white color
imgRGB2 = imgRGB;
imgRGB2(repmat(BW,[1 1 3])) = 255;
%// show extracted signal
imshow(imgRGB2)
To get a better view, here is the detected mask overlayed on top of the original image (I'm using imoverlay function from the File Exchange):
figure
imshow(imoverlay(imgRGB, BW, uint8([255,0,0])))
Here is a code for this:
rgbImage = imread('ecg.png');
redChannel = rgbImage(:, :, 1);
greenChannel = rgbImage(:, :, 2);
blueChannel = rgbImage(:, :, 3);
black = ~redChannel&~greenChannel&~blueChannel;
redChannel(black) = 255;
greenChannel(black) = 255;
blueChannel(black) = 255;
rgbImageOut = cat(3, redChannel, greenChannel, blueChannel);
imshow(rgbImageOut);
black is the area containing the black pixels. These pixels are set to white in each color channel.
In your code you use a threshold and a grayscale image so of course you have much bigger area of pixels that is set to white resp. red color. In this code only pixel that contain absolutly no red, green and blue are set to white.
The following code does the same with a threshold for each color channel:
rgbImage = imread('ecg.png');
redChannel = rgbImage(:, :, 1);
greenChannel = rgbImage(:, :, 2);
blueChannel = rgbImage(:, :, 3);
black = (redChannel<150)&(greenChannel<150)&(blueChannel<150);
redChannel(black) = 255;
greenChannel(black) = 255;
blueChannel(black) = 255;
rgbImageOut = cat(3, redChannel, greenChannel, blueChannel);
imshow(rgbImageOut);

converting rgb image to double and keeping the values in matlab

I have an image and I want to import this image to matlab. I am using the following code. The problem that I have is that when I convert the image to grayscale, everything will be changed and the converted image is not similar to original one. In another words, I want to keep the values (or let say the image) as it is in the original image. Is there any way for doing this?
I = imread('myimage.png');
figure, imagesc(I), axis equal tight xy
I2 = rgb2gray(I);
figure, imagesc(I2), axis equal tight xy
Your original image is already using a jet colormap. The problem is, when you convert it to grayscale, you lose some crucial information. See the image below.
In the original image you have a heatmap. Blue areas generally indicate "low value", whereas red areas indicate "high values". But when converted to grayscale, both areas indicate low value, as they aproach dark pixels (see the arrows).
A possible solution is this:
You take every pixel of your image, find the nearest (closest)
color value in the jet colormap and use its index as a gray value.
I will show you first the final code and the results. The explanation goes below:
I = im2double(imread('myimage.png'));
map = jet(256);
Irgb = reshape(I, size(I, 1) * size(I, 2), 3);
Igray = zeros(size(I, 1), size(I, 2), 'uint8');
for ii = 1:size(Irgb, 1)
[~, idx] = min(sum((bsxfun(#minus, Irgb(ii, :), map)) .^ 2, 2));
Igray(ii) = idx - 1;
end
clear Irgb;
subplot(2,1,1), imagesc(I), axis equal tight xy
subplot(2,1,2), imagesc(Igray), axis equal tight xy
Result:
>> whos I Igray
Name Size Bytes Class Attributes
I 110x339x3 894960 double
Igray 110x339 37290 uint8
Explanation:
First, you get the jet colormap, like this:
map = jet(256);
It will return a 256x3 colormap with the possible colors on the jet palette, where each row is a RGB pixel. map(1,:) would be kind of a dark blue, and map(256,:) would be kind of a dark red, as expected.
Then, you do this:
Irgb = reshape(I, size(I, 1) * size(I, 2), 3);
... to turn your 110x339x3 image into a 37290x3 matrix, where each row is a RGB pixel.
Now, for each pixel, you take the Euclidean distance of that pixel to the map pixels. You take the index of the nearest one and use it as a gray value. The minus one (-1) is because the index is in the range 1..256, but a gray value is in the range 0..255.
Note: the Euclidean distance takes a square root at the end, but since we are just trying to find the closest value, there is no need to do so.
EDIT:
Here is a 10x faster version of the code:
I = im2double(imread('myimage.png'));
map = jet(256);
[C, ~, IC] = unique(reshape(I, size(I, 1) * size(I, 2), 3), 'rows');
equiv = zeros(size(C, 1), 1, 'uint8');
for ii = 1:numel(equiv)
[~, idx] = min(sum((bsxfun(#minus, C(ii, :), map)) .^ 2, 2));
equiv(ii) = idx - 1;
end
Irgb = reshape(equiv(IC), size(I, 1), size(I, 2));
Irgb = Irgb(end:-1:1,:);
clear equiv C IC;
It runs faster because it exploits the fact that the colors on your image are restricted to the colors in the jet palette. Then, it counts the unique colors and only match them to the palette values. With fewer pixels to match, the algorithm runs much faster. Here are the times:
Before:
Elapsed time is 0.619049 seconds.
After:
Elapsed time is 0.061778 seconds.
In the second image, you're using the default colormap, i.e. jet. If you want grayscale, then try using colormap(gray).

How to remove non-barcode region in an image? - MATLAB

After I did a 'imclearborder', there are still a bit of unwanted object around the barcode. How can I remove those objects to isolate the barcode? I have pasted my code for your reference.
rgb = imread('barcode2.jpg');
% Resize Image
rgb = imresize(rgb,0.33);
figure(),imshow(rgb);
% Convert from RGB to Gray
Igray = double(rgb2gray(rgb));
% Calculate the Gradients
[dIx, dIy] = gradient(Igray);
B = abs(dIx) - abs(dIy);
% Low-Pass Filtering
H = fspecial('gaussian', 20, 10);
C = imfilter(B, H);
C = imclearborder(C);
figure(),imagesc(C);colorbar;
Well, i have already explained it in your previous question How to find the location of red region in an image using MATLAB? , but with a opencv code and output images.
Instead of asking for code, try to implement it yourself.
Below is what to do next.
1) convert image 'C' in your code to binary.
2) Apply some erosion to remove small noises.( this time, barcode region also shrinks)
3) Apply dilation to compensate previous erosion.(most of noise will have removed in previous erosion. So they won't come back)
4) Find contours in the image.
5) Find their area. Most probably, contour which has maximum area will be the barcode, because other things like letters, words etc will be small ( you can understand it in the grayscale image you have provided)
6) Select contour with max. area. Draw a bounding rectangle for it.
Its result is already provided in your previous question. It works very nice. Try to implement it yourself with help of MATLAB documentation. Come here only when you get an error which you don't understand.
%%hi, i am ading my code to yours at the end of your code%%%%
clear all;
rgb = imread('barcode.jpeg');
% Resize Image
rgb = imresize(rgb,0.33);
figure(),imshow(rgb);
% Convert from RGB to Gray
Igray = double(rgb2gray(rgb));
Igrayc = Igray;
% Calculate the Gradients
[dIx, dIy] = gradient(Igray);
B = abs(dIx) - abs(dIy);
% Low-Pass Filtering
H = fspecial('gaussian', 10, 5);
C = imfilter(B, H);
C = imclearborder(C);
imshow(Igray,[]);
figure(),imagesc(C);colorbar;
%%%%%%%%%%%%%%%%%%%%%%%%from here my code starts%%%%%%%%%%%%%%%%
bw = im2bw(C);%%%binarising the image
% imshow(bw);
%%%%if there are letters or any other noise is present around the barcode
%%Note: the size of the noise and letters should be smaller than the
%%barcode size
labelImage = bwlabel(bw,8);
len=0;labe=0;
for i=1:max(max(labelImage))
a = find(labelImage==i);
if(len<length(a))
len=length(a);
labe=i;
end
end
imag = zeros(size(l));
imag(find(labelImage==labe))=255;
% imtool(imag);
%%%if Necessary do errossion
% se2 = strel('line',10,0);
% imag= imerode(imag,se2);
% imag= imerode(imag,se2);
[r c]= find(imag==255);
minr = min(r);
maxc = max(c);
minc = min(c);
maxr = max(r);
imag1 = zeros(size(l));
for i=minr:maxr
for j=minc:maxc
imag1(i,j)=255;
end
end
% figure,imtool(imag1);
varit = find(imag1==0);
Igrayc(varit)=0;
%%%%%result image having only barcode
imshow(Igrayc,[]);
%%%%%original image
figure(),imshow(Igray,[]);
Hope it is useful

Resources