function [ ] = main(pCallbacks, pTrackingMethods, pInterpolationMethods, pSoundspeedMethods, pOffsetsToCopy, pSoundvelocityToCopy)
%MAIN Contains the definition of main ARTOA4 gui.

global artoaGui;

%% Initialize callbacks

availableCallbacks = { ...
    'CloseRequestFcn', ...
    'WindowButtonDownFcn', ...
    'loadRfb', ...
    'loadInterim', ...
    'loadSoundsourceFile', ...
    'saveRfc', ...
    'saveInterim', ...
    'saveArgoTrajectory', ...
    'saveOptimumTables', ...
    'saveTrajectoryToProfile', ...
    'loadArtoaIni', ...
    'reloadSoundsourceFile', ...
    'reloadRfbFile', ...
    'convertProfilesToRfb', ...
    'quit', ...
    'openEditTemperature', ...
    'openEditPressure', ...
    'openEditTimeOfArrival', ...
    'openShowSatfixEtaToToa', ...
    'openEditOffsets', ...
    'openTrackParameter', ...
    'openTrackTrajectoryOutput', ...
    'switchHideDeletedDataPoints', ...
    'checkboxDopplerCorrection', ... % FIRST ITEM TRACK PARAMETER CALLBACKS
    'checkboxCalculateVariations', ...
    'comboboxInterpolationMethod', ...
    'comboboxSoundspeedMethod', ...
    'checkboxPlotResiduals', ...
    'inputOutputInterpolationInterval', ...
    'inputGapSize', ...
    'tableSoundSourceCombinationsSelection', ...
    'tableSoundSourceCombinationsEdit', ...
    'buttonTrack', ...
    'buttonAddCombination', ...
    'buttonAddCombinationAbove', ...
    'buttonDuplicateCombination', ...
    'buttonRemoveCombination', ...
    'buttonResetAllCombinations', ...
    'tableSoundsourceOffsetsSelect', ... % FIRST ITEM OF OFFSETS
    'tableSoundsourceOffsetsEdit', ...
    'buttonCalculateOffsets', ...
    'checkboxUseOffsets', ...
    'buttonCopyFloatOffsets', ...
    'buttonCopySoundsourcesOffsets', ...
    'buttonAppliedToNan', ...
    'buttonUndoLastCopy' ...
};

for i = 1:length(availableCallbacks) % check if a callback is undefined
    if ~isfield(pCallbacks, availableCallbacks{i})
        pCallbacks.(availableCallbacks{i}) = @(~, ~) false;
    end
end

%% Initialize main window

artoaGui.figures.main = figure( ...
    'Name', 'ARTOA 4', ...
    'NumberTitle', 'off', ...
    'Color', 'white', ...
    'MenuBar', 'none', ...
    'Units', 'characters' ...
);

%% Geometry variables

heightWindow = 60; % [characters]
widthWindow = 129; % [characters]
heightFrame = .4;
heightTrackingFrame = .5;
widthFrame = .95;
spacer = .025;

%% Set window height
artoaGui.figures.main.Position(3) = widthWindow;
artoaGui.figures.main.Position(4) = heightWindow;

%% Set extraordinary callbacks
set(artoaGui.figures.main, 'CloseRequestFcn', pCallbacks.CloseRequestFcn);
set(artoaGui.figures.main, 'WindowButtonDownFcn', pCallbacks.WindowButtonDownFcn);

%% Initialize file menu
artoaGui.main.menus = struct();

artoaGui.main.menus.file = uimenu(artoaGui.figures.main, 'Label', 'File');
% LOAD
loadHandle = uimenu(artoaGui.main.menus.file, 'Label', 'Load');
uimenu( ...
    loadHandle, ...
    'Label', 'ARGOS file', ...%'Callback', 'artoa.controller.loadArgos' ...
    'Enable', 'off' ...
);
uimenu( ...
    loadHandle, ...
    'Label', 'RFB file', ...
    'Callback', pCallbacks.loadRfb ...
);
uimenu( ...
    loadHandle, ...
    'Label', 'Interim file', ...
    'Callback', pCallbacks.loadInterim ...
);
uimenu( ...
    loadHandle, ...
    'Label', 'SoSo file', ...
    'Callback', pCallbacks.loadSoundsourceFile ...
);


