Activity 9: Binary Operations

July 17, 2008 at 11:26 am (Uncategorized) (, , , , , )

The goal of this activity is to find size of each “cell” in then image. We will be implementing the various techniques we have learned so far in solving the problem.

One of the relevant concepts that we will be implementing is the histogram thresholding to separate the background from the image. Another relevant concept is the opening and closing operations in morphological transformations. Opening is mathematically defined as

which simply means is the dilation of an erosion (see previous entry). Opening has the effect of removing small objects or noise. Closing on the other hand is defined as

which means the erosion of a dilation. It has the effect of removing small holes in the object.

The image above is divided into 9 images of size 256×256 to remove the burden of using too much memory.

My code for the activity is shown below.

getf(“imhist.sce”);
im=imread(‘circ01_01.jpg’);
stacksize(4e7);
pref=‘circ01_0’;

//create filter
se=ones(10,10);
se=mkfftfilter(se, ‘binary’, 4);

area=[];
counter=1

//scan images
for i=1:9
im=imread(strcat([pref,string(i),‘.jpg’]));
im=im2gray(im);
im=im2bw(im, 205/255);
im=erode(im, se); //opening
im=dilate(im, se);
im=dilate(im, se); //closing
im=erode(im, se);
[L,n]=bwlabel(im);
//scan regions
for j=1:n
area(counter)=length(find(L==j));
counter=counter+1;
end
end

scf(10);
histplot(length(area),area);
x=find(area<600 & area>450);
scf(11)
histplot(length(x), area(x));
a=area(x);
a=sum(a)/length(x) //area
y=stdev(area(x)) //error

The ‘pref’ variable is used to defined the prefix of the subimage, and concatenates it with a counter for loop with the 9 sub-images. We also used the ‘bwlabel’ command which looks for continuous regions in a binary image and labels them accordingly.

The histogram yields:

We can see that bwlabel has considered overlapping cells as one. However, we limit our interest to areas with less than 800 pixels  and greater than 400 pixels to increase the accuracy the calculation of the average of the cell. As can be seen below, there are regions that were labeled by bwlabel that was extremely small and some regions that were labeled were very large. Thus, setting a limit to the acceptable area is necessary.

The calculated areas is area=538.15 with std deviation of std=22.645. We are confident that this is indeed within the limits of the accepted area. To check the validity of our results, we took a subimage and calculated the area of the “cells”. The subimage that we took has completely separted cell, which ensures that the area we calculate is the area of a cell, and not the area of compounded/joint cells.

I gave myself a rating of 10 because i believe that i was able to do the activity right.

Collaborators: Cole, Julie.

Permalink Leave a Comment

Activity 4: Image Enhancement

June 26, 2008 at 11:27 am (Uncategorized) (, , )

This activity enhances images by stretching the histogram of pixel values and stretching it in such a way that the maximum is 255 and the minimum is 0. another requirement is that the image cumulative distribution function (cdf) of the pixel values becomes linear. i wrote here a simple imhist function that can be included in the directory of the source code, and calle using getf(“imhist.sce”).

here is the source code of the “imhist.sce” function i wrote:

function [val,num]=imhist(im)
val=[];
num=[];
counter=1;
for i=0:1:255
[x,y]=find(im==i); //finds where im==i
val(counter)=i;
num(counter)=length(x); //find how many pixels of im have value of i
counter=counter+1;
end
return val, num;

-oOo-

after obtaining the probability distribution function (pdf, which is a normalized histogram), we obtain the cumulative distribution function.

taken from: http://home.earthlink.net/~rogergoodman/XRay-2000-06-05-Modabber.jpg

The probability distribution function and the cumulative distribution function

image enhancement is obtained by obtaining the the values of each pixel and backprojecting. in a sense, we are simple mapping each pixel of the original image to a new array with the CDF as the mapping function.

here is the code, which implemented my own imhist function. the “imhist.sce” file is loaded within the same directory as the program below.

-oOo-

//Jeric Tugaff
//Image Enahancement

clear all;
getf(“imhist.sce”);
im=imread(“aram.jpg”); //opens a 24 bit image
im=im*255;
[val, num]=imhist(im);
[sx, sy]=size(im);
num=num/(sx*sy);
normval=val/max(val);
cumnum=cumsum(num)/max(cumsum(num));
h=scf(1);
plot(normval, num);
h=scf(2);
plot(normval, cumnum);

enhanced=[];
im=im/255;
for i=1:sx
for j=1:sy
enhanced(i,j)=cumnum(find(normval==im(i,j)));
end
end
imwrite(enhanced, “enhanced.jpg”);
enhanced=round(enhanced*255);

//hist ulit
[val, num]=imhist(enhanced);
num=num/(sx*sy);
normval=val/max(val);
cumnum=cumsum(num)/max(cumsum(num));
h=scf(3);
plot(normval, num);
h=scf(4);
plot(normval, cumnum);

-oOo-

Using any non-linear CDF

Using any non-liner CDF, we produced better images than backprojecting along a linear CDF. The flowchart of the pixel backprojecting is summarized by this image from Dr. Soriano’s lecture.

Enhanced Image using parabolic CDF

Actual and desired parabolic CDF

Again, there is good (not perfect) correspondence with the desired (smooth) and actual (jagged) CDF. Here is my code, which is quite slow but is more general especially when in cases where the inverse function of the CDF is difficult to solve analytically:

