Converting array into grayscale in matlab - image

I am trying to plot a set of data in grayscale. However, the image i get seems to be always blue.
I have a set of data, albedo that ranges from [0, 0.068], which is a 1X1 double.
My code is:
for all px,py
albedoMax = 0.0679; albedoMin = 0;
out_im(px,py) = 1/(albedoMax-albedoMin)*(albedo - albedoMin);
imshow(out_im);
drawnow;
end
Basically px,py are the image coordinates that i have to iterate over, and the formula is trying to map the input range of [0, 0.068] to [0 1]. However, by running this code, i notice that the output is always blueish. I was wondering what went wrong.
Thanks for the help.

Can't you make use of the rgb2gray function?

What you are making is one layer of the RGB image.
If you are creating a homogeneous blue image with constant color then the normalization is wrong. But if it is just the matter of being blue instead of being gray then just convert it using :
ImGray = rgb2gray(Im);
Do not forget to distribute the pixels like a grid/mesh, to fill all the image not just a part of it.

Related

How to filter out the background in an RGB image(Matlab)? [duplicate]

I have converted my image into a mask and I would now like to obtain what the original colours were given this mask. I have an array called objectPixels that determines which locations belong to the object I am segmenting out. I have tried the code below but I am not obtaining the original colours.
What am I doing wring?
mask = false(size(grayImage));
mask(objectPixels) = true;
%on R channel
tmp = originalImage(:,:,1);
If I understand your question properly, you have a mask of pixels that belong to some objects. You now wish to find an image where any pixels that are labeled true will provide the original colour at these locations while false we skip. I'm going to assume that the output pixels are black if the mask locations are false. This can easily be computed using bsxfun with times as the function. We would essentially replicate the mask for each colour channel in your image, then multiply the mask with the original image.
As such:
out = bsxfun(#times, originalImage, cast(mask, class(originalImage)));
mask is originally a logical array, and in order to multiply both the mask and your original image together, they must be the same type, and that's why cast is used so that we can cast the image to the same type as the original image. We use class to determine the class or type of the original image.
As an example, let's use the onion.png image that's part of MATLAB's system path. I'm going to convert this image to grayscale using rgb2gray then choose an arbitrary threshold of graylevel 100 to give us a mask. Anything greater than 100 will give a mask value of true, while anything else is set to false.
Once I generate this mask, let's figure out what the original colours were based on these mask values. As such:
originalImage = imread('onion.png');
mask = rgb2gray(originalImage) >= 100;
out = bsxfun(#times, originalImage, cast(mask, class(originalImage)));
%// Show the images now
figure;
subplot(1,3,1);
imshow(im);
title('Original Image');
subplot(1,3,2);
imshow(mask);
title('Mask');
subplot(1,3,3);
imshow(out);
title('Output Image');
With the above code, I implement the logic I was talking about, with an additional figure that shows the original image, the mask generated as well as the output image that shows you the original colours of where the mask locations were true.
This is what I get:

How to rescale the intensity range of a grayscale 3 dimension image (x,y,z) using Matlab

I can't find information online about the intensity rescaling of a 3D image made of several 2D images.
I'm looking for the same function as imadjust which only works for 2D images.
My 3D image is the combination of 2D images stacked together but I have to process the 3D image and not the 2D images one by one.
I can't loop imadjust because I want to process the images as one, to consider all the information available, in all directions.
For applying imadjust for set of 2D grayscale images taking the whole value into account, this trick might work
a = imread('pout.tif');
a = imresize(a,[256 256]); %// re-sizing to match image b's dimension
b = imread('cameraman.tif');
Im = cat(3,a,b);
%//where a,b are separate grayscale images of same dimensions
%// if you have the images separately you could edit this line to
%// Im = cat(2,a,b);
%// and also avoid the next step
%// reshaping into a 2D matrix to apply imadjust
Im = reshape(Im,size(Im,1),[]);
out = imadjust(Im); %// applying imadjust
%// finally reshaping back to its original shape
out = reshape(out,size(a,1),size(a,2),[]);
To check:
x = out(:,:,1);
y = out(:,:,2);
As you could see from the Workspace image, the first image (variable x) is not re-scaled to 0-255 as its previous range (variable a) was not near the 0 point.
WorkSpace:
Edit: You could do this as a one-step process like this: (as the other answer suggests)
%// reshaping to single column using colon operator and then using imadjust
%// then reshaping it back
out = reshape(imadjust(Image3D(:)),size(Image3D));
Edit2:
As you have image as cell arrays in I2, try this:
I2D = cat(2,I2{:})
The only way to do this for 3D image is to treat the data as a vector and then reshape back.
Something like this:
%create a random 3D image.
x = rand(10,20,30);
%adjust intensity range
x_adj = imadjust( x(:), size(x) );

Make a representative HSV image in matlab

I want to create an HSV image (or maybe a coordinate map) which shows that coordinates accurately.
I am using the following code and get an image like this the result of the following code which is not what I want.
img = rand(200,200);
[ind_x, ind_y] = ind2sub(size(img),find(isfinite(img)));
ind_x = reshape(ind_x,size(img));
ind_y = reshape(ind_y,size(img));
ind = ind_x.*ind_y;
figure, imagesc(ind); axis equal tight xy
Lets say you quantize the HSV space (0-1) into 256 bins. There will be 256*256*256 possible colors. We could fix a dimension (say saturation) and generate the matrix. Then there will be 256*256 colors.
[x1,x2]=meshgrid(linspace(0,1,256),linspace(0,1,256));
img(:,:,1)=x1;
img(:,:,2)=1; %fully saturated colors
img(:,:,3)=x2;
imgRGB=hsv2rgb(img); %for display purposes
imshow(imgRGB,[])
It will look different in RGB (that's where you would visualize). It looks similar to your image if you visualize HSV matrix (i.e. without converting it to RGB, but MATLAB doesn't know that its HSV)
imshow(img,[]);
The second image you have posted can be obtained with:
[x1,x2]=meshgrid(linspace(0,1,256),linspace(0,1,256));
img(:,:,1)=x1;
img(:,:,2)=0;
img(:,:,3)=x2;
imshow(img,[]) %visualizing HSV

Given a mask, how do I get obtain the original colors of an image?

I have converted my image into a mask and I would now like to obtain what the original colours were given this mask. I have an array called objectPixels that determines which locations belong to the object I am segmenting out. I have tried the code below but I am not obtaining the original colours.
What am I doing wring?
mask = false(size(grayImage));
mask(objectPixels) = true;
%on R channel
tmp = originalImage(:,:,1);
If I understand your question properly, you have a mask of pixels that belong to some objects. You now wish to find an image where any pixels that are labeled true will provide the original colour at these locations while false we skip. I'm going to assume that the output pixels are black if the mask locations are false. This can easily be computed using bsxfun with times as the function. We would essentially replicate the mask for each colour channel in your image, then multiply the mask with the original image.
As such:
out = bsxfun(#times, originalImage, cast(mask, class(originalImage)));
mask is originally a logical array, and in order to multiply both the mask and your original image together, they must be the same type, and that's why cast is used so that we can cast the image to the same type as the original image. We use class to determine the class or type of the original image.
As an example, let's use the onion.png image that's part of MATLAB's system path. I'm going to convert this image to grayscale using rgb2gray then choose an arbitrary threshold of graylevel 100 to give us a mask. Anything greater than 100 will give a mask value of true, while anything else is set to false.
Once I generate this mask, let's figure out what the original colours were based on these mask values. As such:
originalImage = imread('onion.png');
mask = rgb2gray(originalImage) >= 100;
out = bsxfun(#times, originalImage, cast(mask, class(originalImage)));
%// Show the images now
figure;
subplot(1,3,1);
imshow(im);
title('Original Image');
subplot(1,3,2);
imshow(mask);
title('Mask');
subplot(1,3,3);
imshow(out);
title('Output Image');
With the above code, I implement the logic I was talking about, with an additional figure that shows the original image, the mask generated as well as the output image that shows you the original colours of where the mask locations were true.
This is what I get:

Extracting numerical data from an intensity printout

I'm looking to create an intensity matrix in Matlab from an intensity image plot (saved as a jpeg (RGB) file) that was made using what appears to be the jet colormap from Matlab. I am essentially trying to reverse engineer the numerical data from the plot. The original image along with the color bar is linked (I do not have enough reputation to insert images).
http://i.imgur.com/BmryO6W.png
I initially thought this could be done with the rgb2gray command, but it produces the following image with the jet colormap applied which does not match the original image.
http://i.imgur.com/RlBei2z.png
As far as I can tell, the only route available from here is to try matching the RGB value for each pixel to a value in the colormap lookup table. Any suggestions on if this the fastest approach?
It looks like your method using rgb2gray is almost working, apart from the scale. Because the colormap is scaled automatically to the contents of your plot, I think you will have to re-scale it manually (unless you can automatically detect the tick labels on the colorbar). You can do this using the following formula:
% Some random data like yours
x = rand(1000) * 256;
% Scale data to fit your range
xRange = [min(x(:)) max(x(:))];
scaleRange = [-10 10];
y = (x - xRange(1)) * diff(scaleRange) / diff(xRange) + scaleRange(1);
You can check the operation's success with
>> [min(y(:)) max(y(:))]
ans =
-10 10

Resources