function goto_ws=iduiss(arg,nu,ny,onoff)
%IDUISS Handles estimation of models in state-space form.
% 	ARG:
%	open     Opens the dialog box
%	pem      Marks the selection of PEM option
%	ssss     Marks the selection of N4SID option
%	orders   Callback for order choice via popups
%	ordedit  Callback for order choices via edit box
%	mname    Manages the chosen model name
%	estimate Effectuates the estimation
%	qsestimate Effectuates the estimation for quickstart
%	specsel  Effectuates the estimation when structure is chosen
%                from the special order selection plot.
%	close    Closes the dialog
%
%	NU and NY are the number of inputs and outputs in the data
%	ONOFF flag for dialog visibility

%	L. Ljung 4-4-94
%	Copyright (c) 1986-95 by the MathWorks, Inc.
%       $Revision: 1.10 $  $Date: 1995/05/10 21:36:59 $


global XIDss XIDparest XIDmse XIDiter XIDplotw XIDlayout XIDio XIDhw
usd=get(XIDhw(3,1),'userdata');nu=usd(1);ny=usd(2);

if strcmp(arg,'open')
   if isempty(iduiwok(10))%~iduigetp(10,'check');
       iduistat('Opening dialog box ...')
       layout
       
       butwh=[mStdButtonWidth mStdButtonHeight];%butw=55;buth=25;
       butw=butwh(1);buth=butwh(2);
       ftb=mFrameToText;  % Frame to button
       bb = 4; % between buttons
       etf = mEdgeToFrame;
       fig=idbuildw(10); XIDplotw(10,1)=fig;
       set(fig,'units','pixels');
       FigWH=get(fig,'pos');FigWH=FigWH(3:4);
       lev1=max(0,(FigWH(2)-6*buth-5*bb)/2);
       pos = iduilay1([butw+2*ftb],6,6,lev1,bb);
       pos=pos+[(FigWH(1)-pos(1,1)-pos(1,3)-etf)*ones(7,1),zeros(7,3)];
       if strcmp(get(0,'blackandwhite'),'on'),BW=1;else BW=0;end
       s1='iduipoin(1);';s2=iduipoin(1);'iduistat(''Compiling ...'');';
       s3='iduipoin(3);';
       XIDplotw(10,3)=uicontrol(fig,'pos',pos(1,:),'style','frame');
       uicontrol(fig,'Pos',pos(7,:),'style','push','callback',...
          'iduihelp(''selordss.hlp'',''Help: Choice of ARX Structure'');'...
          ,'string','Help');
       uicontrol(fig,'Pos',pos(6,:),'style','push','callback',...
          'set(gcf,''vis'',''off'');','string','Close');
       uicontrol(fig,'Pos',pos(5,:),'style','push','callback',...
          [s1,'iduiss(''specsel'');',s3],'string','Insert');
      uicontrol(fig,'pos',pos(4,:)+[0 0 -butw/2 0],'style','text',...
                'string','S.v. =','horizontalalignment','left');
      uicontrol(fig,'pos',pos(4,:)+[butw/2 0  -butw/2 0],'style','text',...
                'tag','sv','horizontalalignment','left');
      uicontrol(fig,'pos',pos(3,:),'style','edit',...
                'tag','order','horizontalalignment','left',...
               'backgroundcolor','w','callback',[s1,'iduiss(''ordsv'');',s3]);
      uicontrol(fig,'pos',pos(2,:),'style','text',...
                'string','Order','horizontalalignment','left');

     handl=findobj(fig,'type','uicontrol');
     set(handl,'unit','norm')
     if length(XIDlayout)>9,if XIDlayout(10,3)
     eval('set(fig,''pos'',XIDlayout(10,1:4))','')
     end,end
     iduistat('')
     end % end create window

elseif strcmp(arg,'pem')
   set(XIDss(1,2),'value',1);
   set(XIDss(1,5),'value',0);
   set(XIDparest(5),'enable','on');
   iduiss('mname');

elseif strcmp(arg,'ssss')
   set(XIDss(1,5),'value',1);
   set(XIDss(1,2),'value',0);
   set(XIDparest(5),'enable','off');
   eval('set(iduiwok(22),''vis'',''off'');','')
   iduiss('mname');

elseif strcmp(arg,'orders')
   na=get(XIDio(1,4),'value')-1;
   if na==12, 
      nnstr='1:10';
   elseif na==11
      nnstr='1:5';
   else
      if na==10,na=get(XIDio(1,4),'UserData');if isempty(na),na=10;end,end
      nnstr=int2str(na);
   end
   set(XIDparest(3),'string',nnstr);
   iduiss('mname');
