% Photometric Stereo

% Required:
% 1. Derive (ie., fill in the missing steps) the expression for 
%     photometric stereo that I have given you.
% 2. Fill in the computation in this code and hand in the program.
% 3. Compute the albedo and surface normals.
% 4. Print out and hand in the plot of Albedo (figure 2) and surface normals
%     (figure 3).

% Input images (convert from uint8 to double on reading)
I1=double(imread('photo-im1.tif','tiff'));
I2=double(imread('photo-im2.tif','tiff'));
I3=double(imread('photo-im3.tif','tiff'));
figure(1);
subplot(3,1,1);
imshow(I1,[0 255]);
subplot(3,1,2);
imshow(I2,[0 255]);
subplot(3,1,3);
imshow(I3,[0 255]);

% Camera positions
s1=[0,0,1];
s2=[-1,1,2];
s3=[1,0,3];

% Use formulas (Horn, page 230) to recover surface normal and albedo at
%  each point.
% Fill in your code here!
% Return albedo, R(1:256,1:256) (albedo at each point)
%  and surface normals Nx, Ny, Nz
%  (each is 256x256 image with x, y, and z comp of normal vector, respectively)








% Plot image of recovered albedo
figure;
imshow(R,[]);
title('albedo');

% Surface normals Nx, Ny, Nz should be same as original surface: Sx, Sy, Sz
% Plot (p',q'), the recovered surface gradient.
figure(3);
X=ones(256,1)*[0:255];
Y=[0:255]'*ones(1,256);
dx=Nx./Nz;
dy=Ny./Nz;
quiver(X(1:16:256,1:16:256),Y(1:16:256,1:16:256), ...
       dx(1:16:256,1:16:256),dy(1:16:256,1:16:256));
axis([0 256 0 256]);
title('recovered normals');