//Jeric Tugaff
//Image enhancement using parabolic CDF

clear all;
getf(“imhist.sce”);
im=imread(“aram.jpg”); //opens a 24 bit image
im=im*255;
[val, num]=imhist(im);
[sx, sy]=size(im);
num=num/(sx*sy);
normval=val/max(val);
cumnum=cumsum(num)/max(cumsum(num));
h=scf(0);
plot(val, num)

enhanced=[];
desired_cdfx=[0:1:255];
desired_cdfy=desired_cdfx.*desired_cdfx;
desired_cdfy=desired_cdfy/max(desired_cdfy);

for i=1:sx
for j=1:sy
step2(i, j)=cumnum(im(i,j));
end
end

enhanced=interp1(desired_cdfy, desired_cdfx, step2);
h=scf(1);
imshow(enhanced, [0 255]);
enhanced=round(enhanced);
//hist ulit
[val, num]=imhist(enhanced);
num=num/(sx*sy);
normval=val/max(val);
cumnum=cumsum(num)/max(cumsum(num));
h=scf(3);
plot(val, cumnum);

-oOo-

collaborators: julie, lei, cole

rating: 10, because i’ve been able to implement my own imhist function and the resulting cumulative disctribution is has good correspondence with the desired CDF. 🙂

Permalink Leave a Comment

Activity 3: Image Types and Basic Image Enhancement

June 24, 2008 at 10:30 am (Uncategorized) (, , , , )

Image Types

True Color Image

//www.flickr.com/photos/8700785@N08/643095209/

from: http://www.flickr.com/photos/8700785@N08/643095209/

FileName: truecolor.jpg
FileSize: 189687
Format: JPEG
Width: 500
Height: 493
Depth: 8
StorageType: truecolor
NumberOfColors: 0
ResolutionUnit: inch
XResolution: 72.000000
YResolution: 72.000000

Indexed Images.

indexed images parrot

from: http://en.wikipedia.org/wiki/Image:Adaptative_8bits_palette_sample_image.png

FileName: indexed.png
FileSize: 25576
Format: PNG
Width: 150
Height: 200
Depth: 8
StorageType: indexed
NumberOfColors: 256
ResolutionUnit: centimeter
XResolution: 72.000000
YResolution: 72.000000

Grayscale Image.

This is obtained by getting images from the web. However, this image is still 24 bits (which is not a property of grayscale images). To convert it to 8 bit (which is true grayscale), use the code:

im=imread(‘grayscale.jpg’);
im=im(:,:,1);
imwrite(im(:,:), ‘gs.jpg’);

//blog.paranoidferret.com/files/Tutorials/CSharp/Grayscale/bw_flower.jpg

from: http://blog.paranoidferret.com/files/Tutorials/CSharp/Grayscale/bw_flower.jpg

FileName: gs.jpg
FileSize: 9217
Format: JPEG
Width: 250
Height: 250
Depth: 8
StorageType: indexed
NumberOfColors: 256
ResolutionUnit: inch
XResolution: 72.000000
YResolution: 72.000000

Histogram and Thresholding

The histogram of the grayscale image was obtained using the following code:

//Jeric Tugaff
//Histogram

im=imread(‘grayscale.jpg’); //opens a 24 bit image
im=im(:,:,1);
imwrite(im(:,:), ‘gs.jpg’); //converts to 8 bit grayscale image
im=imread(‘gs.jpg’);
val=[];
num=[];
counter=1;
for i=0:1:255
[x,y]=find(im==i); //finds where im==i
val(counter)=i;
num(counter)=length(x); //find how many pixels of im have value of i
counter=counter+1;
end
plot(val, num); //plot. 🙂

We obtained this plot of the histogram for the image of a grayscale flower:

Grayscale image histogram

The two peaks in the histogram plot is a hint that the image is of high quality, and is good for tresholding. To do the thresholding, we use the code:

im=imread(‘gs.jpg’);
thresh=140;
im=im2bw(im, thresh/255);
imshow(im);

This results to this binary image:

Binary Image

Application To Getting Area of Images

tresholds

The images show the effect of tresholding to the leaf image. The name of the image corresponds to the treshold. We can see that the most appriate is using threshold value of 200/255. The method done in using the area follows from the previous exercise. For this activity, the area is  20108.5 while the theoretical area is  20505 with error of 1.9%.

//Jeric Tugaff
//Getting image areas through green’s theorem and grayscale image tresholding

im=imread(‘leaf_cropped.JPG’);
im=im2gray(im); //convert to grayscale
im=im2bw(im, 200/255);
im=1*(im==0); //inverts the image
[x,y]=follow(im);
x1=[];
x1(1:length(x)-1)=x(2:length(x));
x1(length(x))=x(1);
y1=[];
y1(1:length(y)-1)=y(2:length(y));
y1(length(y))=y(1);
area=0.5*abs(sum(x1.*y-y1.*x))  //green’s theorem
ta=0;
[sx, sy]=size(im);    //finds the area through recatangles
for i=1:sy
f=find(im(:, i)==1);
ta=ta+max(f)-min(f);
end
ta
err=(area-ta)/ta*100
//[r,s]=imhist(‘leaf_cropped.JPG’);

Permalink Leave a Comment