4

I created an UItable in Matlab which I fill with various values and options. It looks like:

enter image description here

the corresponding code is the following:

selector_1 = { 'A'; 'B' ; 'C' };
selector_2 = { 'A.1'; 'A.2'; 'A.3'; ...
               'B.1'; 'B.2'; 'B.3'; ...
               'C.1'; 'C.2'; 'C.3' };

rows = 5;           

f = figure('name','Configuration of output','Position',[200 200 430 25+rows*20],'numbertitle','off','MenuBar','none');

dat =  {'select outputfile...', 'select identifier...', 'Specifier',  'Index'};
dat = repmat(dat,rows,1);
columnname =   {'Output file                   ',...
                'Identifier                    ',...
                'Specifier          ', 'Index'};
columnformat = { {selector_1{:}}, {selector_2{:}}, 'char', 'numeric' };
columneditable =  [true true true true]; 
t = uitable('Units','normalized','Position',...
            [0 0 1 1], 'Data', dat,... 
            'ColumnName', columnname,...
            'ColumnFormat', columnformat,...
            'ColumnEditable', columneditable,...
            'RowName',[]);
set(t, 'Data', dat,'celleditcallback','get(t,''Data'')');

So I run the code and the figure is open. The underlying script has therefore finished. When I now edit the table my uitable object is changed and after I finished I can get my final configuration with:

finalconfig =  get(t,'Data');

But the thing is I need manually type this line, because my script has already finished. If I put this line at the end of my script, I get an error.

So I thought about using the following loop, to detect when I close the table and to store the last configuration

while ~isempty(findobj('name','Configuration of output'))
    % some action
end
finalconfig =  get(t,'Data');

And I tried everything to put inside the loop, the whole script, just the set command including the celleditcallback, and other things, but nothing worked. Either my script get stucked inside the loop or the display of my table is not updated when I edit a value. I also tried drawnow at different positions. How one handles this situation? How can I automatically store my final results? I assume "closing the window" is the best action to detect, as I don't think I could implement a "save" button. I also tried to create a gui using GUIDE but got completely lost, I hope to solve it without.


Edit: I was now able to implement a "save"-button and tried the callback as follows:

uimenu('Label','Save configuration','Callback',@saveConfig);
function saveConfig(~,~)
        output = get(t,'Data',);
        save([pwd 'output.mat'],'output');
end

also I implemented a custom CloseRequestFcn as suggested by Lucius Domitius Ahenobarbus. But then I have either one of the following problems:

1) I define everything as a script, everything works fine, but I need to define functions like @saveConfig (actually my favorite) or @my_Closefcn as a unique function-file in my workspace and I have a hard time to pass the right parameters as dat always remains the same, even though it actually gets changend. (The example from the mathworks site works! But it doesn't need additional parameters.)

2) When I use

function configuration
% my script from above
end

I can implement @saveConfig or @my_Closefcn directly (nested) and I guess the passing of the parameters would work fine. But the editing of my table does not work anymore, throwing the following error:

Error using handle.handle/get

Invalid or deleted object.

Error while evaluating uitable CellEditCallback

How to solve that? Now that I know that I can even add buttons to an uitable I REALLY like to avoid GUIDE. My code above is executable, so I'd be glad if you try it to see what my actual problem is, as it is hard to describe.

4

2 回答 2

3

取决于是否使用 GUIDE:

使用 CloseRequestFcn->

不使用指南:

%write your own CloseRequestFcn and set the figure CloseRequest-Callback to it:
set(gcf,'CloseRequestFcn',@my_closefcn)
%use gcf or the handle of the figure directly

并定义 my_closefcn 包括图形句柄的删除语句,否则图形将不会关闭:)

有关“重新定义 CloseRequestFcn”的更多信息,请参阅文档。

带指南:

您可以通过检查图形来编辑 CloseRequestFcn。有一个名为 CloseRequestFcn 的字段将自动创建函数,您无需关心获取句柄。它看起来像这样:

function figure1_CloseRequestFcn(hObject, eventdata, handles)
% hObject    handle to figure1 (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)

% Hint: delete(hObject) closes the figure
delete(hObject);

现在在删除图形之前,您应该能够获取 uitable 的数据(如果您有句柄),我建议将数据分配给基本工作区,例如:

assignin('base', 'finalTableData', get(myTableHandle,'Data'));

编辑

由于我不够清楚,请参阅此示例:

(在一个脚本中使用)->

function test
h=figure;
x=1:10;
mytable=uitable(h,'Data',x);
set(h,'CloseRequestFcn',@myCloseFcn)
%give a unique Tag:
set(h,'Tag', 'myTag')
set(mytable,'Tag','myTableTag')
end

function myCloseFcn(~,~)
myfigure=findobj('Tag','myTag');
myData=get(findobj(myfigure,'Tag','myTableTag'),'Data')
assignin('base','myTestData',myData)
delete(myfigure)
end

其实你的 Closereq-Callback 的参数不用管,只要你知道怎么找到图的句柄就行了!只需为您的身材/合适的人提供一些您以后能够识别的东西。我使用了“标签”,因为我首先想到的是,但也会有其他参数。

于 2013-10-15T13:21:20.280 回答
0

我只能想到在代码之后直接运行代码或在代码内部运行代码之间的两个区别。

一、范围

也许您实际上是在使用函数,而不是脚本。在这种情况下,问题可能是在您的函数内部,您需要的东西超出了范围。

2.时机

虽然这种情况很少见,但有时计算机似乎已经完成,而实际上它仍然很忙(几毫秒左右)。


以下是通用方法的步骤:

  1. 确保在要插入命令的位置有一条简单的行(1==1例如)
  2. 在该行放置一个断点
  3. 一旦 matlab 在断点处停止,请稍等片刻,然后尝试运行您的命令。

如果它有效,我会打赌第 2 个问题。尝试pause(1)在你的命令之前放置一个,看看它是否有帮助。

如果它不起作用,您可能会遇到第 1 个问题。现在需要找到合适的位置来放置您的命令。如果该命令不能放在代码中的其他位置,也许尝试一个丑陋的evalin(,'base'). 但是,后者确实应该被视为一种解决方法而不是解决方案。

于 2013-10-15T16:02:50.757 回答