How to add and delete items on MATLAB Gui - matlab

I'm a new MATLAB GUI user. I'm trying to add various number of items, let's say static texts on the GUI. The number and the position of items will be calculated according to input.
A = uicontrol('Style','pushbutton','Position',[0,0,50,50])
This code adds a pushbutton but I don't know how to use this button after creating that in this way. Does this A have its own handles or hObject? How can I make MATLAB display('someone pressed the button') when I clicked on the button?
Thanks in advance.

A is a uicontrol object. Its property 'callback' defines what action is executed when the button is pressed. Specifically, the property can contain (see here for more detailed information and additional possibilities):
A char vector, which will be executed as code.
Sometimes the char vector this is just a call to a function that does the actual work.
A handle to a function, which will get called with two input arguments, specifying the object and the event.
So, in your case, you can do either of the following:
(Note that the quote whithin the char vector symbols are escaped by duplicating):
set(A, 'callback', 'disp(''Someone pressed the button'')')
(Note that I am defining the as anonymous, and that it does not take any inputs):
dispFun = #()disp('Someone pressed the button')
set(A, 'callback', 'dispFun')
With this approach, the function needs to be in scope when the button is pressed, so that it can be found by the interpreter.
(Note the function must take two inputs):
dispFun = #(o,e)disp('Someone pressed the button')
set(A, 'callback', dispFun)
With this approach there are no scope restrictions. The function handle defines the anonymous function itself, which gets assigned to the callback.
On the other hand, if the function resides in a file, say dispFun_file.m, using
set(A, 'callback', #dispFun_file)
again assigns a handle to the function, but that function is now on a different place. So if the function is modified (or removed from memory with clear functions) the callback will change.

Related

Close uialert figure by button click

Based on a MATLAB example, I added a close command in order to close the uifigure after pressing the OK button. However, in its current state the figure is closed automatically, rather than on the button click. How can I alter the below to have the figure close on click?
Code:
fig = uifigure;
message = {'Fire hazard!','Consider reducing temperature.'};
uialert(fig,message,'Warning',...
'Icon','warning');
close(fig)
You should use a callback in uialert:
fig = uifigure;
message = {'Fire hazard!','Consider reducing temperature.'};
uialert(fig, message, 'Warning', 'Icon', 'warning', ...
'CloseFcn', #(~, ~)close(fig)); % This will be executed after Ok is pressed
The syntax # is the Matlab way to define an anonymous function (Matlab calls these function handles, other languages usually call these lambdas). It allows passing functions as parameters to other functions. If your anonymous function needs to receive parameters, the syntax #(p1, p2, p3) can be used.
In the case of callbacks for uifigures, the callbacks always expect two parameters: fig and event. fig is the figure where the event happened, event is a structure describing the event. In the case above, since all you want to do is close the figure (and you already know which figure you want to close), you can ignore both parameters. The syntax in Matlab to tell that you are receiving a parameter that you purposefully are ignoring is by using a tilde (~) in the position of the parameter. This can be used anywhere actually, including in the definition of normal functions or when unpacking the return value. For example:
[U,~,V] = svd(A)
tells that you are not interested in the singular values of your SVD, only in left and right singular vectors.
You can read more about function handles in the Matlab documentation.

How to create callback function of a uicontrol object which calls the handle object

I have defined an uicontrol pushbutton object and I want to display something in handles when I click on the button. When I try to do that, I get the error Undefined function or variable 'handles'. It does not see the handles or any other object which is in GUI code.
handles.c = 3;
A = uicontrol('Style', 'pushbutton');
A.Callback = display(handles.c)
This code gives the error that I typed above. I may have to give the handle object to the Callback as input but I don't know how to do.
Thanks in advance.
In order to access the handles data structure often referred to in MATLAB's UI documentation, you have to use guidata to set new values and retrieve existing values when in a callback.
So from anywhere, if you want to set the value you'll want to do something like:
handles.c = 3
% Replace `gcf` with the explicit handle to your figure if possible
guidata(gcf, handles)
Then inside of your callback, you can get the current guidata the following way:
function callback(src, event)
handles = guidata(src);
display(handles.c)
end
And then assign this function as the callback to your uicontrol
A = uicontrol('Style', 'pushbutton', 'Callback', #callback);
If you don't want to create a separate callback function and instead insist on a one-liner, you could create an anonymous function to accomplish a similar task
A.callback = #(src, evnt)display(getfield(guidata(src), 'c'))
As you can see, the explicit function is a little easier to understand

Function handle using `set` function MATLAB

I'm working at GUI in MATLAB application.
I use uitable object. Then I find interesting undocumented feature how to sort it's data, select whole row and etc.
I do this way:
% create jhandle to my uitable object
juiTable = findjobj(handles.uitable1,'class','UIScrollPane');
jtable = juiTable(1).getComponent(0).getComponent(0);
%... some my action like this:
jtable.setRowSelectionAllowed(true);
%...
%and now lets try use callback for selected cell in uitable:
juiFunHandle = handle(jtable, 'CallbackProperties');
set(juiFunHandle, 'MousePressedCallback', #CellSelectionCallback);
set(juiFunHandle, 'KeyPressedCallback', #CellSelectionCallback);
That works perfectly.
Now question: how to put multiple parameters to CellSelectionCallback?
I want this function makes some action (makes some button active etc).
For this I try to put GUI handles to it. But how?
My CellSelectionCallback function:
function CellSelectionCallback(juiTable, varargin)
% get it from the example
row = get(juiTable,'SelectedRow')+1;
fprintf('row #%d selected\n', row);
P.S. I see varargin into it. So can I use multiple arguments? How to put it using my set function??
By default, MATLAB callbacks pass two input arguments (the objec that generated the callback and some event data). If you want to pass more (or fewer) arguments to your callback, you can use an anonymous function to accept these two inputs and then call your callback with the desired inputs.
In your case, you could write your anonymous function such that you pass the handles object as an additional input to your callback function
set(juiFunHandle, 'MousePressedCallback', ...
#(src, evnt)CellSelectionCallback(src, evnt, handles));
Then your callback would look something like:
function CellSelectionCallback(jtable, evntdata, handles)

MATLAB : GUI pushbutton call function .m

I have some functions create on matlab (.m). And I would like to call them on an interface GUI : how my push button callback function can call a function .m (which is in the same workspace) ?
Moreover, my function returns some variables so I would like to keep these variables in my workspace in order to access them from other buttons of my interface.
And after, is it possible to put the result of a variable on my interface ?
Thank you in advance,
Best regards
Yes it's possible and is quite simple.
You can call your .m file directly in the pushbutton callback and fetch the results as you would in any other script.
Let's consider a simple example in which you call function A from the callback. Let's say function A outputs 2 arguments, out1 and out2.
In the .m file of function A, the function is defined as follows (input arguments can be anything of course):
function [ou1,out2] = A(Input arguments)
%// code here
end
Then in the pushbutton callback in your GUI, use this syntax to retrieve the outputs of function A and use them:
[B,C] = A(Input arguments); %// Or out1 and out2, the names don't matter here.
Better yet, to share those data with other callbacks from your GUI, you can store the variables in what is called guidata, or the data associated with the GUI. There is a convenient handles structure used to store any kind of data and easily share them between callbacks.
Therefore, in your case you would use:
[handles.B, handles.C] = A(Input arguments)
and as such handles.B and handles.C are accessible from any callback in your GUI. Don't forget to update the handles structure at the end of the callback with this command:
guidata(hObject,handles)
where hObject is the handles to the GUI's figure. For more info about that check the docs here.

Use the output of a callback further in the code

I have a subroutine in my code where I create a GUI for the user to chose a type of analysis:
%% Gives user the choice of replacement method
figure('Units','Normalized','Color','w','Position',[.3 .6 .4 .15],...
'NumberTitle','off','Name','Analysis choice','MenuBar','none');
uicontrol('Style','text','Units','Normalized',...
'Position',[.1 .7 .8 .2],'BackgroundColor','w','String','What replacement method do you want to use?');
uicontrol('Style','pushbutton','Units','Normalized',...
'Position',[.05 .3 .3 .3],'String','Cubic interpolation 24 points',...
'CallBack','cubic_choice'); % cubic_choice.m rotine must be on current folder
uicontrol('Style','pushbutton','Units','Normalized',...
'Position',[.4 .3 .3 .3],'String','Last good data value',...
'CallBack','lgv_choice'); % lgv_choice.m rotine must be on current folder
uicontrol('Style','pushbutton','Units','Normalized',...
'Position',[.75 .3 .2 .3],'String','Linear interpolation',...
'CallBack','li_choice'); % li_choice.m rotine must be on current folder
uiwait;
close;
Further in the code, I have a if loop that analysis the choice that the user made:
if strcmp(inp,'cubic') ...
The problem is, when I press the button "Cubic interpolation 24 points", the callback function doesn't give me the inp variable, i.e., it doesn't appear on the workspace.
The callback function is something like this:
%% Callback script for replacement method
% Cubic interpolation with 24 points method
function [inp] = cubic_choice
inp = 'cubic';
uiresume(gcbf); % resumes the button call
i know that I probably have to use setappdata and getappdata because I already read it in some other thread but I can't get it to work.
Can anyone help me?
Thanks in advance.
Kind regards,
Pedro Sanches
Rather than using a global variable, you imho should check the functions getappdata, setappdata and / or guidata.
Basically, from your callback, you'll have to set your choice at some place you can access it in the rest of the code.
One possibility e.g. is to use set/getappdata as follows:
function cubic_choice()
figHandle = ancestor(gcbf, 'figure');
setappdata(figHandle, 'choice', 'cubic');
uiresume(gcbf);
end
Right after your uiwait call you can then get this property, taking figHandle from the return-value of your figure-call in the first line of your example:
inp = getappdata(figHandle, 'choice');
This is an issue of variable scope and design. inp will not be visible outside the callback function. You are also not "returning it to the workspace" because it is the GUI that is calling you back; no assignment takes place in the workspace.
You could declare global inp both in your workspace and in the callback function, as in
function [inp] = cubic_choice
global inp
inp = 'cubic';
However, you may want to consider responding to the choice directly from within the callback handler. This means, whatever code you have in your if-statement may just as well go directly into your callback function.
Alternatively, if it is really about choices, why not use radio buttons? Then, you could hold on to he handle h returned by uicontrol and query it's state at any later time with get(h, 'value').