Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/matlab/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/user-interface/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Matlab 是否有可能防止弹出一个可用的弹出菜单?或者:如何通过单击单元格,返回行&;列索引?_Matlab_User Interface_User Controls_Callback_Matlab Uitable - Fatal编程技术网

Matlab 是否有可能防止弹出一个可用的弹出菜单?或者:如何通过单击单元格,返回行&;列索引?

Matlab 是否有可能防止弹出一个可用的弹出菜单?或者:如何通过单击单元格,返回行&;列索引?,matlab,user-interface,user-controls,callback,matlab-uitable,Matlab,User Interface,User Controls,Callback,Matlab Uitable,对于用户界面,我正在编写一个uitable。用户在第一列中选择一个选项A、B或C,第二列中的子选项取决于在第一列中选择的选项A.1、A.2或A.3或B.1、B.2或B.3或C的相同选项 该表的代码可在附录A中找到 当用户首次定义主选项时,子选项将自动相应地减少为仅有效选项。这是通过为第1列评估CellEditCallback并为第2列重置ColumnFormat实现的。(附录B中的功能modifySelection) 如果用户现在意识到自己犯了错误,需要再次编辑子选项,则ColumnForma

对于用户界面,我正在编写一个
uitable
。用户在第一列中选择一个选项A、B或C,第二列中的子选项取决于在第一列中选择的选项A.1、A.2或A.3B.1、B.2或B.3C的相同选项

该表的代码可在附录A中找到

当用户首次定义主选项时,子选项将自动相应地减少为仅有效选项。这是通过为第1列评估
CellEditCallback
并为第2列重置
ColumnFormat
实现的。(附录B中的功能
modifySelection
) 如果用户现在意识到自己犯了错误,需要再次编辑子选项,则
ColumnFormat
仍将根据先前编辑的主选项进行设置,并且有效选项不可用,除非他再次重新选择主选项。(参见图中的蓝色突出显示)

为了解决这个问题,我还实现了
CellSelectionCallback
调用函数
justifySelection
(在附录B中),该函数通过选择进行检查,在第1列中选择了哪个选项,以再次为第2列提供正确的子选项。但是,由于此回调对选择有反应,我需要选择两次,一次触发
CellSelectionCallback
,另一次实际获取我的选择。对于大桌子,这可能是非常烦人的

所以我的问题是:

是否有办法防止第2列中的弹出菜单弹出,直到它找到第1列的内容,从而立即提供有效的选项?

或:

如何检测鼠标单击单元格并获取行和列索引?但不调用以下选择和弹出操作?

我已经把所有的东西都翻了一遍,但没有找到任何有用的东西。 也许可以使用
按钮DOWNFCN
做些什么,但是如何获取单元格索引呢?那么
BusyAction
属性如何用于我的目的呢

有什么想法吗

我很抱歉提前用这么多代码轰炸您,这已经是最简单的示例,但完全可执行,所以您可以尝试一下


附录A/B

function fancyUitable 

selector_1 = { 'A'; 'B' ; 'C' };
selector_2 = { 'first select first row!' };

h = figure('Position',[200 100 268 120],'numbertitle','off','MenuBar','none');

defaultData =  repmat( {'select main option...', 'select suboption...'} ,5,1);
columnname =   {'Option                             ',...
                'Suboption                          '};
columnformat = { {selector_1{:}}, selector_2 };
columneditable =  [true true]; 
t = uitable(h,'Units','normalized','Position',[0 0 1 1],...
              'Data', defaultData,... 
              'ColumnName', columnname,...
              'ColumnEditable', columneditable,...
              'ColumnFormat', columnformat,...  
              'RowName',[],...
              'CellEditCallback',@modifySelection,...
              'CellSelectionCallback',@justifySelection);

set(h,'Tag','Config_figure')
set(t,'Tag','Config_table')
end

%   **Appendix B**
%   (part of the same function file)


function modifySelection(~,evt_edit)
if evt_edit.Indices(2) == 1
    modifyPopup( evt_edit.Indices(1) );
end
end

function justifySelection(~,evt_select)
try  %to surpress an unimportant error
    if evt_select.Indices(2) == 2
        modifyPopup( evt_select.Indices(1) );
    end
end
end

最后是单个函数
modifyPopup
,它重写了
列格式

