passing uicontrol objects to uicontrol callbacks

26 ビュー (過去 30 日間)
Steve Slana
Steve Slana 2018 年 7 月 10 日
コメント済み: Dennis 2018 年 7 月 13 日
I have three sliders that are in the same position, and based on a radio button selection, I'd like to make one of the three appear at one time.
I've tried to do this by making only one visible at any point in time. I've tried to accomplish this by passing the slider uicomponents to the respective callback functions of the radio buttons, so that i might make one visible and the other two invisible.
Essentially,
%%%%%Make slider objects at same position%%%%%%
p=uipanel;
sliderterminal = uicontrol(p,'Style','slider');
sliderinitial = uicontrol(p,'Style','slider');
sliderthreshold = uicontrol(p,'Style','slider');
%%%%%controlling radio buttons%%%%%%
bg = uibuttonggroup(p);
rinitial = uicontrol(bg,'Style','radiobutton','Callback',@initialcutoff)
rterminal = uicontrol(bg,'Style','radiobutton','Callback',@terminalcutoff)
rthreshold = uicontrol(bg,'Style','radiobutton','Callback',@thresholdindex)
%%%%%%Callback Functions%%%%%
function initialcutoff(sliderthreshold,sliderinitial,sliderterminal)
sliderterminal.Visible='off';
sliderthreshold.Visible='off';
sliderinitial.Visible='on';
end
function terminalcutoff(sliderthreshold,sliderinitial,sliderterminal)
sliderinitial.Visible='off';
sliderthreshold.Visible='off';
sliderterminal.Visible='on';
end
function thresholdindex(sliderthreshold,sliderinitial,sliderterminal)
sliderinitial.Visible='off';
sliderterminal.Visible='off';
sliderthreshold.Visible='on';
end
When the callback functions are accessed the desired uicontrol objects are not passed in from the base workspace. If anybody could help me with this issue I would greatly appreciate insight. Please let me know if I'm going about this all wrong.
PS - I didn't add the position information for the uicomponents as i figured added a lot of extraneous information isn't too good of an idea.

採用された回答

Dennis
Dennis 2018 年 7 月 11 日
There are several ways to pass data/handles between callbacks. For some in depth information you can check here.
I can see 2 problems with your code.
  1. Callback functions in matlab always have atleast 2 inputs (3 if working with guide). Those are provided by matlab and you do not need to specify them.
function mycallback(hObj,event,handles)
%code
end
  1. When you want to pass additional arguments to a callback function you need to tell matlab which ones.
rinitial = uicontrol(bg,'Style','radiobutton','Callback',{@initialcutoff,sliderterminal,sliderinitial,sliderthreshold})
But remember the first arguments of your callback function are reserved.
Now about a possible solution to your question: I would start storing all my handles in a struct.
handles.p=uipanel;
%%%%%controlling radio buttons%%%%%%
handles.bg = uibuttongroup(handles.p);
handles.rinitial = uicontrol(handles.bg,'Style','radiobutton','Callback',{@radiobutton_callback},'position',[20 40 20 20]);
handles.rterminal = uicontrol(handles.bg,'Style','radiobutton','Callback',{@radiobutton_callback},'position',[20 60 20 20]);
handles.rthreshold = uicontrol(handles.bg,'Style','radiobutton','Callback',{@radiobutton_callback},'position',[20 80 20 20]);
handles.sliderterminal = uicontrol(handles.p,'Style','slider','position',[20 200 100 20],'visible','off');
handles.sliderinitial = uicontrol(handles.p,'Style','slider','position',[20 200 120 20],'visible','off');
handles.sliderthreshold = uicontrol(handles.p,'Style','slider','position',[20 200 110 20],'visible','off');
guidata(handles.p,handles)
Next i would write one callback function for your radiobutton and pass your handles struct:
function radiobutton_callback(hObj,~)
handles=guidata(hObj);
if handles.rinitial.Value ==1
handles.sliderterminal.Visible='off';
handles.sliderthreshold.Visible='off';
handles.sliderinitial.Visible='on';
elseif handles.rterminal.Value ==1
handles.sliderterminal.Visible='on';
handles.sliderthreshold.Visible='off';
handles.sliderinitial.Visible='off';
else
handles.sliderterminal.Visible='off';
handles.sliderthreshold.Visible='on';
handles.sliderinitial.Visible='off';
end
end
  6 件のコメント
Steve Slana
Steve Slana 2018 年 7 月 13 日
Thank you so much for all your help I think I understand now! This stranger really appreciates it!
Best wishes to you!
Dennis
Dennis 2018 年 7 月 13 日
Your welcome

サインインしてコメントする。

その他の回答 (2 件)

Shantanu Gontia
Shantanu Gontia 2018 年 7 月 11 日
There are two ways you can do this
1. Make the sliderterminal, sliderinitial, sliderthreshold variables global and use them directly in the callbacks without a need of passing them as arguments.
2. In the callback property of the radio buttons, instead of passing the functions initialcutoff, terminalcutoff, thresholdindex, create anonymous functions that call these functions with the required arguments. For instance,
rinitial = uicontrol(bg,'Style','radiobutton','Callback', @(varargin) initialcutoff(sliderthreshold, sliderinitial, sliderterminal));
You can code similarly for the other buttons as well.
  2 件のコメント
Jan
Jan 2018 年 7 月 11 日
Global variables are a bad idea in every case.
Steve Slana
Steve Slana 2018 年 7 月 11 日
Thanks for your help shantanu!
I agree that global variable would easily solve this problem, but I've read in the matlab documentation that global variables are not good programming practice. Since I am new, I am wary of what I am told to be a problem in the future, I'm going to try to stay away from them.
Thank you again for your input, I very much appreciate you taking the time to respond!

サインインしてコメントする。


Jan
Jan 2018 年 7 月 11 日
編集済み: Jan 2018 年 7 月 11 日
You can use one callback for all 3 radio buttons:
handles.p = uipanel;
handles.slider(1) = uicontrol(p, 'Style', 'slider');
handles.slider(2) = uicontrol(p, 'Style', 'slider');
handles.slider(3) = uicontrol(p, 'Style', 'slider');
handles.bg = uibuttonggroup(p);
uicontrol(bg, 'Style', 'radiobutton', 'Callback', {@initial, handles, 1})
uicontrol(bg, 'Style', 'radiobutton', 'Callback', {@initial, handles, 2})
uicontrol(bg, 'Style', 'radiobutton', 'Callback', {@initial, handles, 3})
function initial(RadioH, EventData, handles, Index)
set(handles.slider, 'Visible', 'off');
set(handles.slider(Index), 'Visible', 'on');
end
  1 件のコメント
Steve Slana
Steve Slana 2018 年 7 月 11 日
編集済み: Steve Slana 2018 年 7 月 11 日
Thank you so much for helping me Jan!
This solution works perfectly!

サインインしてコメントする。

カテゴリ

Help Center および File ExchangeInteractive Control and Callbacks についてさらに検索

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by