% SAVE
artoaGui.main.menus.fileSave = uimenu( ...
    artoaGui.main.menus.file, ...
    'Label', 'Save', ...
    'Enable', 'off' ...
);

uimenu( ...
    artoaGui.main.menus.fileSave, ...
    'Label', 'RFC file', ...
    'Callback', pCallbacks.saveRfc ...
);

uimenu( ...
    artoaGui.main.menus.fileSave, ...
    'Label', 'Interim file', ...
    'Callback', pCallbacks.saveInterim ...
);

uimenu( ...
    artoaGui.main.menus.fileSave, ...
    'Label', 'ARGO trajectory file', ...
    'Callback', pCallbacks.saveArgoTrajectory ...
);

uimenu( ...
    artoaGui.main.menus.fileSave, ...
    'Label', 'Optimum tables', ...
    'Callback', pCallbacks.saveOptimumTables ...
);

uimenu( ...
    artoaGui.main.menus.fileSave, ...
    'Label', 'Trajectory to .profile', ...
    'Callback', pCallbacks.saveTrajectoryToProfile ...
);

% CONVERT
artoaGui.main.menus.fileConvert = uimenu( ...
    artoaGui.main.menus.file, ...
    'Label', 'Convert', ...
    'Enable', 'on' ...
);

uimenu( ...
    artoaGui.main.menus.fileConvert, ...
    'Label', '*.profile to .rfb', ...
    'Callback', pCallbacks.convertProfilesToRfb ...
);

% RELOAD
artoaGui.main.menus.fileReload = uimenu( ...
    artoaGui.main.menus.file, ...
    'Label', 'Reload', ...
    'Enable', 'on' ...
);

% ARTOA INI
artoaGui.main.menus.fileReloadArtoaIni = uimenu( ...
    artoaGui.main.menus.fileReload, ...
    'Label', 'artoa.ini', ...
    'Callback', pCallbacks.loadArtoaIni ...
);

% SOSO FILE
artoaGui.main.menus.fileReloadSoundsourceFile = uimenu( ...
    artoaGui.main.menus.fileReload, ...
    'Label', 'Soundsource file', ...
    'Callback', pCallbacks.reloadSoundsourceFile ...
);

% RFB FILE
artoaGui.main.menus.fileReloadRfbeFile = uimenu( ...
    artoaGui.main.menus.fileReload, ...
    'Label', 'RFB metadata', ...
    'Callback', pCallbacks.reloadRfbFile ...
);

% QUIT
artoaGui.main.menus.fileQuit = uimenu( ...
    artoaGui.main.menus.file, ...
    'Label', 'Quit', ...
    'Callback', pCallbacks.quit ...
);

%% Initialize edit menu

artoaGui.main.menus.edit = uimenu( ...
    artoaGui.figures.main, ...
    'Label', 'Edit', ...
    'Enable', 'off' ...
);

% TEMPERATURE
artoaGui.main.menus.editTemperature = uimenu( ...
    artoaGui.main.menus.edit, ...
    'Label', 'Temperature', ...
    'Callback', pCallbacks.openEditTemperature ...
);

% PRESSURE
artoaGui.main.menus.editPressure = uimenu( ...
    artoaGui.main.menus.edit, ...
    'Label', 'Pressure', ...
    'Callback', pCallbacks.openEditPressure ...
);

% TIME OF ARRIVAL
artoaGui.main.menus.editTimeOfArrival = uimenu( ...
    artoaGui.main.menus.edit, ...
    'Label', 'Time of arrival', ...
    'Callback', pCallbacks.openEditTimeOfArrival, ...
    'Separator', 'on', ...
    'Enable', 'off' ...
);

%% Show menu
artoaGui.main.menus.show = uimenu( ...
    artoaGui.figures.main, ...
    'Label', 'Show', ...
    'Enable', 'on' ...
);