elseif strcmp(arg,'ordedit')
   sl1=get(XIDparest(3),'string');
   nrr=find(sl1=='(');
   if ~isempty(nrr),if nrr>1,sl1=sl1(1:nrr-1);end,end
   if any(sl1==':')
     errordlg(str2mat('The multi-model feature is available only',...
          'for the N4SID option.'));
%     iduiss('ssss')
   else
     badname=0;
     eval('nn=eval([''['',sl1,'']'']);','badname=1;')
     if badname
        set(XIDparest(4),'value',6);
        iduiio('mname');return
     end
     set(XIDio(1,4),'value',min(nn+1,11),'UserData',nn);
   end

elseif strcmp(arg,'mname')
   sl1=get(XIDparest(3),'string');
   nrr=find(sl1=='(');
   if ~isempty(nrr),if nrr>1,sl1=sl1(1:nrr-1);end,end
   if any(sl1==':')
      mname='';
   else
     method='n4s';
     eval('if get(XIDss(1,2),''value''),method=''pss'';end','')
     badname=0;
     eval('nn=eval([''['',sl1,'']'']);','badname=1;')
     if badname
        set(XIDparest(4),'value',4);
        mname=[nnstr,'c'];
     else
        mname=[method,int2str(nn)];
     end
   end 
   set(XIDparest(7),'string',mname);
elseif strcmp(arg,'estimate')
   cmdstr=['if strcmp(get(XIDparest(2),''interruptible''),''yes''),',...
            'set(XIDiter(1),''pointer'',''arrow'');',...
           'end,set(XIDiter(7),''userdata'',0);'];
   eval(cmdstr,'')  %Resetting the Stop-button
   usdss='[]';
   noD=0;
   estX0=0;
   oe='no';
   method='n4sid';
   mseflag=0;
         mseflag=1;
         eval('estX0=(get(XIDss(1,7),''value'')==2);','') 
         eval('noD=(get(XIDss(1,8),''value'')==1);','')
         eval('if get(XIDss(1,6),''value'')==1,oe=''oe'';end','')
         eval('if get(XIDss(1,2),''value''),method=''pem'';end','')
   sl1=get(XIDparest(3),'string');nnstr=sl1;
   if any(sl1==':')&strcmp(method,'pem')
      errordlg(str2mat('PEM does not allow several orders.',...
                'Change the selected order.'));
      iduistat('Error.');
      return
   end
   badname=0;
   parnr=find(sl1=='(');
   if ~isempty(parnr)
      nnstr=sl1(1:parnr-1);
      parnr2=find(sl1==')');
      if isempty(parnr2)
         errordlg('The auxiliary order must be contained in parentheses.');
         iduistat('Error.');
         return
      end
      sauxord=sl1(parnr+1:parnr2-1);
   else
      sauxord='[]';
   end
   auxord=eval(sauxord);
   eval('nn=eval([''['',nnstr,'']'']);','badname=1;')
   if badname,set(XIDparest(4),'value',4),iduiio('estimate');return,end
   if length(nn)>1&length(auxord)>1
      errordlg('The order and the auxiliary order cannot both be vectors.');
      iduistat('Error.');
      return
   end
   if any(nn<1)|any(floor(nn)~=nn)
      errordlg('The order must be a positive integer.');
      iduistat('Error.');
      return
   end
   if min(auxord)<nn+1
         auxord=auxord(find(auxord>nn));
         errordlg(str2mat('AUXORD must be larger than ORDER.',...
          'It has been changed accordingly.'));
   end
         
   if strcmp(method,'n4sid')
      iduistat('Estimating model using N4SID ...')
   else
      iduistat('Estimating model by iterative search using PEM ...')
   end
   
      [eDat,eDat_info,eDat_n]=iduigetd('e');
      TSamp=eval(eDat_info(1,:));
      model=get(XIDparest(7),'string');
      if strcmp(method,'pem')
         usd=get(XIDparest(2),'UserData');
         spsobs=deblank(usdss(1,:));psobs=eval(['[',spsobs,']']);         
	 slim=deblank(usd(1,:));lim=eval(slim);
	 stol=deblank(usd(2,:));tol=eval(stol);
	 smaxiter=deblank(usd(3,:));maxiter=eval(smaxiter);
	 sindex=deblank(usd(4,:));index=eval(sindex);
         if isempty(psobs)
	    ind1=floor(nn/ny);spsobs='[';
            for kc=1:ny-1
               psobs(kc)=ind1;spsobs=[spsobs,int2str(ind1),' '];
            end
            if ny>1
               psobs(ny)=nn-sum(psobs);
               spsobs=[spsobs,int2str(psobs(ny)),']'];
            else
               psobs=nn;spsobs=int2str(nn);
            end
        else
           nn=sum(psobs);set(XIDparest(3),'string',int2str(nn));
           if mseflag,set(XIDio(1,4),'value',nn+1);drawnow,end
        end
        if length(psobs)~=ny
           errordlg(str2mat('The number of pseudo-observability indices must equal the number of outputs.',...
                  'Press Options in the state-space model structure window and modify accordingly.'));
           return
        end
        DKX=[1-noD,1,estX0];if strcmp(oe,'oe');DKX(2)=0;end
        LASTM=canstart(eDat,psobs,nu,DKX);
        if isempty(LASTM),iduiinsm([]);return,end
        if strcmp(oe,'oe')&max(abs(eig(th2ss(LASTM))))>1.05
           DKX(2)=1;; if mseflag,set(XIDss(1,6),'value',2);end
           iduihelp(str2mat('The output error model (K=0) turned out to be',...
              'unstable. In order to continue, the K-matrix is now being',...
              'estimated.'));
           LASTM=canstart(eDat,psobs,nu,DKX);
        end
	model=['pss',int2str(nn)];
