MATLAB: Uicontrol question: Slider only acts on last Figure, does not act on Figure it’s associated with.

uicontrol

MATLAB version: R2012b
I'm trying to learn uicontrol using the example given from http://www.mathworks.com/help/matlab/ref/uicontrol.html
I put the example into a for loop running 3 times and get 3 plots.
Question 1: I get Figure1, Figure2, & Figure5. Why Figure5? Why does it skip 3 & 4?
Question 2: The pop-up menu and the push button both control the plot the buttons are on (which is the action I'm wanting) but the sliders on all 3 plots only controls the last plot made (i.e., Figure5).
Restating – the pop-up menu & push button on Figure1 will control the Figure1 plot, and likewise for Figure 2 & 5, but the slider on Figure1 controls the Figure 5 plot, and likewise the slider on Figure2.
I want the slider to behave like the pop-up and push button and control the Figure they're placed on. I thought perhaps that ax needed to be a matrix referenced to ii, i.e., ax(ii) but that didn't help. Note that when I looped it twice (and only have a Figure1 & Figure2) I have the same issue.
Here's the code:
function myui
for ii = 1:3
% Create a figure and axes
f = figure('Visible','off');
ax = axes('Units','pixels');
surf(peaks)
% Create pop-up menu
popup = uicontrol('Style', 'popup',...
'String', {'parula','jet','hsv','hot','cool','gray'},...
'Position', [20 340 100 50],...
'Callback', @setmap);
% Create push button
btn = uicontrol('Style', 'pushbutton', 'String', 'Clear',...
'Position', [20 20 50 20],...
'Callback', 'cla');
% Create slider
sld = uicontrol('Style', 'slider',...
'Min',1,'Max',50,'Value',41,...
'Position', [400 20 120 20],...
'Callback', @surfzlim);
% Add a text uicontrol to label the slider.
txt = uicontrol('Style','text',...
'Position',[400 45 120 20],...
'String','Vertical Exaggeration');
% Make figure visble after adding all components
set(f,'Visible','on');
end %end for ii
function setmap(source,callbackdata)
% source = handle to the object that was used to call the function
% callbackdata is the event associated with the object.
val = get(source,'Value');
maps = get(source,'String');
newmap = maps{val};
colormap(newmap);
end
function surfzlim(source,callbackdata)
val = 51 - get(source,'Value');
zlim(ax,[-val val]);
end
end %end function myui

Best Answer

Tom - I'm not sure why you see figures 1, 2, and 5 as when I run the code, I see figures 1 through 3. Perhaps you have two figures, 3 and 4, already open? Add following line to the beginning of your script which will close all open figures.
close all;
As for the sliders being applied to the last figure only, look closely at the code. On each iteration of the for loop you assign the following to the local variable ax
ax = axes('Units','pixels');
That means on the third iteration of the loop, ax will be the axes for the third figure. Now look at the slider callback
function surfzlim(source,callbackdata)
val = 51 - get(source,'Value');
zlim(ax,[-val val]);
end
We reference the local variable ax which is the axes to the third figure and since you are using the same callback for each slider, then all changes to the slider will be applied to the third axes only.
We need to somehow indicate which axes each slider should be applied to and we do this by passing the axes handle as an input into the slider callback. For example,
% Create slider
sld = uicontrol('Style', 'slider',...
'Min',1,'Max',50,'Value',41,...
'Position', [400 20 120 20],...
'Callback', {@surfzlim,ax});
Note how we pass ax as an input into the callback. Now define the callback as
function surfzlim(source,callbackdata,hAxes)
val = 51 - get(source,'Value');
zlim(hAxes,[-val val]);
end
We define hAxes as the third input to the callback (the first two inputs are the default input parameters) and use it in the call to zlim.
Try integrating the above into your code and see what happens!