function [bin, lab, Gr, GrM, num, binB, binBB, waveGr] = nestpars(arg, optmiss, ltperc, srtvl, boxes, validValues)

% dodata opcija za binBB za time varijable, i izdvanjanje samo "donjih" bez pravljenja matrice
%v4 - dodata 4 opica na optmiss za Blok Multiple
%v3 - dodato je i ispravljeno ltperc (drugo)

%optmiss je sada bar 6-elementarni vektor, [b1,b2,b3,b4,b5,b6]
% b1 je 0/1 za NaN da se pojavi sto u ovoj verziji neradi,
% b2 je marks, ako je definisan i veci od 0
% b3 je 0/1 1 onda svaka varijabla u binarnim multiplim ima svoju posebnu bazu, tj 0 sve zajedno jednu
% b4 je broj varijabli u blokmultiploj
% b5 je da se okrenu labele za "Sum -" i za "Sum +"
% b6 je za vallabs, da dummy_jti uzima sve vrednosti iz labela

%waveGr kolone sa tri reda, prvi gde pocinje, drugi koliko se dodaje za sledecu kolunu sa kojom se poredi, i treci koliko kolona za poredjenje ima

	global drvfin;
	global arg;
	arg=ucase(arg);

	brtok = max(size(arg));
	brt = brtok;
	drv = [(1:brtok)';zeros(2,brtok)];
	drvfin=[];
	kraj =1;
	while kraj <= size(drv,2)
		if arg(drv(1,kraj))==")"
			poc = kraj;
			while poc>1 & arg(drv(1,poc))~="("
				poc = poc - 1;
			end
			if poc==1
				if arg(drv(1,1))~="("
					error("Nedostaje '('");
				end
			end
			if poc+1==kraj %samo zagrade
				drv(:,poc)=[];
				drv(:,poc)=[];
				kraj = kraj-2;
				poc = kraj;
			else
				drv(:,kraj)=[];
				drv(:,poc)=[];
				kraj=kraj-2;

				hesh();
				vece();
				blanko();
			end
		end
		kraj=kraj+1;
	end
	kraj = kraj-1;
	if kraj~=1
		poc = kraj;
		while poc>1 & arg(drv(1,poc))~="("
			poc = poc - 1;
		end
		if poc~=1 | arg(drv(1,1))=="("
			error("Nedostaje ')'");
		end
		hesh();
		vece();
		blanko();
	end
	
	drvfin = [drvfin drv];
	%[arg(drvfin(1,:));num2str("%d",drvfin)]
	if nargin==1 %samo da izvdvoji finalne varijable
		bin = donje(drv(1));
		bin = arg(bin);
	else
		if ~def(validValues)
			validValues = [];
		end
		[bin, lab, Gr, GrM, num, binB, binBB, waveGr] = nest (drv(1), 1, optmiss, ltperc, srtvl, boxes, validValues);
	end


	clear drvfin;
	clear arg;
end

macro hesh
	i = poc+1;
	while i<=kraj
		if arg(drv(1,i))=="#" & drv(2,i)==0 & drv(3,i)==0
			if ~(drv(2,i-1)==0 & drv(3,i-1)==0)
				error("nepravila upotreba #")
			end

			drv(2,i) = drv(1,i-1);
			drvfin = [drvfin, drv(:,i-1)];
			drv(:,i-1)=[];
			kraj = kraj-1;
			while(i<=kraj & arg(drv(1,i))~="#")
				drv(:,i)=[];
				kraj = kraj-1;
			end
			if arg(drv(1,i))~="#"
				error("Nepravila upotreba #")
			else
				drv(:,i)=[];
				kraj = kraj-1;
			end
		end
		i = i+1;
	end
end

macro vece
	i = kraj-1;
	while poc<i & poc~=kraj
		if arg(drv(1,i))==">" & drv(2,i)==0 & drv(3,i)==0
			drv(2,i) = drv(1,i-1);
			drv(3,i) = drv(1,i+1);
			drvfin = [drvfin, drv(:,i-1), drv(:,i+1)];
			drv(:,i+1)=[];
			drv(:,i-1)=[];
			kraj = kraj-2;
			i=i-1;
		end
		i = i-1;
	end
end

macro blanko
	while poc<kraj
		brt=brt+1;
		if size(arg,1)==1
			arg = [arg "+"];
		else
			arg = [arg; "+"];
		end
		pom = [brt;drv(1,kraj-1);drv(1,kraj)];
		drvfin = [drvfin,drv(:,kraj-1),drv(:,kraj)];
		drv(:,kraj)=[];
		kraj = kraj-1;
		drv(:,kraj)=pom;
	end
end


function bin = donje(k)
	global drvfin;
	global arg;

	if k==0
		bin=[];
		return;
	end
	p = find(drvfin(1,:)==k);

	if arg(drvfin(1,p))=="+"
		bin1 = donje(drvfin(2,p));
		bin2 = donje(drvfin(3,p));
		if bin1==[] | bin2==[]
			error("Pogreska u zadavanju sintakse");
		end

		bin = [bin1, bin2];
		return;
	elseif arg(drvfin(1,p))==">"
		bin = donje(drvfin(3,p));
		if bin==[]
			error("Pogreska u zadavanju sintakse");
		end
		return;
	elseif arg(drvfin(1,p))=="#"
		bin = donje(drvfin(2,p));
		if bin==[]
			error("Pogreska u zadavanju sintakse");
		end
		return;
	else
		bin = drvfin(1,p);
		return;
	end
end


function [bin, lab, gr, grM, num, binB, binBB, waveGr] = nest(k,level,optmiss, ltperc,srtvl, boxes, validValues)
%grM - je isto sto i gr, ali ne na najsitnije nego na najkrupniji nivo a>b, gr je za svako b, a grM je samo za a
	global drvfin;
	global arg;

	if k==0
		bin=[];
		lab=[];
		gr=[];
		grM=[];
		num=[];
		binB=[];
		binBB=[];
		waveGr = [];
		return;
	end
	p = find(drvfin(1,:)==k);

	if arg(drvfin(1,p))=="+"
		[bin1,lab1,gr1,grM1,num1,binB1,binBB1, waveGr1] = nest(drvfin(2,p),level,optmiss, ltperc, srtvl, boxes, validValues);
		[bin2,lab2,gr2,grM2,num2,binB2,binBB2, waveGr2] = nest(drvfin(3,p),level,optmiss, ltperc, srtvl, boxes, validValues);
		if bin1==[] | bin2==[]
			error("Pogreska u zadavanju sintakse");
		end
		bin = [bin1, bin2];
		binB = [binB1, binB2];
		binBB = [binBB1, binBB2];
		if outputType
			char = "|";
		else
			char = "";
		end
		if size(lab1,1)>size(lab2,1)
			lab = [lab1,[lab2;make(size(lab1,1)-size(lab2,1),size(lab2,2),char)]];
		elseif size(lab1,1)<size(lab2,1)
			lab = [[lab1;make(size(lab2,1)-size(lab1,1),size(lab1,2),char)],lab2];
		else
			lab = [lab1, lab2];
		end
		gr = [gr1, mmax(gr1)+gr2];
		grM = [grM1, mmax(grM1)+grM2];
		if (waveGr2~=[])
			waveGr2(1,:) = waveGr2(1,:)+mmax(gr1);
		end
		%waveGr1
		%waveGr2
		waveGr = [waveGr1, waveGr2];
		num = [num1;num2];
		return;
	elseif arg(drvfin(1,p))==">"
		[bin1,lab1,gr1,grM1,num1,binB1,binBB1, waveGr1] = nest(drvfin(2,p),level,optmiss, ltperc, srtvl, boxes, validValues);
		[bin2,lab2,gr2,grM2,num2,binB2,binBB2, waveGr2] = nest(drvfin(3,p),level+1,optmiss, ltperc, srtvl, boxes, validValues);
		if bin1==[] | bin2==[]
			error("Pogreska u zadavanju sintakse");
		end
		bin2s = size(bin2,2);
		
		bin = zeros(size(bin1,1),size(bin1,2)*size(bin2,2));
		binB = zeros(size(bin));
		binBB = zeros(size(bin));
		num = make(size(bin1,2)*size(bin2,2),1,NaN);
		if outputType
			lab = make (size(lab1,1)+size(lab2,1),size(lab1,2)*size(lab2,2),"~");
			%lab = make (2,size(lab1,2)*size(lab2,2),"~");
		else
			lab = make (size(lab1,1)+size(lab2,1),size(lab1,2)*size(lab2,2),"");
			%lab = make (2,size(lab1,2)*size(lab2,2),"");
		end
		gr=[];
		for i = 0:size(bin1,2)-1
			for j = 1:bin2s
				bin(:,i*bin2s+j) = bin1(:,i+1).*bin2(:,j);
				binB(:,i*bin2s+j) = bin1(:,i+1).*binB2(:,j);
				binBB(:,i*bin2s+j) = binBB1(:,i+1).*binBB2(:,j);
			end
			if gr==[]
				gr=gr2;
				grM=gr2;
			else
				gr = [gr, mmax(gr)+gr2];
				grM(size(grM,1),size(grM,2))=grM(size(grM,1),size(grM,2)) + gr2(2)-gr2(1)+1;
			end
			lab (((1+size(lab1,1)):size(lab,1)),((i*bin2s+1):(i*bin2s+bin2s))) = lab2;
			%lab (2,((i*bin2s+1):(i*bin2s+bin2s))) = lab2(2,:);
			lab(1,i*bin2s+1) = lab1(2,i+1);
			lab(1:size(lab1,1), i*bin2s+1) = lab1(:, i+1);
			num(i*size(bin2,2)+1:(i+1)*size(bin2,2)) = num2;
		end
		
		waveGr  = [];
		if (waveGr1~=[])
			if (waveGr2~=[])
				error("You have already defined WAVE in table segment")
			else
				waveGr1(2,:) = waveGr1(2,:)*bin2s;
				%waveGr1(1,:) = (waveGr1(1,:)-1)*bin2s+1;
				%waveGr1(3,:) = bin2s;
				waveGr  = waveGr1;
			end
		elseif (waveGr2~=[])
			if (waveGr1~=[])
				error("You have already defined WAVE in table segment")
			else
				k = waveGr2;
				for j=1:size(gr1,2)
					for i=gr1(1,j):gr1(2,j)
						k(1,:) =  waveGr2(1,:)+(i-1)*waveGr2(2)*waveGr2(3)*size(waveGr2,2);
						waveGr =[waveGr, k];
					end
				end
			end
		end
		
		return;
	elseif arg(drvfin(1,p))=="#"
		i = drvfin(1,p)+1;
		values = [];
		while (arg(i)~="#")
			if arg(i)==":"
				if i==1
					error("Not valid use of :")
				end
				values
				if size(values,1)>1
					values = [values(1:(size(values,1)-1));(values(size(values,1)):str2num(arg(i+1)))];
				else
					values = [values(1);(values(size(values,1)):str2num(arg(i+1)))];
				end
				i=i+1;
			else
				values=[values;str2num(arg(i))];
			end
			i=i+1;
		end
		%[bin,lab,gr,grM,num,binB] = nest(drvfin(2,p),optmiss, ltperc, srtvl);
		[bin,lab,num,binB,binBB, waveGr]=dummy(arg(drvfin(2,p)),optmiss,boxes,values);
		gr=[1;size(bin,2)];
		grM = gr;
		lab = lab';

		hd = make(2,size(lab,2),"");
		hd(2,:) = lab;
		if strcmp(arg(drvfin(2,p)),"$TOTAL")
			hd(1,:) = GetVarLabel(arg(drvfin(2,p)));
			else
				hd(1,:) = "Total";
				hd(2,:) = "";
			end
		if (~strcmp(hd(1,1),""))
			hd(1,:)= arg(drvfin(2,p));
		end
		lab = hd;
	else
		%[bin1,lab1,gr1,num1] = nest(drvfin(2,p),level,optmiss, ltperc);
		%[bin2,lab2,gr2,num2] = nest(drvfin(3,p),level,optmiss, ltperc);
		%OVE 5 LINIJA ISPOD MOGU DA SE ISKLJUCE, ONE SU U RAZVOJU BILE POTREBNE, SADA VISE NE
		bin1 = nest(drvfin(2,p),level,optmiss, ltperc, srtvl, boxes, validValues);
		bin2 = nest(drvfin(3,p),level,optmiss, ltperc, srtvl, boxes, validValues);
		if bin1~=[] | bin2~=[]
			error("Pogreska u zadavanju sintakse");
		end
	  	[bin,lab,num,binB,binBB,waveGr] = dummy(arg(drvfin(1,p)),optmiss,boxes);

	  	if validValues~=[] | optmiss(2)>3 % ovo znaci da ima neki "marks"
	  		if validValues == []
		  		validValues = (1 : optmiss(2))';
			end
			centar1 = floor(max(size(validValues))/2);
			if max(size(validValues))/2>centar1;
				centar2 = centar1+2;
			else
				centar2 = centar1+1;
			end

			labRez = "";
			binRez = [];
			numRez = [];
			binBRez = [];
			binBBRez = [];
			if (optmiss(5)==1)
				lbMi = "Sum +";
				lbPl = "Sum -";
			else
				lbMi = "Sum -";
				lbPl = "Sum +";
			end
			indx = find(num in validValues(1:centar1));
			if any(indx)
				labRez = [labRez;lab(indx);lbMi];
				bin1 = bin(:,indx);
				binB1 = binB(:,indx);
				binBB1 = binBB(:,indx);
				binRez = [bin1,rsum(bin1)>0];
				binBRez = [binB1,rsum(binB1)>0];
				binBBRez = [binBB1,rsum(binBB1)>0];
				numRez = [num(indx);-Inf];
			end

			if centar1+1~=centar2
				indx = find(num==validValues(centar1+1));
				if any(indx)
					labRez = [labRez;lab(indx)];
					binRez = [binRez,bin(:,indx)];
					binBRez = [binBRez,binB(:,indx)];
					binBBRez = [binBBRez,binBB(:,indx)];
					numRez = [numRez;num(indx)];
				end
			end

			indx = find(num in validValues(centar2:NaN));
			if any(indx)
				bin1 = bin(:,indx);
				binB1 = binB(:,indx);
				binBB1 = binBB(:,indx);
				binRez = [binRez,rsum(bin1)>0,bin1];
				binBRez = [binBRez,rsum(binB1)>0,binB1];
				binBBRez = [binBBRez,rsum(binBB1)>0,binBB1];
				labRez = [labRez;lbPl;lab(indx)];
				numRez = [numRez;Inf;num(indx)];
			end

			indx = find(~(num in validValues));
			if any(indx)
				bin1 = bin(:,indx);
				binB1 = binB(:,indx);
				binBB1 = binBB(:,indx);
				binRez = [binRez,bin1];
				binBRez = [binBRez,binB1];
				binBBRez = [binBBRez,binBB1];
				labRez = [labRez;lab(indx)];
				numRez = [numRez;num(indx)];
			end

			bin = binRez;
			binB = binBRez;
			binBB = binBBRez;
			lab = labRez(2:NaN);
			num = numRez;
	  	end

		if ltperc~=[] %sve manje od ltperc(1) u ltperc(2)
			if wgh~=[]
				bin1 = bin.*wgh;
			else
				bin1 = bin;
			end

			per = csum(bin1);
			if wgh~=[]
				ctotal = (rsum(bin1)>0)'*wgh;
			else
				ctotal = sum(rsum(bin1)>0);
			end

			per = per'/ctotal*100;
			%[(1:size(num,1)), num, per]
			%ltperc(1)
			%srtvl
			if srtvl~=[]
				indx = find(per<ltperc(1) & num<srtvl);
			else
				indx = find(per<ltperc(1));
			end
			clear per;

			if indx~=[]
				f = find(num==ltperc(2));
				bin_col = rsum(bin(:,indx))>0;
				binB_col = rsum(binB(:,indx))>0;
				binBB_col = rsum(binBB(:,indx))>0;
				if f==[]%medju dobijenim vrednostima nema one u koju treba rekodirati, sve manje od ...
					num(indx)=[];
					bin(:,indx)=[];
					binB(:,indx)=[];
					binBB(:,indx)=[];
					lab(indx)=[];
					bin = [bin,bin_col];
					binB = [binB,binB_col];
					binBB = [binBB,binBB_col];
					num = [num;ltperc(2)];

					pomlab = GetNumLabel(GetVarName(arg(drvfin(1,p))),ltperc(2));
					f = find(strcmp(pomlab,""));
					if (any(f))
						pomlab = pomlab(f(1));
					else
						pomlab = num2str("%0.2f",ltperc(2));
					end
					lab = [lab;pomlab];
				else
					findx = find(f==indx);
					if any(findx)%da li je ona u koju treba medju onima koje treba izbaciti
						indx(findx)=[];
						bin(:,f) = bin_col;
						binB(:,f) = binB_col;
						binBB(:,f) = binBB_col;
					else
						bin(:,f) = (bin(:,f) + bin_col)>0;
						binB(:,f) = (binB(:,f) + binB_col)>0;
						binBB(:,f) = (binBB(:,f) + binBB_col)>0;
					end
					if indx~=[]
						num(indx)=[];
						bin(:,indx)=[];
						binB(:,indx)=[];
						binBB(:,indx)=[];
						lab(indx)=[];
					end
				end
			end
		end

		lab = lab';
		if 1%level==1 %########################## ovo je ovde da se dodaje jos ime varijable
		if outputType
			hd = make(2,size(lab,2),"~");
		else
			hd = make(2,size(lab,2),"");
		end
		hd(2,:) = lab;
		if strcmp(arg(drvfin(1,p)),"$TOTAL")
			hd(1,1) = GetVarLabel(arg(drvfin(1,p)));
			else
				hd(1,1) = "Total";
				hd(2,1) = "";
			end
			if (~strcmp(hd(1,1),""))
				hd(1,1)= arg(drvfin(1,p));
			end
			lab = hd;
		end

		gr=[1;size(bin,2)];
		grM = gr;
		if (waveGr~=[])
			xxx = waveGr;
			waveGr = gr;
			waveGr(2,1) = 1;
			waveGr(3,1) = xxx;
		end
		return;
	end
end