function OD = ODmapa(PMs, radkuvstupnihoobr, sloupcuvstupnihoobr, pocetprimek, zvyhodnovat)
% funkce pro tvorbu ODmapy a nalezeni optickeho disku v obraze (respektive nalezeni bodu PM odpovidajicich optickemu disku). 
% ODmapa je sedotonovy obraz o stejnych rozmerech jako vstupni obraz, ktery nejjasnejsim
% bodem reprezentuje stred optickeho disku.
%
%
% VSTUP:
% - PMs - matice obsahujici vsechny potrebne informace o kazdem tzv. bode PM. Bod PM je bod, ve kterem podel jedne radialni primky doslo k nejvetsi
%   zmene jasu. V jednotlivych radcich jsou jednotlive body PM.
% - radkuvstupnihoobr -  pocet radku vstupniho obrazu - nutne pro korektni inicializaci OD mapy
% - sloupcuvstupnihoobr - pocet sloupcu vstupniho obrzu - nutne pro korektni inicializaci OD mapy
% - pocetprimek - pocet radialnich primek kterymi byl vstupni obraz prohledavan
% - zvyhodnovat - promenna nesouci informaci o tom, zda zvyhodnovat hrany s
%   vysokym gradientem, nebo ponechat vsem hranam stejnou vahu

% VYSTUP:
% - OD - vystupni OD matice, ktera obsahuje body PM (body odpovidajici hranici OD) nalezeneho optickeho disku.
%   Matice obsahuje vsechny potrebne informace k lokalizaci a vykresleni hranic optickeho disku



    mapa = zeros(radkuvstupnihoobr, sloupcuvstupnihoobr);     % inicializace mapy


    pom = 1;    % pomocna promenna
    pom2= PMs(1,2);     % pomocna promenna 
    variacevekt = inf(1,pocetprimek);   % inicializace vektoru - zrychleni smycky (nelze pouzit zeros ani ones, protoze by mohly ovlivnit vysledky)
    vzdalenosti = inf(1,pocetprimek);   % inicializace vektoru - zrychleni smycky (nelze pouzit zeros ani ones, protoze by mohly ovlivnit vysledky)
    
    global h;
    waitbar(0, h, 'Tvorba OD mapy...');             % inicializace waitbaru
    delit = round(size(PMs,1)/30);
    
    for i = 1:size(PMs,1);      % naplneni mapy
        if pom2 == PMs(i,2)     % nacitame body PM, dokud odpovidaji jednomu centralnimu pixelu (nelze udelat efektivneji, protoze po filtraci ma kazdy bod v obraze rozdilny pocet bodu PM)
                variacevekt(pom)=PMs(i,3);  % vektor varianci pro jeden centralni bod
                vzdalenosti(pom)=PMs(i,4);  % vektor vzdalenosti pro jeden centralni bod

                pom = pom+1;            
        else                    % jakmile jsou nacteny vsechny body PM pro jeden centralni pixel
            variacevekt(variacevekt == Inf) = [];   % odstraneni prebytecnych inicializacnich hodnot ve vektoru (ovlivnovaly by vypocty)
            vzdalenosti(vzdalenosti == Inf) = [];   % odstraneni prebytecnych inicializacnich hodnot ve vektoru 
            
            stredhod = mean(vzdalenosti);       % spocteme stredni hodnotu jejich vzdalenosti 
            rozdil = vzdalenosti - stredhod;    % nasledne jejich odchylky od teto stredni vzdalenosti
            rozdil = rozdil.^2;                 % umocnime
            suma = sum(rozdil);                 % a spocteme sumu techto umocnenych odchylek
            jmenovatel = sqrt(suma);            % jmenovatel reprezentuje smerodatnou odchylku vzdalenosti 
            
            if ((jmenovatel ~= 0) && length(variacevekt)>(pocetprimek/4))   % v OD mape zustane pixel cerny, pokud nesplnuje tyto podminky (jinak je zde riziko saturace v OD mape a nekorektnost)
                if zvyhodnovat == 1
                    citatel = sum(variacevekt);   %------------------------------ zvyhodnuje hrany s vetsim gradientem 
                else                    
                    citatel = length(variacevekt); %------------------------------ vsechny hrany maji stejnou vahu
                end

                mapa(PMs(i-length(variacevekt):i-1,1),PMs(i-length(variacevekt):i-1,2)) = citatel/jmenovatel; % vypocet jednoho pixelu OD mapy
            end
            
            variacevekt = inf(1,pocetprimek);             % inicializace vektoru pro dalsi iteraci
            variacevekt(1) = PMs(i,3);   % napleni vektoru prvni hodnotou nasledujici iterace, ktera by byla jinak ztracena
            vzdalenosti = inf(1,pocetprimek);             % inicializace vektoru pro dalsi iteraci
            vzdalenosti(1) = PMs(i,4);   % napleni vektoru prvni hodnotou nasledujici iterace, ktera by byla jinak ztracena

            pom = 2;                % nastaveni pomocneho indexu
            pom2 = PMs(i,2);        % nastaveni nove podminky        
        end
        
        if rem(i,delit) == 0
            waitbar(i/(size(PMs,1)));
        end
    end    
    close(h);
    
% -------- nutne pro doplneni posledni iterace, ktera  by neprobehla (za poslednim radkem matice PMs nedochazi ke zmene souradnice, proto nedojde ke skoku do druhe vetve podminky)
        variacevekt(variacevekt == Inf) = [];
        vzdalenosti(vzdalenosti == Inf) = [];

        stredhod = mean(vzdalenosti);
        rozdil = vzdalenosti - stredhod;
        rozdil = rozdil.^2;
        suma = sum(rozdil);
        jmenovatel = sqrt(suma);
        
        if ((jmenovatel ~= 0) && length(variacevekt)>(pocetprimek/4) )
            if zvyhodnovat == 1
                citatel = sum(variacevekt);   %------------------------------- zvyhodnuje hrany s vetsim gradientem 
            else
                citatel = length(variacevekt); %------------------------------- vsechny hrany maji stejnou vahu
            end

            mapa(PMs(i-length(variacevekt):i-1,1),PMs(i-length(variacevekt):i-1,2)) = citatel/jmenovatel;
        end
% ------------------------------
     
%      figure
%      imshow(mapa, [])

     
     [num, idx] = max(mapa(:));         % zjisteni maximalni hodnoty v mape
     [rad, sloup] = ind2sub(size(mapa),idx); % nalezeni pozice maxima

     OD = PMs(PMs(:,1) == rad,:);    % do matice OD ulozime hodnoty, u kterych se v prvnim sloupci PMs nachazi hodnota nalezeneho maxima 
     OD(OD(:,2)~= sloup,:) = [];   % dale z OD odstranime hodnoty, u kterych se ve druhem sloupci nenachazi hodnota sloup a tak ziskame matici pouze s hodnotami vysledneho OD
    
end