% SATFIX-ETA to TOA
artoaGui.main.menus.showSatfixEtaToToa = uimenu( ...
    artoaGui.main.menus.show, ...
    'Label', 'SATFIX-Eta to Toa', ...
    'Callback', pCallbacks.openShowSatfixEtaToToa, ...
    'Enable', 'off' ...
);

%% Initialize track menu

artoaGui.main.menus.track = uimenu( ...
    artoaGui.figures.main, ...
    'Label', 'Track', ...
    'Enable', 'off' ...
);

% TRAJECTORY OUTPUT
artoaGui.main.menus.trajectoryOutput = uimenu( ...
    artoaGui.main.menus.track, ...
    'Label', 'Trajectory output', ...
    'Callback', pCallbacks.openTrackTrajectoryOutput ...
);


%% Initialize view menu

artoaGui.main.menus.view = uimenu( ...
    artoaGui.figures.main, ...
    'Label', 'View', ...
    'Enable', 'on' ...
);

artoaGui.main.menus.viewHideDeletedDataPoints = uimenu( ...
    artoaGui.main.menus.view, ...
    'Label', 'Hide deleted data points', ...
    'Callback', pCallbacks.switchHideDeletedDataPoints ...
);


%% Version info

gitInfo = getGitInfo();

artoaGui.main.textVersionInfo = uicontrol( ...
    'Parent', artoaGui.figures.main, ...
    'String', artoa.versioning.getVersionString(), ...
    'Style', 'text', ...
    'FontSize', 10, ...
    'Units', 'characters', ...
    'Background', [1 1 1], ...
    'Position', [(widthWindow - 20) 1 20 1] ...
);

%% Float loaded status
artoaGui.main.textLoadedFloat = uicontrol( ...
    'Parent', artoaGui.figures.main, ...
    'String', 'No float loaded.', ...
    'Style', 'text', ...
    'FontSize', 10, ...
    'Units', 'characters', ...
    'HorizontalAlignment', 'left', ...
    'Background', [1 1 1], ...
    'Position', [3 1 80 1] ...
);

%% Track parameter

artoaGui.trackParameter.frameTrackingParameter = uipanel( ...
    'Parent', artoaGui.figures.main, ...
    'Title', 'Tracking Parameter', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [ ...
    spacer ...
    (1 - spacer - heightTrackingFrame) ...
    widthFrame ...
    heightTrackingFrame ...
    ] ...
);

% default geometry values for track parameter
left = .025;
width = .25;
buttonHeight = .3;

% Options frame

artoaGui.trackParameter.frameOptions = uipanel( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'Title', 'Corrections', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [left .75 width .20] ...
);

artoaGui.trackParameter.checkboxDopplerCorrection = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameOptions, ...
    'String', 'Apply Doppler Correction', ...
    'Style', 'checkbox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .5 .9 .3], ...
    'Value', 1, ...
    'CallBack', pCallbacks.checkboxDopplerCorrection ...
);

% Interpolation method frame
artoaGui.trackParameter.frameInterpolationMethod = uipanel( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'Title', 'Input Interpolation Method', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [(2*left + width) .75 width .20] ...
);

artoaGui.trackParameter.comboboxInterpolationMethod = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameInterpolationMethod, ...
    'String', pInterpolationMethods, ...
    'Style', 'popupmenu', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .5 .9 .4], ...
    'CallBack', pCallbacks.comboboxInterpolationMethod ...
);

artoaGui.trackParameter.textGapSize = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameInterpolationMethod, ...
    'String', 'Gap Size [days]', ...
    'Style', 'text', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .1 .5 .3], ...
    'CallBack', '' ...
);

artoaGui.trackParameter.inputGapSize = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameInterpolationMethod, ...
    'String', '10', ...
    'Style', 'edit', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(.7-left) .1 .3 .3], ...
    'CallBack', pCallbacks.inputGapSize ...
);

% Soundspeed method frame

artoaGui.trackParameter.frameSoundspeedMethod = uipanel( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'Title', 'Sound Speed Method', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [(3*left + 2*width) .75 width .20] ...
);

