function PMsvystup = filtracePMs(PMsvstup, filtrovat, minvzdal, pocetprimek)
% funkce pro odstraneni nezadoucich bodu PM z PM matice. Nezadouci body
% predstavuji takove body PM, ktere s nejvetsi pravdepodobnosti dle sve podstaty nemohou
% lezet na hranici optickeho disku

% VSTUP:
% - PMsvstup - vstupni matice bodu PM
% - filtrovat - promenna slouzici k zapinani a vypinani filtrace - pokud je
%   rovna 1, filtrace bodu PM je aktivni a body oznacene jako neplatne jsou
%   odstraneny. Pokud je promenna rovna 0, k filtraci nedochazi. V tom pripade jsou potencialni neplatne body PM jen oznaceny
% - minvzdal - minimalni vzdalenost od centralniho pixelu, ve ktere
%   dochazelo k prohledavani vstupniho obrazu. Slouzi pro nevypinatelnou
%   filtraci, ktera odstranuje neplatne body PM nalezene v minimalni
%   vzdalenosti
% - pocetprimek - pocet radialnich primek kterymi byl vstupni obraz prohledavan

% VYSTUP:
% - PMsvystup - vystupni matice bodu PM. Na rozdil od vstupu obsahuje navic
%   dalsi sloupec. Sesty sloupec - index znacici platny nebo neplatny bod PM.
%   Pokud je index roven 1, byl bod PM vyhodnocen jako platny. Pokud je index
%   roven 0, byl bod PM vyhodnocen jako neplatny a pokud je aktivni volba
%   filtrace, je nasledne odstranen.



    PMsvystup = PMsvstup;   % pracujeme s vystupni matici
    PMsvystup(PMsvystup(:,4) == minvzdal,:) = [];     % smazani radku, ve kterych doslo k nalezeni maximalni variace v minimalni vzdalenosti (ochrana proti cernym oblastem obrazu)

    if filtrovat == 1       % pokud je zapnuta volba filtrace, pak filtrujeme
       PMsvystup(PMsvystup(:,3)<=0,:)=[];    % odstraneni řádků (bodů PM) s negativni a nulovou hodnotou variace
    %  PMsvystup(PMsvystup(:,3)<0,:)=[];     % odstraneni řádků pouze s negativni hodnotou variace
    end
    

    
    global h;
    waitbar(0, h,'Filtruji...');             % inicializace waitbaru
    delit = round(size(PMsvystup,1)/30);     % pomocna promenna pro waitbar
    
    
    pom = 1;    % pomocna promenna
    pom2= PMsvystup(1,2);  % pomocna promenna
    vektvzdal = inf(1,pocetprimek);        % inicializace vektoru vzdalenosti z duvodu zrychleni nasledujiciho cyklu
                                           % pouzito inf, protoze zeros nebo ones by teoreticky mohlo ovlivnovat vysledky
                                           
    
    for i = 1:size(PMsvystup,1)   % cyklus pro vypocet prahu a filtraci bodu PMS na zaklade jejich vzdalenosti

           if pom2 == PMsvystup(i,2)          % nacitame body PM, dokud odpovidaji jednomu centralnimu pixelu (z duvodu predchozi filtrace na zaporne variace a minimalni vzdalenosti nelze udelat cyklus efektivneji)
                vektvzdal(pom)=PMsvystup(i,4) ;  % vektor vzdalenosti pro jeden centralni bod
                pom = pom+1;
                
           else                               % jakmile jsou nacteny vsechny body PM pro jeden centralni pixel
                vektvzdal(vektvzdal == Inf) = [];    % odstraneni prebytecnych inicializacnich hodnot ve vektoru (ovlivnovaly by vypocty)
               
                medikk = median(vektvzdal);      % je spocitan median jejich vzdalenosti od centralniho pixelu
                Td = median(abs(vektvzdal-medikk));     % vypocet prahove hodnoty pro filtraci bodu PM
                
                korekce = ceil(medikk/10);         % korekce prahu - prah samotny je dosti prisny a propousti jen tvary velmi podobne kruznici je tedy mozne udelat prah vice benevolentni
                %korekce = floor(medikk/10);        % v pripade korekce je vsak mozne ze bude hranice mene presna kvuli falesnym bodum PM, u nekruhovych OD vsak bude hranice lepe odpovidat skutecne hranici
                %korekce = round(medikk/5);         % korekce take muze ovlivnit uspesnost detekce OD. Jde o kompromis.
                %korekce = 0;                        
                
                odchylka = abs(vektvzdal - medikk);     % odchylka vzdalenosti bodu PM od medianu vzdalenosti vsech bodu PM od centralniho pixelu
                zachovat = odchylka <= (Td+korekce);           % pokud je odchylka vzdalenosti daneho bodu PM mensi nez spocteny prah, pak bod zustane zachovan (body s log. 0 budou nasledne odstraneny)
                PMsvystup(i-length(vektvzdal):i-1,6) = zachovat;  % prirazeni platnosti (log. 0 nebo log. 1) ke vsem bodum PM - vytvoreni 6. sloupce v matici PMs

                vektvzdal = inf(1,pocetprimek);             % inicializace vektoru vzdalenosti pro dalsi iteraci
                vektvzdal(1) = PMsvystup(i,4);   % napleni vektoru prvni hodnotou, ktera by se jinak ztratila (byla by preskocena)
                
                pom = 2;                % nastaveni pomocneho indexu
                pom2 = PMsvystup(i,2);        % nastaveni nove podminky pro pridavani bodu PM do vektvzdal vzdalenosti
           end  
           
        if rem(i,delit) == 0
            waitbar(i/(size(PMsvystup,1)));
        end
    end
    %close(h);
    % -------- nutne pro doplneni posledni iterace, ktera  by neprobehla (za poslednim radkem vektvzdal PMs nedochazi ke zmene souradnice, proto nedojde ke skoku do druhe vetve podminky)
        vektvzdal(vektvzdal == Inf) = [];
    
        medikk = median(vektvzdal);
        Td = median(abs(vektvzdal-medikk)); 
        
     
                korekce = ceil(medikk/10);
                %korekce = floor(medikk/10);        
                %korekce = round(medikk/5);         
                %korekce = 0;

        odchylka = abs(vektvzdal - medikk);     
        zachovat = odchylka <= (Td+korekce);         
        PMsvystup(i-length(vektvzdal):i-1,6) = zachovat;
    % --------------

    if filtrovat == 1           % pokud je zapnuta volba filtrace, pak filtrujeme
        PMsvystup(PMsvystup(:,6)==0,:)=[];      % odstraneni bodu PM s vysokou odchylkou vzdalenosti    
    end

end