如何使用get()更改uielement的回调?

时间:2012-06-22 15:56:02

标签: matlab user-interface callback matlab-guide uielement

一些背景

我使用GUIDE构建的图形和在运行时添加的程序放置复选框的组合创建了一个GUI。复选框位于矩阵中,其中行和列的数量在运行时确定。为了跟踪每个复选框,我使用了cb_r1_c1cb_r7_c10之类的标记约定来表示矩阵中的位置。

我创建了一个函数foo_cb_callback(),它检查传递给它的hObject信息,以确定刚刚单击的复选框的标记。使用此信息(复选框的行和列),此函数知道下一步该做什么。我发现这是一种更清洁,更安全的方式来处理未知数量的复选框的回调。到目前为止,这一战略运作良好。只有一个问题。

问题

我无法更改程序添加的复选框的回调属性,无法正确调用foo_cb_callback()函数。

使用get(objhandles.cb_r1_c1,'callback')

检查现有复选框时是否存在现有回调

返回的变量属于“function_handle”类,并在屏幕上打印一串文本

@(hObject,eventdata)testfuig('checkbox1_Callback',hObject,eventdata,guidata(hObject))

我想将此更改为

@(hObject,eventdata)testfuig('foo_cb_callback',hObject,eventdata,guidata(hObject))

我首先尝试的是

我的第一次尝试是这样的。

callbackstr = '@(hObject,eventdata)testfuig(''foo_cb_callback'',hObject,eventdata,guidata(hObject))';
set(objhandles.cb_r1_c1,'callback',callbackstr);

但这不起作用,因为它只是一个字符串而不是一个function_handle分类对象。看起来应该有一些方法来获取字符串或单元格数组并将其转换为function_handle类。这将是最理想的情况,因为我可以轻松地轻松控制任何元素的回调。

我接下来尝试了什么

由于我已经使用'uicontrol()'函数构建了复选框,因此我尝试在创建时添加回调。

tagstr = 'cb_r1_c1';
uicontrol(objhandles.mainfig, 'Style','checkbox','Tag',tagstr,'callback', 'foo_cb_callback(''hObject''));

这创建了复选框,并且在回调属性中确实有foo_cb_callback(hObject),但是当点击该复选框时,我收到错误??? Undefined function or variable 'hObject'.

所以我放弃了,并解决了它

我发现了两个非理想的解决方案来解决这个问题。第一个是在GUIDE中使用标记cb_hidden创建一个不可见的复选框。然后我就可以使用以下代码了。

callback = get(objhandles.cb_hidden, 'callback');
set(objhandles.cb_r1_c1,'callback',callback);

这正确地将cb_r1_c1的回调设置为与cb_hidden相同的回调。通过这种方式,我能够将所有复选框回调重定向到此虚拟复选框,并从那里调用foo_cb_callback(hObject)

但是,这个解决方案并不理想,因为它需要在GUI中的某个隐藏的复选框。

另一种解决方法

由于我在运行时为每个复选框创建了唯一标记,因此我决定将标记直接写入回调字符串。

tagstr = 'cb_r1_c1';
uicontrol(objhandles.mainfig, 'Style','checkbox','Tag',tagstr,'callback', 'foo_cb_callback(''' tagstr  '''));

这会将回调设置为foo_cb_callback('cb_r1_c1'),正确调用foo_cb_callback()并传递字符串'cb_r1_c1'foo_cb_callback()的前几行看起来像这样

function foo_cb_callback(tag)
global gdata
hObject = gdata.objhandles.(tag);

从那里我可以做任何我能用的理想解决方案。 但是,此解决方案仍然不理想,因为我无法传入变量(非变化字符串除外)。另外,我真的很想知道这样做的正确方法,我相信有一天我会找到它的用途。

2 个答案:

答案 0 :(得分:1)

像这样简单的事情不起作用吗?

function myCallback(src, event)
    disp('myCallback called');
end


set(hObject, 'callback', @myCallback);

答案 1 :(得分:1)

你先尝试了什么,

callbackstr = '@(hObject,eventdata)testfuig(''foo_cb_callback'',hObject,eventdata,guidata(hObject))';
set(objhandles.cb_r1_c1,'callback',callbackstr);

非常接近。您只需要设置一个字符串,而不是一个函数句柄(在您的情况下为匿名函数):

callbackFun = @(hObject,eventdata)testfuig('foo_cb_callback',hObject,eventdata,guidata(hObject));
set(objhandles.cb_r1_c1,'callback',callbackFun);

另外,它应该真的说testfuig吗?