function SVRespObj = svplot(RespObj,Systems,X,Y,PlotStyle);      
%SVPLOT Create a Singular Value Response Object for the Control System Toolbox

%   Authors: Karen Gondoly, 2-13-98
%   Revised: Adam W. DiVergilio, 11-99
%   Copyright 1986-2000 The MathWorks, Inc. 
%   $Revision: 1.21 $ $Date: 2000/06/19 21:02:58 $

ni = nargin;

%---Properties
SVRespObj = struct(...
   'FrequencyUnits','',...
   'MagnitudeUnits','',...
   'PeakResponse','off',...
   'PeakResponseValue',[]);

%---Return cases (ni==0,1)
switch ni
case 0
   RespObj = response;
   SVRespObj = class(SVRespObj,'svplot',RespObj);
   return
case 1
   if ~isa(RespObj,'response')
      error('Invalid Response Object passed to SVPLOT')
   elseif isa(RespObj,'svplot')
      SVRespObj = RespObj;
   else
      SVRespObj = class(SVRespObj,'svplot',RespObj);
   end
   return
end

%---Initialize SVRespObj
SVFlag = isa(RespObj,'svplot');
if SVFlag
   SVRespObj = RespObj;
   RespObj = SVRespObj.response;
else
   Preferences = get(RespObj,'Preferences');
   SVRespObj.FrequencyUnits = Preferences.FrequencyUnits;
   SVRespObj.MagnitudeUnits = Preferences.MagnitudeUnits;
   set(get(RespObj,'PlotAxes'),'XScale',Preferences.FrequencyScale,'YScale',Preferences.MagnitudeScale);
end

%---Access needed parent property values
PV = get(RespObj,{'PlotAxes','UIContextMenu','SystemNames'});
[LTIdisplayAxes,ContextMenu,SystemNames] = deal(PV{:});
if SVFlag
   % Adding to existing SVPLOT object
   RH0 = get(RespObj,'ResponseHandles');
else
   % New SVPLOT object
   RH0 = {};
end

%---Get dimension info and names of new systems
NumOldSys = length(RH0);                      % number of existing systems
NewSystemNames = SystemNames(NumOldSys+1:end);
NumNewSys = length(NewSystemNames);           % number of added systems 

%---Set initial values for SVPLOT-specific properties
PeakRespVals = struct('System',cell(NumNewSys,1),'Frequency',[],'Peak',[]);

%---Initialize ResponseHandles array and LTIresponseLine's UserData
ResponseHandles = cell(NumNewSys,1);

for ctR=1:length(ResponseHandles)  % each system
   % Get plot data
   Xarray = X{ctR};
   Yarray = Y{ctR};
   SizeArray = size(Xarray);
   NumArray = prod(SizeArray);
   dflag = abs(Systems{ctR}.Ts);
   
   % Get the style and legend
   Style = struct2cell(PlotStyle(ctR));
   [CC,LL,MM,LegendStr] = deal(Style{:});
   if NumArray>1
      ArrayDimsStr = sprintf('%dx',SizeArray);
      LegendStr = sprintf('%s array: %s',ArrayDimsStr(1:end-1),LegendStr);
   end
   
   %---Add legend to system name for new systems
   set(ContextMenu.Systems.Names(NumOldSys+ctR),...
      'Label',sprintf('%s (%s)',NewSystemNames{ctR},LegendStr),...
      'ForegroundColor',CC)
   
   %---Determine if system is discrete
   RH=cell(SizeArray);
   RH2=cell(SizeArray);
   for ctArray=1:NumArray
      Xdata = unitconv(Xarray{ctArray},'rad/sec',SVRespObj.FrequencyUnits);
      Ydata = unitconv(Yarray{ctArray},'abs',SVRespObj.MagnitudeUnits);

      %---Response line UserData
      LineUd = struct('System',NewSystemNames{ctR},'Input',1,...
         'Output',1,'Array',rguihelper('ind2sub',SizeArray,ctArray));

      for ctlines=1:size(Ydata,1)
         RH{ctArray}(ctlines,1)=line(Xdata,Ydata(ctlines,:),...
            'Color',CC,'Marker',MM,'LineStyle',LL,'UserData',LineUd,...
            'Tag','LTIresponseLines','DeleteFcn','delresp(gcbo)',...
            'Visible','off','Parent',LTIdisplayAxes(1,1),...
            'ButtonDownFcn','rguifcn(''showbox'',gcbf);');
      end

      %---Only draw Nyquist line when it is at the end of the data
      if dflag>0
         NyqFreq = unitconv(pi/dflag,'rad/sec',SVRespObj.FrequencyUnits);
         if abs(Xdata(end)-NyqFreq)<NyqFreq/10
            % RE: make handle invisible to prevent LEGEND from picking it up
            RH{ctArray}(ctlines+1,1)=line([NyqFreq;NyqFreq],[0 1],...
               'Parent',LTIdisplayAxes(1,1),'Tag','NyquistLines',...
               'Visible','off','HandleVis','off','HitTest','off',...
               'Color','k','LineStyle','-');
         end
      end
   end
   ResponseHandles{ctR} = {RH};
end

%---Set the BackgroundAxes labels
BackAxLabels = {...
      'Title','Singular Values',...
      'Ylabel',sprintf('Singular Values (%s)',SVRespObj.MagnitudeUnits),...
      'Xlabel',sprintf('Frequency (%s)',SVRespObj.FrequencyUnits)};

if SVFlag  % Append Data
   RespObj = pvset(RespObj,'UIContextMenu',ContextMenu,...
      'ResponseHandles',[RH0;ResponseHandles],...
      BackAxLabels{:});
   SVRespObj.PeakResponseValue = [SVRespObj.PeakResponseValue;PeakRespVals];
   SVRespObj.response = RespObj;

else
   %---Add the Plot Option Menus
   ContextMenu.PlotOptions.PeakResponse = uimenu(ContextMenu.PlotOptions.Main,...
      'Label',xlate('Peak Response'),...
      'Callback','menufcn(''togglepeak'')');

   RespObj = pvset(RespObj,'ResponseHandles',ResponseHandles, ...
      'UIContextMenu',ContextMenu,BackAxLabels{:});
   SVRespObj.PeakResponseValue = PeakRespVals;
   SVRespObj = class(SVRespObj,'svplot',RespObj);
end

%---Update HG pointer to Response Object
builtin('set',ContextMenu.Main,'userdata',SVRespObj)