function  modifyPopup( row )
    id_group_1 = {'A.1';'A.2';'A.3'};
    id_group_2 = {'B.1';'B.2';'B.3'};
    id_group_3 = {'C.1';'C.2';'C.3'};
    id_default = {'select main option first'};

    myfigure = findobj('Tag','Config_figure');
    config_data = get(findobj(myfigure,'Tag','Config_table'),'Data');
    selector = config_data(row,1);
    selector = selector{1};

    config_format = get(findobj(myfigure,'Tag','Config_table'),'ColumnFormat');
    switch selector
        case 'A'
            config_format{2} = id_group_1';
        case 'B'
            config_format{2} = id_group_2';
        case 'C'
            config_format{2} = id_group_3';
        otherwise
            config_format{2} = id_default;
    end
    set(findobj(myfigure,'Tag','Config_table'),'ColumnFormat',config_format)
end
赏金:为什么只是+50我想这要么不可能,要么答案很简单,只要一个人有了正确的初始想法。我不是在寻找一个使用java对象属性等的复杂解决方案。提前谢谢


我将评论中的讨论包括在这里,以保持概述:

如果您想尝试,可以复制代码并按照以下步骤重现不希望出现的行为:

  • 在第一行中选择主选项A
  • 然后,第一行中的子选项包含选项A.1、A.2和 A.3
  • 选择第二行的主选项B,因此 第二行中的子选项是B.1、B.2和B.3
  • 但是现在您想要更改第一行中的子选项(直接);您希望得到A.1、A.2和A.3选项;但你没有。您将获得B.1、B.2和B.3;-因为您最后选择的主选项是B(尽管在不同的行中)
  • 似乎你不应该寻找最后一个选项,而应该寻找相关的选项。因此,要么确保单击 子选项执行“查找”以查看存在哪个主选项

    这正是我要找的!但我怎么能做到呢如何 检测单击,获取列和行索引,设置正确的
    ColumnFormat
    然后最后让单元格弹出。
    唯一 到目前为止,我看到的可能性是
    CellSelectionCallback
    ,但事实并非如此 在单元格已弹出无效选项后执行。 我需要一种
    点击回调
    ,就像按钮

    或者确保选择主选项仅设置该行的子选项


    这是不可能的,您不能为某一行设置子选项,因为您需要修改
    ColumnFormat
    ,这会影响整个表,而不仅仅是一行。

    解决方案是在GUI中使用带有两个UITables的单元格选择回调。使第一个表保存{'a'、'b'、'c'}的数据,然后在单元格选择回调中,使第二个UITable可见,并根据第一个UITable的单元格选择属性设置其数据。如果你往下看“一个不需要findjobj的小黑客”一行,这个链接应该有你所需要的一切


    虽然我高度赞赏Rody Oldenhuis的努力和解决方案,他绝对值得获奖,但他的解决方案需要对我的代码进行大量修改,因此我一直在尝试寻找更简单的解决方案。在这里,它终于99%的错误免费

    (函数脚本中的所有代码部分)




    显示:


    我不会使用
    uitable
    ;它不适合做这种事情

    我会这样做:

    function GUIdemo
    
        %%// Construct GUI
    
        %// Main figure
        mainFig = figure;
        set(mainFig, 'Color', get(0, 'DefaultUicontrolBackgroundColor'));
    
        %// Create as many blocks as needed. The only thing you have to do is
        %// figure out the "right" positions for each block
        popupHandles = create_ui_blocks([
            0.00  0.50 1.00  0.35
            0.00  0.15 1.00  0.35]);
    
        %// This OK button gathers all selected options, and just prints them.
        uicontrol(...
            'style'   , 'pushbutton',...
            'units'   , 'normalized',...
            'parent'  , mainFig,...
            'position', [0.4 0.01 0.2 0.1],...
            'callback', @(~,~)getData(popupHandles),...
            'string'  , 'OK'...
            );
    
    
        %%// Helper functions
    
        %// Create control blocks. Each block is composed of:
        %// - a uipanel as container
        %// - three radio buttons for the main selection
        %// - a corresponding popup or the secondary selection
        function popupHandles = create_ui_blocks(positions)
    
            %// initialize
            numBlocks = size(positions,1);
    
            panels = zeros(numBlocks,1);
            groups = zeros(numBlocks,1);
            radios = zeros(numBlocks,3);
            popups = zeros(numBlocks,1);
    
            %// Build each block
            for ii = 1:numBlocks
    
                %// The container
                panels(ii) = uipanel(...
                    'parent'  , mainFig,...
                    'position', positions(ii,:)...
                    );
    
                %// The radio buttons
                groups(ii) = uibuttongroup(...
                    'parent'  , panels(ii),...
                    'position', [0.05 0.05 0.45 0.9]...
                    );
                radios(ii,1) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'A',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.66 0.9 0.25]...
                    );
                radios(ii,2) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'B',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.33 0.9 0.25]...
                    );
                radios(ii,3) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'C',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.0 0.9 0.25]...
                    );
    
                %// Initially, nothing's selected
                set(groups(ii), 'SelectedObject',[]);
    
                %// The popups
                popups(ii) = uicontrol(...
                    'style'   , 'popup',...
                    'units'   , 'normalized',...
                    'parent'  , panels(ii),...
                    'position', [0.55 0.4 0.4 0.2],...
                    'string'  , 'Select main option',...
                    'enable'  , 'off'...
                    );
    
                %// On changing radiobutton, correct the string list of the popups
                set(groups(ii),'SelectionChangeFcn', @(~,~)selectionChangeCallback(ii));
    
                %// This is needed by the OK button callback
                popupHandles = popups;
    
            end
    
            %// What happens when clicking a radio button?
            %// NOTE: this is a doubly-nested function
            function selectionChangeCallback(num)
                switch get(groups(num), 'SelectedObject')
                    case radios(num,1)
                        set(popups(num), 'string', {'A.1', 'A.2', 'A.3'}, 'enable', 'on');
                    case radios(num,2)
                        set(popups(num), 'string', {'B.1', 'B.2', 'B.3'}, 'enable', 'on');
                    case radios(num,3)
                        set(popups(num), 'string', {'C.1', 'C.2', 'C.3'}, 'enable', 'on');
                    otherwise
                        %// ...
                end
            end
    
        end
    
        %// What happens when pressing the OK button?
        function data = getData(popupHandles)
            data = char(cellfun(@(x,y)x{y}, ...
                get(popupHandles, 'String'),...
                get(popupHandles, 'Value'),...
                'UniformOutput', false))         %#ok<NOPRT> //
        end
    
    end
    
    布局当然仍然粗糙,但你明白了。当然,单选按钮也可以替换为一个弹出窗口(更紧凑)、三个按钮或任何您喜欢的按钮

    弹出窗口的内容彼此不相关,这正是
    uitable
    方法的问题所在。在这个GUI中,更改单选按钮时,弹出窗口内容的更改可以是即时的,因为您可以更好地控制如何处理更改

    function edit(src,evt)
    
    if evt.Indices(2) == 1
        modifyPopup( src,evt.Indices(1) );
    end
    
    % disables cell selection highlighting, when one jumps to next table,
    % a bit laggy though
    fh = get(src,'parent');
    copyobj(src,fh);
    delete(src);
    
    end
    
    function  modifyPopup( src,row )
        id_group_1 = {'A.1';'A.2';'A.3'};
        id_group_2 = {'B.1';'B.2';'B.3'};
        id_group_3 = {'C.1';'C.2';'C.3'};
        id_default = {'select output file first'};
    
        config_data = get(src,'Data');
        selector = config_data(row,1);
        selector = selector{1};
    
        config_format = get(src,'ColumnFormat');
        switch selector
            case 'A'
                config_format{2} = id_group_1';
            case 'B'
                config_format{2} = id_group_2';
            case 'C'
                config_format{2} = id_group_3';
            otherwise
                config_format{2} = id_default;
        end
        config_data = { selector , 'select suboption...' };  %reset column 2
        set(src,'Data',config_data);
        set(src,'ColumnFormat',config_format);
    end
    
    function addRow(fh,k,lhp)
    selector_1 = { 'A'; 'B' ; 'C' };
    selector_2 = { 'first select first row!' };
    
    defaultData =  {'select main option...', 'select suboption...'};
    columnformat = { {selector_1{:}}, selector_2};
    columneditable =  [true true];
    
    th = uitable(fh,'Units','normalized','Position',[0 1-(k+1)*lhp 1 lhp],...
                  'Data', defaultData,... 
                  'ColumnName', [],...
                  'ColumnWidth', {200 200},...
                  'ColumnEditable', columneditable,...
                  'ColumnFormat', columnformat,...  
                  'RowName',[],...
                  'Tag','value',...
                  'UserData',k,...
                  'SelectionHighlight','off',...
                  'CellEditCallback',@edit);
    end
    
    function store(~,~)
    ui = findobj(0,'Type','uitable','Tag','value');
    L = numel(ui);
    output = cell(L,2);
    order = zeros(L,1);
    for ii=1:L;
        output(ii,:) = get(ui(ii),'Data');
        order(ii)    = get(ui(ii),'UserData');
    end
    [~,idx] = sort(order);    %as order of handles unequals displayed order
    assignin('base','output',output(idx,:));
    end
    
    function GUIdemo
    
        %%// Construct GUI
    
        %// Main figure
        mainFig = figure;
        set(mainFig, 'Color', get(0, 'DefaultUicontrolBackgroundColor'));
    
        %// Create as many blocks as needed. The only thing you have to do is
        %// figure out the "right" positions for each block
        popupHandles = create_ui_blocks([
            0.00  0.50 1.00  0.35
            0.00  0.15 1.00  0.35]);
    
        %// This OK button gathers all selected options, and just prints them.
        uicontrol(...
            'style'   , 'pushbutton',...
            'units'   , 'normalized',...
            'parent'  , mainFig,...
            'position', [0.4 0.01 0.2 0.1],...
            'callback', @(~,~)getData(popupHandles),...
            'string'  , 'OK'...
            );
    
    
        %%// Helper functions
    
        %// Create control blocks. Each block is composed of:
        %// - a uipanel as container
        %// - three radio buttons for the main selection
        %// - a corresponding popup or the secondary selection
        function popupHandles = create_ui_blocks(positions)
    
            %// initialize
            numBlocks = size(positions,1);
    
            panels = zeros(numBlocks,1);
            groups = zeros(numBlocks,1);
            radios = zeros(numBlocks,3);
            popups = zeros(numBlocks,1);
    
            %// Build each block
            for ii = 1:numBlocks
    
                %// The container
                panels(ii) = uipanel(...
                    'parent'  , mainFig,...
                    'position', positions(ii,:)...
                    );
    
                %// The radio buttons
                groups(ii) = uibuttongroup(...
                    'parent'  , panels(ii),...
                    'position', [0.05 0.05 0.45 0.9]...
                    );
                radios(ii,1) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'A',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.66 0.9 0.25]...
                    );
                radios(ii,2) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'B',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.33 0.9 0.25]...
                    );
                radios(ii,3) = uicontrol(...
                    'style'   , 'radio',...
                    'units'   , 'normalized',...
                    'string'  , 'C',...
                    'parent'  , groups(ii),...
                    'position', [0.05 0.0 0.9 0.25]...
                    );
    
                %// Initially, nothing's selected
                set(groups(ii), 'SelectedObject',[]);
    
                %// The popups
                popups(ii) = uicontrol(...
                    'style'   , 'popup',...
                    'units'   , 'normalized',...
                    'parent'  , panels(ii),...
                    'position', [0.55 0.4 0.4 0.2],...
                    'string'  , 'Select main option',...
                    'enable'  , 'off'...
                    );
    
                %// On changing radiobutton, correct the string list of the popups
                set(groups(ii),'SelectionChangeFcn', @(~,~)selectionChangeCallback(ii));
    
                %// This is needed by the OK button callback
                popupHandles = popups;
    
            end
    
            %// What happens when clicking a radio button?
            %// NOTE: this is a doubly-nested function
            function selectionChangeCallback(num)
                switch get(groups(num), 'SelectedObject')
                    case radios(num,1)
                        set(popups(num), 'string', {'A.1', 'A.2', 'A.3'}, 'enable', 'on');
                    case radios(num,2)
                        set(popups(num), 'string', {'B.1', 'B.2', 'B.3'}, 'enable', 'on');
                    case radios(num,3)
                        set(popups(num), 'string', {'C.1', 'C.2', 'C.3'}, 'enable', 'on');
                    otherwise
                        %// ...
                end
            end
    
        end
    
        %// What happens when pressing the OK button?
        function data = getData(popupHandles)
            data = char(cellfun(@(x,y)x{y}, ...
                get(popupHandles, 'String'),...
                get(popupHandles, 'Value'),...
                'UniformOutput', false))         %#ok<NOPRT> //
        end
    
    end
    
    data =
        A.1
        B.1