artoaGui.trackParameter.comboboxSoundspeedMethod = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameSoundspeedMethod, ...
    'String', pSoundspeedMethods, ...
    'Style', 'popupmenu', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .5 .9 .4], ...
    'CallBack', pCallbacks.comboboxSoundspeedMethod ...
);

artoaGui.trackParameter.checkboxPlotResiduals = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameSoundspeedMethod, ...
    'String', 'Plot Residuals', ...
    'Enable', 'off', ...
    'Style', 'checkbox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .1 .9 .3], ...
    'CallBack', pCallbacks.checkboxPlotResiduals ...
);

% Output interpolation interval

artoaGui.trackParameter.textOutputInterpolationInterval = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'String', 'Output Interpolation Interval [h]', ...
    'Style', 'text', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(4*left + 3*width) .75 (.5*width) .20], ...
    'CallBack', '' ...
);

artoaGui.trackParameter.inputOutputInterpolationInterval = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'String', '24', ...
    'Style', 'edit', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(5*left + 3*width) .775 (.25*width) .05], ...
    'CallBack', pCallbacks.inputOutputInterpolationInterval ...
);

% Sound source combination table

columns = { ...
    'Use', ...
    'Begin', ...
    'End', ...
    'Sound Sources', ...
    '<html>(Reference)<br>Position Start', ...
    '<html>(Reference)<br>Position End', ...
    '<html>Tracking<br>Method', ...
    '<html>Backward<br>Tracking' ...
};
columnFormat = cell(1, length(columns));
columnFormat{1} = 'logical';
columnFormat{end - 1} = pTrackingMethods;
columnFormat{end} = 'logical';
artoaGui.trackParameter.tableSoundSourceCombinations = uitable( ...
    artoaGui.trackParameter.frameTrackingParameter, ...
    'Units', 'normalized', ...
    'Position', [left, 0.25, (5*left + 3.25*width), 0.45], ...
    'Data', cell(1, length(columns)), ...
    'ColumnName', columns, ...
    'ColumnEditable', true, ...
    'ColumnFormat', (columnFormat), ...
    'CellSelectionCallback', pCallbacks.tableSoundSourceCombinationsSelection,... %@(app,event) disp(num2str(event.Indices)) ...
    'CellEditCallback', pCallbacks.tableSoundSourceCombinationsEdit ...
);
clear columns columnFormat;

% Track buttons frame

artoaGui.trackParameter.frameTrackButtons = uipanel( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'Title', 'Tracking controls', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [(1-left-1.55*width) .025 1.5*width .1] ...
);

artoaGui.trackParameter.buttonTrack = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameTrackButtons, ...
    'String', 'Track', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [2*left+.45 .25 .45 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonTrack ...
);

artoaGui.trackParameter.checkboxCalculateVariations = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameTrackButtons, ...
    'String', 'Calculate variations', ...
    'Style', 'checkbox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .25 .45 2.5*buttonHeight], ...
    'Value', 0, ...
    'CallBack', pCallbacks.checkboxCalculateVariations ...
);

% Combination buttons frame

artoaGui.trackParameter.frameCombinationButtons = uipanel( ...
    'Parent', artoaGui.trackParameter.frameTrackingParameter, ...
    'Title', 'Combination controls', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [left .125 (5*left + 3.25*width) .125] ...
);
factor = .6;

artoaGui.trackParameter.buttonAddCombination = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameCombinationButtons, ...
    'String', 'Add', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .1 factor*width 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonAddCombination ...
);

artoaGui.trackParameter.buttonAddAboveCombination = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameCombinationButtons, ...
    'String', 'Add above selected', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(2*left + factor*width) .1 factor*width 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonAddCombinationAbove ...
);

artoaGui.trackParameter.buttonDuplicateCombination = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameCombinationButtons, ...
    'String', 'Duplicate selected', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(3*left + 2*factor*width) .1 factor*width 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonDuplicateCombination ...
);


artoaGui.trackParameter.buttonRemoveCombination = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameCombinationButtons, ...
    'String', 'Remove selected', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(4*left + 3*factor*width) .1 factor*width 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonRemoveCombination ...
);

