Code covered by the BSD License  

Highlights from
Aztec barcode reader

image thumbnail

Aztec barcode reader

by

 

This program can read Aztec barcode from video or pictures. It is partial in Dutch

[rij_ascii errorc]=function_aztec_reader(B, hoekmax)
function [rij_ascii errorc]=function_aztec_reader(B, hoekmax) 
%deze barcode reader is geschikt voor zowel de grote als de kleine versie
%van aztec code. Gemaakt voor Project F 2009 door C. ten Hove. Voor vragen
%c.h.tenhove@student.utwente.nl. Deze functie reader is gespecialiseerd in
%video beelden.


%Roteren van het plaatje
if hoekmax>0
    BW = edge(B,'log');
    t =[(-hoekmax):hoekmax (90-hoekmax):(90+hoekmax)];
    R= radon(BW,t);
    [R locatie]=sort(R,'descend');
    [a hoek1]=max(sum(R(1:15,1:(hoekmax*2+1))));
    [a hoek90]=max(sum(R(1:15,(hoekmax*2+2):end)));
    hoek=floor((t(hoek1)+t(hoek90+hoekmax*2+1)-90)/2);
    B=imrotate(B,-hoek);
end
afmetingenB=size(B);
x=afmetingenB(2);
y=afmetingenB(1);


%schitteringen eruit halen en randen van rotatie wegwerken
gem=mean(mean(B));

    for a=1:y
        for b=1:x
            if ((B(a,b)==0) || (B(a,b)>1.6*gem))
                B(a,b)=gem;
            end
        end
    end


%Met bovenstaande gegevens kijken wat betere instellingen zijn
afstanden1=sort(locatie(1:30,hoek1)); 
afstanden2=sort(locatie(1:30,hoek90+hoekmax*2+1));
verschil=[];
for a=1:29
    verschil1= afstanden1(a+1,1)-afstanden1(a,1);
    verschil2= afstanden2(a+1,1)-afstanden2(a,1);
    if verschil1>1
        verschil=[verschil verschil1];
    end
    if verschil2>1
        verschil=[verschil verschil2];
    end
end
afstand=floor(median(verschil)/2)+1;
detail2=floor(afstand/3)+1;
detail=floor(y/15)+1;

%afstand=5; detail2=2; detail=17;
%afbeelding bijsnijden als er te weinig verandering op een lijn is

[snijden H1 V1]=bijsnijden(B,x,y,afstand);
B=B(snijden(1):snijden(2),snijden(3):snijden(4));

%omzetten in zwart/wit afbeelding

afmetingenB=size(B);
yb=afmetingenB(1);
xb=afmetingenB(2);

for a=1:yb
    for b=1:xb
        if B(a,b)<=gem %*0.97
            A(a,b)=0;
        else
            A(a,b)=1;
        end
    end
end


%afmetingen van A bepalen
afmetingen2=size(A);
y2=afmetingen2(1);
x2=afmetingen2(2);

%lijnen scannen om het raster te bepalen----------------
[horizontaal verticaal]=raster(A,x2,y2,afstand,detail,detail2);

%filteren lijnen

h=size(horizontaal);
v=size(verticaal);
a=1;
horizontaal1=[];
verticaal1=[];
vorige=0; %deze is 1 als er de vorige keer een gemiddelde is genomen en loopt op naarmate er meer vorige keren waren

while a<=(h(2)-1)
    if horizontaal(a+1)-horizontaal(a)<afstand
        vorige=vorige+1;
    else
        if vorige==0
          horizontaal1=[horizontaal1 horizontaal(a)];
        else
          horizontaal1=[horizontaal1 floor(mean(horizontaal((a-vorige):(a))))];
          vorige=0;
        end
    end
    a=a+1;
end
if vorige>0
    horizontaal1=[horizontaal1 floor(mean(horizontaal((a-vorige):(a))))];
else
    horizontaal1=[horizontaal1 horizontaal(a)];
end

a=1;
vorige=0;
while a<=(v(2)-1)
    if verticaal(a+1)-verticaal(a)<afstand
        vorige=vorige+1;
    else
        if vorige==0
          verticaal1=[verticaal1 verticaal(a)];
        else
          verticaal1=[verticaal1 floor(mean(verticaal((a-vorige):(a))))];
          vorige=0;
        end
    end
    a=a+1;
end
if vorige>0
    verticaal1=[verticaal1 floor(mean(verticaal((a-vorige):(a))))];
else
    verticaal1=[verticaal1 verticaal(a)];
end

verticaal=verticaal1;
horizontaal=horizontaal1;
h=size(horizontaal);
v=size(verticaal);
%scannen binaire data-------------------------------------

%afstand bepalen en nog rijen toevoegen als er nog wat ontbreekt

verschilv=[];
for a=1:(v(2)-1)
    verschilv=[verschilv verticaal(a+1)-verticaal(a)];
