getappdata / setappdata does not work for me?

9 次查看(过去 30 天)
I am trying to improve my code by adopting 'better' programming practices. I want to start using into the setappdata functions and looked into the documentation and, on the face of it, it seems like a no-brainer but there are some frustrating catches I'm not getting? Here are the first few lines of my current script :
global Diam ListeImages ah handleImage ValuePopup ColorCircle_ab cb_sRGB;
figImage = figure;
Tmp = 1;
setappdata(figImage,'ValuePopup1',Tmp);
cb_sRGB = true;
As I understand it, to use setappdata requires some existing 'graphic object' in the input arguments? Fine. So, let's create an empty figure object, called 'figImage'. Then, pass it some 'element' like 'ValuePopup', along with its 'value'. So far so good? (no compiler complain, here) As you can see, this is declared on the very first lines of the script so it's as 'global' as I can get. Then, further down, in some function, I have this code :
function DisplayImage(imageIn)
global img ListeImages Inner ValuePopup ColorCircle_ab cb_sRGB;
Tmp = getappdata(figImage,'ValuePopup1');
Naturally, this does not work? I get a nice 'Invalid or deleted object' error. What am I missing?
The documentation says: "The graphics object must be accessible from within the functions you plan to store and retrieve the data.". How on earth should I make the 'object' accessible from within my function? I tried adding figImage to my globals (but that would be stupid?) like so :
global figImage Diam ListeImages ah handleImage ValuePopup ColorCircle_ab cb_sRGB;
and then, in my function definition :
function DisplayImage(imageIn)
global figImage img ListeImages Inner ValuePopup ColorCircle_ab cb_sRGB;
But as soon as the compiler gets to this line :
set(figImage, 'Name', 'AfficheImage_2022_02_03.m');
I still get an 'Invalid or deleted object.' error. Somehow, I'm not going the correct way about this.
Sadly, there isn't much documentation on this function for me to chew on...

采纳的回答

Jan
Jan 2022-2-16
编辑:Jan 2022-2-16
After the line
figImage = figure;
the variable figImage contains the handle of the figure. If you want to use this handle in a function, you have to provide it as input argument:
function main
figH = figure;
myVar = rand
setappdata(figH, 'myVar', myVar); % Store variable in figure
subFunction(figH);
end
function subFunction(figH)
myVar = getappdata(figH, 'myVar');
disp(myVar);
plot(1:10);
end
Usually the variables stored by setappdata() are used by callbacks of the figure:
function main
figH = figure;
myVar = rand;
setappdata(figH, 'myVar', myVar); % Store variable in figure
uicontrol(figH, 'Style', 'pushbutton', 'String', 'Click!', ...
'Callback', @myCallback);
end
function myCallback(buttonH, EventData)
figH = ancestor(buttonH, 'figure');
myVar = getappdata(figH, 'myVar');
disp(myVar);
end
Alternatively you could provide the handle of the figure as 3rd input argument:
... as above
uicontrol(figH, 'Style', 'pushbutton', 'String', 'Click!', ...
'Callback', {@myCallback, figH});
function myCallback(buttonH, EventData, figH)
% Not needed then: figH = ancestor(buttonH, 'figure');
The idea of setappdata is to store data inside a figure (or any other gui element), instead of using global variables. But if you use the root object, this is exactly the same as globals:
setappdata(groot, 'myVar', rand)
This has the same püroblem as globals: All functions can overwrite this variable. e.g. if you run multiple instances of the same GUI or if you run third-party software, which uses the same names by accident.
In your case the messge "Invalid or deleted object" means, that the variable figImage is still existing, but contains the handle of an already deleted figure or it is empty. Seeing your posted code, I cannot guess, why this is the case.

更多回答(1 个)

Cris LaPierre
Cris LaPierre 2022-2-16
编辑:Cris LaPierre 2022-2-16
I thnk the better way is to pass the figure object into your function as an input parameter. I think your issue is due to you setting a property 'ValuePopup' but getting a property named 'Valuepopup1'. Probably just a simple typo.
Here is a simple example.
figImage = figure;
Tmp = 1;
setappdata(figImage,'ValuePopup',Tmp);
% call the function
DisplayImage(figImage)
getTmp = 1
function DisplayImage(figImage)
getTmp = getappdata(figImage,'ValuePopup')
end
  2 个评论
Roger Breton
Roger Breton 2022-2-16
Boy! I feel egg on my face... The actual code I ran was indeed using :
setappdata(figImage,'ValuePopup1',Tmp);
I'm sorry about that typo (I corrected it in my post). But I understand from your code, as well as from Jan's, that what's implicit in Matlab's documentation about making objects accessible from within functions is to pass the figure handle as parameter everywhere. That ought to be made explicit in the documentation, for poor souls like me...
Cris LaPierre
Cris LaPierre 2022-2-16
Your approach of using a global also works, and if you hadn't had that typo, you never would have posted your question. It's just that globals are often not the best way to share variables.

请先登录,再进行评论。

类别

Help CenterFile Exchange 中查找有关 Get Started with Financial Instruments Toolbox 的更多信息

标签

产品


版本

R2021b

Community Treasure Hunt

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

Start Hunting!

Translated by