Skip to content
classdef VerticalHierarchicalGridDraw < GUIBase
%TABLEGRIDDRAW Draw a TableGrid into a uipanel
% Draws a 2D Grid inside a uipanel (Yay!)
properties
my_grid = []
controls = {}
root_controls = [];
gui_params = []
pb_new = []
pb_delete = []
end
methods
function object = VerticalHierarchicalGridDraw(my_grid, gui_params)
if nargin == 1
gui_params = GUIParameters();
end
object.my_grid = my_grid;
object.gui_params = gui_params;
object.root_controls = struct();
object.root_controls.pb_new = -1;
object.root_controls.pb_delete = -1;
my_grid.addlistener('StructureChanged', @(src, event)redraw_and_update_bb(object, src, event));
end
end
methods
function recurse_delete(object, controls)
delete(controls.control);
if ishandle(controls.pb_extend)
delete(controls.pb_extend);
end
if ishandle(controls.cell_controls.pb_new)
delete(controls.cell_controls.pb_new);
delete(controls.cell_controls.pb_delete);
end
for i = 1:size(controls.subgrid, 2)
object.recurse_delete(controls.subgrid{i});
end
end
end
end
function [height, grid_controls, cell_controls] = draw_onto( object, parent_handle, parent_cell, grid, grid_controls, cell_controls, depth, start_height, x, y )
%DRAW_ONTO Draws the controls onto the parent_handle. This function needs to be called everytime an update happens.
% This function draws the entire handle onto the handle. This function
% needs to be called everytime the back table is updated. The class will
% notify when its necessary.
if nargin == 2
%Need to invert y, so need total size
[x, y] = object.get_bounding_box();
[~, object.controls, object.root_controls] = draw_onto(object, parent_handle, [], object.my_grid.grid, object.controls, object.root_controls, 0, 0, x, y);
return ;
end
% First delete an extra controls % First delete an extra controls
for i = size(grid, 2)+1:size(grid_controls, 2)
object.recurse_delete(grid_controls{i});
grid_controls(i) = [];
end
assert( ~(size(grid_controls, 2) > size(grid, 2)), 'Implment delete when necessary.');
height = 0;
for i = 1:size(grid, 2)
if size(grid_controls, 2) >= i
if ishandle(grid_controls{i}.control)
delete(grid_controls{i}.control);
end
else
grid_controls{i} = struct();
grid_controls{i}.subgrid = {};
grid_controls{i}.pb_extend = -1;
grid_controls{i}.cell_controls = struct();
grid_controls{i}.cell_controls.pb_new = -1
grid_controls{i}.cell_controls.pb_delete = -1
end
[new_height, grid_controls{i}.subgrid, grid_controls{i}.cell_controls] = draw_onto( object, parent_handle, grid{i}, grid{i}.grid, grid_controls{i}.subgrid, grid_controls{i}.cell_controls, depth+1, start_height+height, x, y);
new_height = max([new_height object.gui_params.edit_height]);
height = height + new_height;
%Kill the direct access here.
str = grid{i}.get_user_string();
grid_controls{i}.control = uicontrol(parent_handle, 'Style', 'edit', 'Position', [depth*object.gui_params.edit_width, y-((height+start_height)), object.gui_params.edit_width, new_height], 'String', str, 'Callback', @(src,event)GUIHelpers.update_cell(src, event, grid{i}));
if size(grid{i}.grid, 2) == 0
if grid_controls{i}.pb_extend == -1 || ~ishandle(grid_controls{i}.pb_extend)
grid_controls{i}.pb_extend = uicontrol(parent_handle, 'Style', 'pushbutton', 'Position', [(depth+1)*object.gui_params.edit_width, y-((height+start_height)), 40, new_height], 'String', '+', 'Callback', @(src, event)object.my_grid.add_cell(grid{i}, []) );
else
set(grid_controls{i}.pb_extend, 'Position', [(depth+1)*object.gui_params.edit_width, y-((height+start_height)), 40, new_height]);
set(grid_controls{i}.pb_extend, 'Callback', @(src, event)object.my_grid.add_cell(grid{i}, []) );
end
else
if grid_controls{i}.pb_extend ~= -1 && ishandle(grid_controls{i}.pb_extend)
delete(grid_controls{i}.pb_extend);
grid_controls{i}.pb_extend = -1;
end
end
end
if size(grid, 2) ~= 0
if ishandle(cell_controls.pb_delete)
pb_delete = cell_controls.pb_delete;
else
pb_delete = uicontrol(parent_handle, 'Style', 'pushbutton', 'String', 'Remove');
cell_controls.pb_delete = pb_delete;
end
if ishandle(cell_controls.pb_new)
pb_new = cell_controls.pb_new;
else
pb_new = uicontrol(parent_handle, 'Style', 'pushbutton', 'String', 'Add');
cell_controls.pb_new = pb_new;
end
set(pb_delete, 'Position', [depth*object.gui_params.edit_width+80, y-((height+start_height))-20, 80, 20]);
set(pb_delete, 'Callback', @(src, event)object.my_grid.delete_cell(parent_cell, object.my_grid.get_child_cell(parent_cell, object.my_grid.children_count(parent_cell)) ) );
set(pb_new, 'Position', [depth*object.gui_params.edit_width, y-((height+start_height))-20, 80, 20]);
set(pb_new, 'Callback', @(src, event)object.my_grid.add_cell(parent_cell, []));
height = height+20;
else
if ishandle(cell_controls.pb_new)
delete(cell_controls.pb_new);
delete(cell_controls.pb_delete);
end
end
end
function [x, y] = get_bounding_box( object )
%GET_BOUNDING_BOX Gets the size in pixels of the grid.
%Returns the size of the grid (as a box) for layout purposes.
x = object.my_grid.max_width; %Store maximum width
x = object.gui_params.edit_width*x + 40; %Then calculate the pixels.
y = size(object.my_grid.right_most_grid_cells, 2);
y = object.gui_params.edit_height*y + object.my_grid.subgrid_count*20; %Same here.
end
......@@ -40,8 +40,7 @@ switch Action,
file = varargin{2};
try
data = importdata(file);
gui = GUI([],0);
gui.setData(data);
gui = GUI(data, [],0);
gui.init();
catch exception
msgbox(exception.identifier);
......@@ -52,12 +51,12 @@ switch Action,
if isempty(data)
return
end
if ~data.valid
errordlg(...
DAStudio.message('Block Data has been corputed'),...
'Error', 'modal');
return
end
% if ~data.valid
% errordlg(...
% DAStudio.message('Block Data has been corputed'),...
% 'Error', 'modal');
% return
% end
if data.open && ishandle(data.fig)
delete(data.fig);
......@@ -110,30 +109,27 @@ end
if isempty(data)
data = Data();
data.init();
else
if ~data.valid
errordlg(...
DAStudio.message('Block Data has been corputed'),...
'Error', 'modal');
return
end
% if ~data.valid
% errordlg(...
% DAStudio.message('Block Data has been corputed'),...
% 'Error', 'modal');
% return
% end
if data.open
if ishghandle(data.fig)
figure(data.fig);
end
return
end
end
end;
if mode == 1
gui = GUI(blockHandleTTTopMask,1);
gui = GUI(data, blockHandleTTTopMask,1);
elseif mode == 0
gui = GUI([],0);
gui = GUI(data, [],0);
end
gui.setData(data);
gui.init();
if(mode == 1)
set_param(blockHandleTTTopMask,'UserData',data);
......