artoaGui.trackParameter.buttonResetAllCombinations = uicontrol( ...
    'Parent', artoaGui.trackParameter.frameCombinationButtons, ...
    'String', 'Reset All', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1 - left - factor*width) .1 factor*width 2.5*buttonHeight], ...
    'CallBack', pCallbacks.buttonResetAllCombinations ...
);

clear left width buttonHeight factor;

%% Offset table

artoaGui.editOffsets.frameOffsets = uipanel( ...
    'Parent', artoaGui.figures.main, ...
    'Title', 'Offsets', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [ ...
    spacer ...
    (1 - 2 * spacer - heightFrame - heightTrackingFrame) ...
    widthFrame ...
    heightFrame + 0.025 ...
    ] ...
);

% setup geometry variables
left = 0.03;
fullwidth = 1 - (2 * left);

% Initialize offset table
artoaGui.editOffsets.tableSoundsourceOffsets = uitable( ...
    artoaGui.editOffsets.frameOffsets, ...
    'Units', 'normalized', ...
    'Position', [left, 0.35, fullwidth, 0.65], ...
    'ColumnEditable', true, ...
    'CellSelectionCallback', pCallbacks.tableSoundsourceOffsetsSelect, ...
    'CellEditCallback', pCallbacks.tableSoundsourceOffsetsEdit ...
);

% Optimum offsets frame
artoaGui.editOffsets.frameOptimumOffsets = uipanel( ...
    'Parent', artoaGui.editOffsets.frameOffsets, ...
    'Title', 'Offset controls', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [left .025 fullwidth .3] ...
);

% Setup calculate offsets button

artoaGui.editOffsets.buttonCalculateOffsets = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Calculate offsets', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .25 fullwidth/2 .2], ...
    'CallBack', pCallbacks.buttonCalculateOffsets ...
);

artoaGui.editOffsets.checkboxUseOffsets = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Apply offsets', ...
    'Style', 'checkbox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [left .75 fullwidth/2 .2], ...
    'CallBack', pCallbacks.checkboxUseOffsets ...
);

artoaGui.editOffsets.textFloatOffsetToApplied = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Float', ...
    'Style', 'text', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 4*fullwidth/8) .725 fullwidth/8 .2] ...
);

artoaGui.editOffsets.comboboxFloatOffsetToApplied = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', pOffsetsToCopy, ...
    'Style', 'popupmenu', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 5*fullwidth/8) .725 2*fullwidth/8 .2] ...
);

artoaGui.editOffsets.buttonCopyFloatOffsets = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'to Applied', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 7*fullwidth/8) .725 fullwidth/8 .2], ...
    'CallBack', pCallbacks.buttonCopyFloatOffsets ...
);


artoaGui.editOffsets.textSoundsourcesToApplied = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Soundsources', ...
    'Style', 'text', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 4*fullwidth/8) .5 fullwidth/8 .2] ...
);

artoaGui.editOffsets.comboboxSoundsourcesToApplied = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', pSoundvelocityToCopy, ...
    'Style', 'popupmenu', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 5*fullwidth/8) .5 2*fullwidth/8 .2] ...
);

artoaGui.editOffsets.buttonCopySoundsourcesOffsets = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'to Applied', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + 7*fullwidth/8) .5 fullwidth/8 .2], ...
    'CallBack', pCallbacks.buttonCopySoundsourcesOffsets ...
);

artoaGui.editOffsets.buttonAppliedToNan = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Applied to NaN', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + fullwidth/2) .275 fullwidth/2 .2], ...
    'CallBack', pCallbacks.buttonAppliedToNan ...
);

artoaGui.editOffsets.buttonUndoLastCopy = uicontrol( ...
    'Parent', artoaGui.editOffsets.frameOptimumOffsets, ...
    'String', 'Undo last copy', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [(1.5*left + fullwidth/2) .05 fullwidth/2 .2], ...
    'CallBack', pCallbacks.buttonUndoLastCopy ...
);

end