%        if estX0
%           LASTM=unfixpar(LASTM,'x0',[]);
%           strx0=[model,' = unfixpar(',model,',''x0'',[],)'];
%        else
%          strx0=[];
%        end
   

  	eval('LASTM=pem(eDat,LASTM,index,maxiter,tol,lim,[],TSamp);')
	mod_info=str2mat(eDat_info,...
         [model,' = canstart(',eDat_n,',',spsobs,',',int2str(nu)...
               ,',[',int2str(DKX(1)),',',int2str(DKX(2)),...
          ',',int2str(DKX(3)),'])']);
%        if ~isempty(strx0),mod_info=str2mat(mod_info,strx0);end
         mod_info=str2mat(mod_info,...
           [model,' = pem(',eDat_n,',',model,',',sindex,',',smaxiter,','...
              ,stol,',',slim,',[],',num2str(TSamp),')']);
      else
        if length(nn)>1
          iduiss('open');
          if isempty(iduiwok(10)),XIDplotw(10,1)=idbuildw(10);end
          iduistat('N4SID calculates models of several orders ...')
	end	 
        if length(auxord)>1
          if isempty(iduiwok(11)),XIDplotw(11,1)=idbuildw(11);end
          iduistat('Models for different aux orders being calculated ...')
	end	 

        [Ncap,nyutest]=size(eDat);
        if isempty(auxord),testa=max(nn)*1.2+3;else testa=max(auxord);end
        if Ncap<(1.5*ny+2.5*nu)*(max(nn)+2)+ny
         errordlg('There are too few data points for this choice of orders.');
          iduistat('No model estimated.');
          return
        end
        DKX=[1-noD,1,estX0];if strcmp(oe,'oe');DKX(2)=0;end
       eval(['[LASTM,best_i,dum,failflag]=',...
             'n4sid(eDat,nn,ny,auxord,DKX,[],TSamp,1,''gui'');'])
        if failflag==1,iduiinsm([]);return,end
        if failflag==2,
           errordlg('Too few data points for this choice of order.');
           iduistat('No model estimated.');
           return
        end
        if isempty(LASTM)
	   figure(XIDplotw(10,1)) % Filling out the default
	   V=get(XIDplotw(10,3),'userdata');
	   set(findobj(gcf,'tag','sv'),'string',num2str(V(2,1)));
	   set(findobj(gcf,'tag','order'),'string',int2str(V(1,1)));
           iduistat('Ready to select models.')
           iduistat('Click on bars to inspect models.',0,10);
           return
        end
	mod_info=str2mat(eDat_info,...
          [model,' = n4sid(',eDat_n,',',int2str(nn),',',int2str(ny),',',...
          int2str(best_i),',[',int2str(DKX(1)),',',int2str(DKX(2)),...
          ',',int2str(DKX(3)),'],[],',num2str(TSamp),')']);
      end
      mod_nam=model;%[model,'_',eDat_n];
      mod_nam=mod_nam(find(mod_nam~=' '));
      iduiinsm(LASTM,str2mat('',mod_info),mod_nam);