end
if isempty(verschilv)
    verschilv=afstand;
end
verschilvO=floor(median(verschilv));
verschilv=floor(median(verschilv)/2);

verschilh=[];
for a=1:(h(2)-1)
    verschilh=[verschilh horizontaal(a+1)-horizontaal(a)];
end
if isempty(verschilh)
    verschilh=afstand;
end
verschilhO=floor(median(verschilh));
verschilh=floor(median(verschilh)/2);

[verticaal horizontaal]=opschonen_raster(horizontaal, verticaal, verschilhO, verschilvO, y2, x2);

while verticaal(end)>(y2-verschilv)
    verticaal(end)=[];
end
while horizontaal(end)>(x2-verschilh)
    horizontaal(end)=[];
end

h=size(horizontaal);
v=size(verticaal);

%binair uitlezen

for a=1:h(2)
    for b=1:v(2)
        binair(b,a)=A(verticaal(b)+verschilv,horizontaal(a)+verschilh);
    end
end

zbinair=size(binair);

%uitlezen data--------------------------------------------

%vinden middelpunt

[middelpunt(1),middelpunt(2),kans_op_correct_middelpunt, type]=middel(binair, zbinair);

if isempty(kans_op_correct_middelpunt)
   rij_ascii=[]; errorc=-1;
   return
end
%binaire rij systematisch uitlezen via verschillende methodes

if type==2
    [rij, rasterP, gegevens, lagenR]=uitlezenl(binair, zbinair, middelpunt);
elseif type==1
    [rij, rasterP, gegevens, lagenR]=uitlezenk(binair, zbinair, middelpunt);
else
   rij_ascii=[]; errorc=-1; 
   return
end

%afmetingen uitlezen en eventueel corrigeren

if type==1
    [fgegevens error]=RSeigen(gegevens,4,3);
    lagen=bin2dec(num2str(fgegevens(1:2)))+1;
    k=bin2dec(num2str(fgegevens(3:8)))+1;
elseif type==2
    [fgegevens error]=RSeigen(gegevens,4,5);
    lagen=bin2dec(num2str(fgegevens(1:5)))+1;
    k=bin2dec(num2str(fgegevens(6:16)))+1;
end

%proberen te corrigeren als de afbeelding er niet volledig opstaat
if lagen>lagenR
    %msgbox('de barcode staat niet volledig op de afbeelding')
    if type==2
        Z=zeros(lagen*4+16,lagen*4+16);
        Z((lagen*2+9-middelpunt(1)):((lagen*2+8-middelpunt(1))+zbinair(1)),(lagen*2+9-middelpunt(2)):((lagen*2+8-middelpunt(2))+zbinair(2)))=binair;
        binair=Z;
        middelpunt=[lagen*2+8 lagen*2+8];
        [rij, rasterP, gegevens, lagenR]=uitlezenl(binair, [lagen*4+16 lagen*4+16], middelpunt);
    elseif type==1
        Z=ones(lagen*4+12,lagen*4+12);
        if (((lagen*2+7-middelpunt(1))>0) && ((lagen*2+7-middelpunt(2))>0))
            Z((lagen*2+7-middelpunt(1)):((lagen*2+6-middelpunt(1))+zbinair(1)),(lagen*2+7-middelpunt(2)):((lagen*2+6-middelpunt(2))+zbinair(2)))=binair;
            binair=Z;
            middelpunt=[lagen*2+6 lagen*2+6];
            [rij, rasterP, gegevens, lagenR]=uitlezenk(binair, [lagen*4+12 lagen*4+12], middelpunt);
        else
           rij_ascii=[]; errorc=-1; 
           return
        end
    else
           rij_ascii=[]; errorc=-1; 
           return
    end
elseif lagen<lagenR
    %msgbox('de barcode staat niet volledig op de afbeelding')
end

lrij=size(rij);

%enen en nullen omdraaien zodat die kloppen als dit nodig is

for a=1:lrij(2)
    if rij(a)==1
        rij(a)=0;
    else
        rij(a)=1;
    end
end

%rij omdraaien zodat de gewone tekst eerst komt

rij=fliplr(rij);

%Reed-Salomon Error correctie----------------------

%het aantal bits van de RS Error correctie bepalen
if((lagenR >= 0) && (lagenR <= 2)) 
    m = 6;
elseif((lagenR >= 3) && (lagenR <= 8)) 
    m = 8;
elseif((lagenR >= 9) && (lagenR <= 22)) 
    m = 10;
elseif (lagenR >= 23)
    m = 12;
else
   rij_ascii=[]; errorc=-1; 
   return
end

%Error correctie op de data toepassen
[rij errorc]=RSeigen(rij,m,k);  %eventueel wordt de k later nog aangepast

%rij=dec2bin(rij)'; errorc=8; %uitschakelen foutcorrectie

%uitlezen rij
rij_ascii=uitlezenrij(rij);




Contact us