
% LOAD IN tilt RESULTS and MEX %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
clear; close all; 
load 'nlf'; 
mex Ctransform.c; 
mex Clearn.c;   
mex Cfind.c;   
mex Ccopy.c; 
mex Cmax.c; 

% CONSTANTS %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
epsilon = .1;  % allowed correlation between selected Gabors
sub = 2;    % subsampling rate for Gabor
Lrange = 3; % allowed shifting in location (times sub pixels)
Orange = 1; % allowed shifting in orientation
SHUTUP = 1.; % SHUTUP is to neglect the positions with low average responses               
binnum = 50; % number of bins 
nstep = 3;  % number of iterations
Totalsketch = 50;  % allowed number of selected Gabors   
sub1 = 2; Lrange1 = 3; 
% sub1 = 1; Lrange1 = 6; 

% FILTER %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
C = corr(allfilter, epsilon);    % generate the inhibition maps

% TRAINING IMAGES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
fold = .5; 
Folder = 'bike';  % image input folder
Iname = dir([Folder '\*.jpg']);
nimage = size(Iname, 1);
for (i = 1 : nimage)
    J{i} = imresize(double(rgb2gray(imread([Folder '\' Iname(i).name]))), fold, 'nearest');
    [sx1, sy1] = size(J{i}); 
    Sx(i) = sx1; Sy(i) = sy1; % sizes of images
end
[sx0 sy0] = size(J{1}); 
ax = sx0; ay = sy0; 
Sx0 = zeros(1, nimage) + sx0; 
Sy0 = zeros(1, nimage) + sy0; 
for (i = 1 : nimage)
    for (o = 1 : norient)
        allfiltered{i, o} = zeros(sx0, sy0); 
    end
end

% VARIABLES FOR MEX-C %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
Mi = zeros(1, Totalsketch);  % orientation of selected Gabor
Mx = zeros(1, Totalsketch);  % position of selected Gabor
My = zeros(1, Totalsketch); 
Mm = zeros(1, Totalsketch);  % lambda
Mm1 = zeros(1, Totalsketch);  % logZ
sym = zeros(sx0, sy0);  % symbolic plot of selected Gabor
Asym = cell(1, nimage);   % symbolic plot for each image with active Gabor
for (i = 1 : nimage)
    Asym{i} = zeros(sx0, sy0);  
end

% START FROM SINGLE IMAGE LEARNING %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
I0{1} = J{1}; 
nimage0 = 1; Lrange0 = 0; Orange0 = 0; 
allfiltered0 = applyfilterfftsame(I0, allfilter); 
allfiltered00 = applyfilterfftsame(I0, allfilter); 
Asym0{1} = zeros(sx0, sy0);
Ctransform(nimage0, norient, allfiltered0, Sx0, Sy0, Upperbound);
Ctransform(nimage0, norient, allfiltered00, Sx0, Sy0, Upperbound);
disp(['start from single image learning']);
tic
Clearn(nimage0, norient, allfiltered0, C, h, sx0, sy0, Mi, Mx, My, Mm, Mm1, allsymbol(1, :), sym, Asym0, Lrange0, Orange0, sub, Totalsketch, Upperbound, SHUTUP, binnum, M, lam, e, lz);
disp(['mex-C learning time: ' num2str(toc) ' seconds']);
outepsgif(-sym, 'ex5c_bike_sym0'); 


% TRAINING IMAGES AT DIFFERENT SCALES %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
totalScale0 = 7;  % total number of scales
totalStretch = 1;
totalScale = totalScale0*totalStretch; 
ax = sx0; ay = sy0; 
Sxx = zeros(nimage, totalScale); Sxa = zeros(1, totalScale*nimage); 
Syy = zeros(nimage, totalScale); Sya = zeros(1, totalScale*nimage); 
mscale = zeros(nimage, totalScale);  % log-likelihood score over scales
JJ = cell(1, totalScale*nimage); 
tss1 = cell(1, totalScale*nimage); 
sym1 = cell(1, totalScale*nimage); 

for (i = 1:nimage)
 for (j0=1:totalStretch)
  for(j1=1:totalScale0)
    j = j0+(j1-1)*totalStretch; 
    scaleF = .6+(j1-1)*.1; 
    stretchF = 1. + (j0-1)*.4;  
    [sx00 sy00] = size(J{i}); 
    JJ{(i-1)*totalScale+j} = imresize(J{i},[round(sx00*scaleF) round(sy00*scaleF*stretchF)], 'nearest');  % scaled images
    [sx1, sy1] = size(JJ{(i-1)*totalScale+j}); 
    Sxx(i, j) = sx1; Syy(i, j) = sy1; % sizes of images
    Sxa((i-1)*totalScale+j) = sx1; Sya((i-1)*totalScale+j) = sy1; 
    tss1{(i-1)*totalScale+j} = zeros(sx1+ax, sy1+ay);  % log-likelihood score map for testing images
    sym1{(i-1)*totalScale+j} = zeros(sx1, sy1);  % symbolic sketch on testing image
  end
 end
end

disp(['start filtering training images at all scales']);
tic
allfiltered1 = applyfilterfft(JJ, allfilter);  % filter training images
disp(['filtering time: ' num2str(toc) ' seconds']);

Ctransform(totalScale*nimage, norient, allfiltered1, Sxa, Sya, Upperbound);
allmaxed = cell(totalScale*nimage, norient);
for (i = 1:totalScale*nimage)
    for (o = 1:norient)
        allmaxed{i, o} = allfiltered1{i, o} + 0.; 
    end
end

Cmax(totalScale*nimage, norient, allmaxed, Sxa, Sya, Lrange1, Orange, sub1);

% ITERATE DETECTION AND LEARNING %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
for(it = 1:nstep)
    disp(['detection for step ' num2str(it)]);
    for (i=2:nimage)
        disp(['    start detecting in image ' num2str(i)]);
        tic
        msci = zeros(1, totalScale); Fx = zeros(1, totalScale); Fy = zeros(1, totalScale); 
        Sxi = Sxx(i, :); Syi = Syy(i, :); 
        Cfind(i, nimage, totalScale, norient, allfiltered1, allmaxed, h, ax, ay, Mi, Mx, My, Mm, Mm1, allsymbol(1, :), Lrange1, Orange, sub1, Totalsketch, Upperbound, tss1, sym1, Sxi, Syi, msci, Fx, Fy);
        disp(['    mex-C detection time: ' num2str(toc) ' seconds']);

        maxscale = max(msci);   % most likely scale
        for(j=1:totalScale)
            if(msci(j)==maxscale)
               Jshow{i} = JJ{(i-1)*totalScale+j}+sym1{(i-1)*totalScale+j}*100.;  % overlaid sketch 
               for (o = 1 : norient)
                   Ccopy(allfiltered{i, o}, allfiltered1{(i-1)*totalScale+j, o}, floor(Fx(j)+.5), floor(Fy(j)+.5), sx0, sy0, Sxi(j), Syi(j)); 
               end
            end
        end
    end
    for (o = 1 : norient)
       Ccopy(allfiltered{1, o}, allfiltered00{1, o}, 0, 0, sx0, sy0, sx0, sy0); 
    end

    disp(['multiple image learning for step ' num2str(it)]);
    tic
    Clearn(nimage, norient, allfiltered, C, h, sx0, sy0, Mi, Mx, My, Mm, Mm1, allsymbol(1, :), sym, Asym, Lrange, Orange, sub, Totalsketch, Upperbound, SHUTUP, binnum, M, lam, e, lz);
    disp(['mex-C learning time: ' num2str(toc) ' seconds']);
    outepsgif(-sym, ['ex5c_bike_sym' num2str(it)]); 
end

Jshow{1} = J{1}+Asym{1}*100.; 
outepsgif(-sym, 'ex5c_bike_symfinal'); 
for(i=1:nimage)
       outepsgif(Jshow{i}, ['ex5c_bike' num2str(i)]);  % overlaid sketch 
end

save 'model' norient h sx0 sy0 Mi Mx My Mm Mm1 allfilter allsymbol Lrange Orange sub Totalsketch Upperbound M sub1 Lrange1 SHUTUP ax ay fold totalScale0;