elseif strcmp(arg,'specsel')
      if nargin==1
         sord=get(findobj(XIDplotw(10,1),'tag','order'),'string');
         if isempty(sord)
            iduistat('No model selected.',0,10);
            return
         end
         err=0;eval('nn=eval(sord);','err=1;')
         if err,
            iduistat('Order cannot be evaluated.',0,10);
            return
         end
         nn=floor(nn);
      else
         nn=get(XIDplotw(10,3),'userdata');nn=nn(1,1);
      end
      err=0;
      eval('set(XIDparest(3),''string'',int2str(nn));','err=1;')
      if err
        errordlg(str2mat('Cannot find the Parametric Models Window.',...
          'Please reopen it.'));return
      end
      set(XIDparest(4),'value',5);

      iduistat([int2str(nn),'th order model being estimated ...'],0,10);
      iduistat([int2str(nn),'th order model calculated using N4SID ...'])
      set(XIDplotw(10,1),'pointer','watch');

      iduiss('mname');
      [eDat,eDat_info,eDat_n]=iduigetd('e');
      TSamp=eval(eDat_info(1,:));
      DKX=[0,1,0];
      eval('if get(XIDss(1,6),''value'')==1,DKX(2)=0;end','')
      eval('if get(XIDss(1,8),''value'')==2,DKX(1)=1;end','')
      eval('if get(XIDss(1,7),''value'')==2,DKX(3)=1;end','') 

      [LASTM,best_i]=n4sid(eDat,nn,ny,[],DKX,[],TSamp,1,'guichoice');
      model=['n4s',int2str(nn)];
	mod_info=str2mat(eDat_info,...
          [model,' = n4sid(',eDat_n,',',int2str(nn),',',int2str(ny),',',...
          int2str(best_i),',[',int2str(DKX(1)),',',int2str(DKX(2)),...
          ',',int2str(DKX(3)),'],[],',num2str(TSamp),')']);
      mod_nam=model;%[model,'_',eDat_n];
      mod_nam=mod_nam(find(mod_nam~=' '));
      iduistat('');
      iduiinsm(LASTM,str2mat('',mod_info),mod_nam);
      iduistat('New models may now be selected.',0,10);
elseif strcmp(arg,'qsestimate')
      [eDat,eDat_info,eDat_n]=iduigetd('e');
      TSamp=eval(eDat_info(1,:));
      DKX=[0,1,0];
      [LASTM,best_i,nn]=n4sid(eDat,'best',ny,[],[],[],TSamp,1);
      model=['n4s',int2str(nn)];
	mod_info=str2mat(eDat_info,...
         [' ',model,' = n4sid(',eDat_n,',',int2str(nn),',',int2str(ny),',',...
          int2str(best_i),',[',int2str(DKX(1)),',',int2str(DKX(2)),...
          ',',int2str(DKX(3)),'],[],',num2str(TSamp),')']);
      mod_nam=model;%[model,'_',eDat_n];
      mod_nam=mod_nam(find(mod_nam~=' '));
      iduiinsm(LASTM,str2mat('',mod_info),mod_nam);
elseif strcmp(arg,'down')
  iduistat('Press Insert to estimate model or click on other bar.',0,10)
    figure(XIDplotw(10,1))
    V=get(XIDplotw(10,3),'userdata');
    [nl1,nm1]=size(V);
    vv=V(:,2:nm1);
    pt=get(gca,'currentpoint'); pp=round(pt(1,1));
    pp=max(min(vv(1,:)),pp);pp=min(max(vv(1,:)),pp);
    ind=find(vv(1,:)==pp);if isempty(ind),return,end
    sfit=num2str(vv(2,ind));
    ord=int2str(pp);
    set(findobj(gcf,'tag','sv'),'string',sfit);
    set(findobj(gcf,'tag','order'),'string',ord);
elseif strcmp(arg,'ordsv')
    figure(XIDplotw(10,1))
    V=get(XIDplotw(10,3),'userdata');
    [nl1,nm1]=size(V);
    vv=V(:,2:nm1);
    horder=findobj(XIDplotw(10,1),'tag','order');
    pp=get(horder,'string');
    err=0;    eval('pp=eval(pp);','err=1;')
    if err,
       iduistat('Order cannot be evaluated.',0,10);
       set(horder,'string','');
       return
    end
    if length(pp)>1|length(pp)<1
       iduistat('Order must be a positive integer.',0,10);
       set(horder,'string','');
       return
    end
    if pp<min(vv(1,:))|pp>max(vv(1,:))
      err=1;
    else
      ind=find(vv(1,:)==pp);if isempty(ind),err=1;end
    end
    if err
       iduistat('This order is not an available choice.',0,10);
       set(horder,'string','');set(findobj(gcf,'tag','sv'),'string','');
       return
    end  
    sfit=num2str(vv(2,ind));
    set(findobj(gcf,'tag','sv'),'string',sfit);
    iduistat('Press Insert to compute model or select other order.',0,10);

end

