% SelfSupAM_DiagnosisMovies.m
%       Creates movie animations of medical diangosis illustration.
%
%   Greg Amis
%   Technology Lab
%   Dept. of Cognitive & Neural Systems
%   Boston University
%   26 March 2009
%
%   Licensing Policy
%   This implementation is made available to the general public under the terms 
%   of Copyleft, as defined by the <a href="http://www.fsf.org/">Free Software Foundation</a> 
%   (see discussion <a href="http://www.gnu.org/copyleft/copyleft.html">here</a> for example). 
%   As such, it is available free of charge, and may be copied, redistributed, or modified, 
%   as long as any resulting work is distributed under the same terms of
%   Copyleft.

%% Init
overlap = 0.7;
Nstage1 = 50; 
Nstage2 = 10000; 
Ntest   = 5000;
seed = 1827;
L = 3;

rand('state',1827);

%Prep data
[inputs,labels] = create_diagnosis_data( ceil(Nstage1+Nstage2)*4/3, overlap );
randOrder = randperm(length(labels));
inputs = inputs(:,randOrder);
labels = labels(randOrder);

SelfSupAM_loadJava();
stage1Training = edu.bu.cns.data.LabeledInputsImpl(...
    [inputs(1,1:Nstage1)',NaN(Nstage1,1)], int32(labels(1:Nstage1)-1), L );
stage2Training = edu.bu.cns.data.InputsImpl(inputs(:,Nstage1+1:Nstage1+Nstage2)');
    
[testInputs,testLabels] = create_diagnosis_data(Ntest,overlap);
[ X, Y ] = meshgrid(linspace(0,1,100));
gridInputs = edu.bu.cns.data.InputsImpl( [ X(:), Y(:) ] );

am = SelfSupAM_createInstance( 'E2',1, 'V',1, 'M',2, 'L',L );
am.setUp();

f = figure('Position',[420 549 458 399],'DoubleBuffer','on'); 
hold on;
axis square; 
axis( repmat([-0.1 1.1],1,2) );
set(gca,'FontSize',10,...
    'XTick',[ 0 1 ],'XTickLabel','low|high',...
    'YTick',[ 0 1 ],'YTickLabel','none|shock');
xlabel('temperature','FontSize',12,'FontAngle','italic');
ylabel('shock','FontSize',12,'FontAngle','italic');
title({'Category boxes and classification pattern after';...
       '### Stage 1 points (Test Accuracy =##%)'},...
            'FontSize',12,'FontWeight','bold');

aviDir = [ getenv('userprofile'), '\Desktop\' ];

%% Stage 1
fn = [aviDir,'Stage1.avi'];
clear aviobj;
if exist(fn,'file'), delete(fn); end;

aviobj = avifile(fn, 'fps',3, 'compression','none');
am.resetLearning();

for n = 1:Nstage1
    
    am.trainStage1(stage1Training.get(n-1));
    
    gridPreds = am.test(gridInputs)' + 1;
    testAccuracy = round(100*mean(SelfSupAM_test(am,testInputs)==testLabels));
        
    cla;
    SelfSupAM_plot2D(am,gridPreds);
    a = stage1Training.get(n-1).features;
    p = plot(a([1 1]),[-.05,1.05],'m','LineWidth',2);
        
    title({'Category boxes and classification pattern after';...
            sprintf('%d Stage 1 points (Test Accuracy = %d%%)',n,testAccuracy)},...
            'FontSize',12,'FontWeight','bold');

 	aviobj = addframe(aviobj,gca);
    
end; %for n

aviobj = close(aviobj);
clear aviobj;

delete(p);
frame = getframe(gcf);
[frameCdata,frameMap] = rgb2ind(frame.cdata,256);
imwrite(frameCdata,frameMap,'D:\Working\Publications\SelfSupARTMAP\www\demo\Stage1.gif');


%% Stage 2
fn = [aviDir,'Stage2.avi'];
if exist('aviobj','var'), close(aviobj); end;
if exist(fn,'file'), delete(fn); end;

aviobj = avifile(fn, 'fps',15, 'compression','none');
am.resetLearning();
am.trainStage1(stage1Training);

for n = 1:5000
    
    am.trainStage2(stage2Training.get(n-1));
    
    gridPreds = am.test(gridInputs)' + 1;
    testAccuracy = round(100*mean(SelfSupAM_test(am,testInputs)==testLabels));
        
    cla;
    SelfSupAM_plot2D(am,gridPreds);
    a = stage2Training.get(n-1).features;
    p = plot(a(1),a(2),'m*','MarkerSize',8);
        
    title({'Category boxes and classification pattern after';...
            sprintf('%d Stage 1 and %d Stage 2 points (Test Accuracy = %d%%)',...
                    Nstage1, n, testAccuracy ) },...
            'FontSize',12,'FontWeight','bold');
    aviobj = addframe(aviobj,gca);
    
end; %for n

aviobj = close(aviobj);
clear aviobj;

delete(p);
frame = getframe(gcf);
[frameCdata,frameMap] = rgb2ind(frame.cdata,256);
imwrite(frameCdata,frameMap,'D:\Working\Publications\SelfSupARTMAP\www\demo\Stage2.gif');


