function [] = trajectoryOutput(pCallbacks)
%TRAJECTORY Summary of this function goes here
%   Detailed explanation goes here

global artoaGui artoaWorkspace;

%% Initialize required variables

windowTitle = [ 'ARTOA4 - Float ' num2str(artoaWorkspace.float.floatname) ' - Trajectory' ];

availableCallbacks = { ...
    'CloseRequestFcn', ...
    'buttonDeleteSingle', ...
    'buttonDeleteAll', ...
    'checkboxMercator', ...
    'checkboxTrackVisible', ...
    'tableGeneratedTracksSelect', ...
    'checkboxShowPositionDates', ...
    'checkboxSynchronizeZoomToaWindow' ...
};

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


%% Initialize trajectory output gui

artoaGui.figures.trajectoryOutput = figure( ...
    'Name', windowTitle, ...
    'NumberTitle', 'off', ...'MenuBar','none', ...
    'Units', 'characters' ...
);

artoaGui.trajectoryOutput = struct();

set( ...
    artoaGui.figures.trajectoryOutput, ...
    'CloseRequestFcn', ...
    pCallbacks.CloseRequestFcn ...
);

%% Setup layout variables
rightSidebarWidth = .15;
rightSidebarLeft = .825;

leftSidebarWidth = .2;
leftSidebarLeft = .015;

%% Setup axes
if ~artoa.data.hasMember(artoaWorkspace, {'trajectoryOutput', 'enableMercatorProjection'})
    artoaWorkspace.trajectoryOutput.enableMercatorProjection = false;
end
artoa.controller.track.trajectoryOutput.setupTrajectoryAxes( ...
    artoaWorkspace.trajectoryOutput.enableMercatorProjection ...
);

% Setup loading trajectory hint
artoaGui.trajectoryOutput.loadingTrajectoryHint = uicontrol( ...
    'Parent', artoaGui.figures.trajectoryOutput, ...
    'Style', 'text', ...
    'String', 'Loading trajectories...', ...
    'FontSize', 8, ...
    'BackgroundColor', [1 1 1], ...
    'Units', 'normalized', ...
    'Visible', 'off' ...
);
% integration into the initialization above somehow does not work, so apply
% this afterwards
artoaGui.trajectoryOutput.loadingTrajectoryHint.Position = [.25 .5 .5 .1];
artoaGui.trajectoryOutput.loadingTrajectoryHint.FontSize = 10;
artoaGui.trajectoryOutput.loadingTrajectoryHint.ForegroundColor = [0 0 0];

%% Generate controls

%% Left sidebar

%% Time divergence to GPS

artoaGui.trajectoryOutput.frameAxesTimeDivergence = uipanel( ...
    'Title', 'Time divergence to GPS', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [leftSidebarLeft, .675, leftSidebarWidth, .3] ...
);

artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence = axes(artoaGui.trajectoryOutput.frameAxesTimeDivergence);
artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence.Position = [.15 .15 .8 .8];
xlabel(artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence, 'Message Date');
ylabel(artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence, 'Time divergence [s]');
grid(artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence, 'on');
artoaGui.trajectoryOutput.axesTrajectoryTimeDivergence.Visible = 'off';

% Setup hint to select trajectory
artoaGui.trajectoryOutput.selectTrajectoryHint = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameAxesTimeDivergence, ...
    'Style', 'text', ...
    'String', 'No trajectory selected', ...
    'FontSize', 8, ...
    'BackgroundColor', [1 1 1], ...
    'Units', 'normalized' ...
);
% integration into the initialization above somehow does not work, so apply
% this afterwards
artoaGui.trajectoryOutput.selectTrajectoryHint.Position = [.1 .5 .8 .1];
artoaGui.trajectoryOutput.selectTrajectoryHint.FontSize = 10;
artoaGui.trajectoryOutput.selectTrajectoryHint.ForegroundColor = [.3 .3 .3];

%% Horizontal velocities

artoaGui.trajectoryOutput.frameAxesHorizontalVelocities = uipanel( ...
    'Title', 'Horizontal Velocities', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [leftSidebarLeft, .3625, leftSidebarWidth, .3] ...
);

artoaGui.trajectoryOutput.axesHorizontalVelocities = axes(artoaGui.trajectoryOutput.frameAxesHorizontalVelocities);
artoaGui.trajectoryOutput.axesHorizontalVelocities.Position = [.15 .15 .8 .8];
xlabel(artoaGui.trajectoryOutput.axesHorizontalVelocities, 'Message Date');
ylabel(artoaGui.trajectoryOutput.axesHorizontalVelocities, 'Velocity [cm/s]');
grid(artoaGui.trajectoryOutput.axesHorizontalVelocities, 'on');
artoaGui.trajectoryOutput.axesHorizontalVelocities.Visible = 'off';

% Setup hint to select trajectory
artoaGui.trajectoryOutput.selectTrajectoryHintHorizontalVelocities = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameAxesHorizontalVelocities, ...
    'Style', 'text', ...
    'String', 'No trajectory selected', ...
    'FontSize', 8, ...
    'BackgroundColor', [1 1 1], ...
    'Units', 'normalized' ...
);
% integration into the initialization above somehow does not work, so apply
% this afterwards
artoaGui.trajectoryOutput.selectTrajectoryHintHorizontalVelocities.Position = [.1 .5 .8 .1];
artoaGui.trajectoryOutput.selectTrajectoryHintHorizontalVelocities.FontSize = 10;
artoaGui.trajectoryOutput.selectTrajectoryHintHorizontalVelocities.ForegroundColor = [.3 .3 .3];

%% Vertical velocities

artoaGui.trajectoryOutput.frameAxesVerticalVelocities = uipanel( ...
    'Title', 'Vertical Velocities', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [leftSidebarLeft, .05, leftSidebarWidth, .3] ...
);

artoaGui.trajectoryOutput.axesVerticalVelocities = axes(artoaGui.trajectoryOutput.frameAxesVerticalVelocities);
artoaGui.trajectoryOutput.axesVerticalVelocities.Position = [.15 .15 .8 .8];
xlabel(artoaGui.trajectoryOutput.axesVerticalVelocities, 'Message Date');
ylabel(artoaGui.trajectoryOutput.axesVerticalVelocities, 'Velocity [mm/s]');
grid(artoaGui.trajectoryOutput.axesVerticalVelocities, 'on');
artoaGui.trajectoryOutput.axesVerticalVelocities.Visible = 'off';

% Setup hint to select trajectory
artoaGui.trajectoryOutput.selectTrajectoryHintVerticalVelocities = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameAxesVerticalVelocities, ...
    'Style', 'text', ...
    'String', 'No trajectory selected', ...
    'FontSize', 8, ...
    'BackgroundColor', [1 1 1], ...
    'Units', 'normalized' ...
);
% integration into the initialization above somehow does not work, so apply
% this afterwards
artoaGui.trajectoryOutput.selectTrajectoryHintVerticalVelocities.Position = [.1 .5 .8 .1];
artoaGui.trajectoryOutput.selectTrajectoryHintVerticalVelocities.FontSize = 10;
artoaGui.trajectoryOutput.selectTrajectoryHintVerticalVelocities.ForegroundColor = [.3 .3 .3];



%% Right sidebar

%% Track list frame

artoaGui.trajectoryOutput.frameTrackList = uipanel( ...
    'Title', 'Generated tracks', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [rightSidebarLeft, .675, rightSidebarWidth, .3] ...
);

columns = { ...
    '', ...
    'No.', ...
    'Tracking Method' ...
};
artoaGui.trajectoryOutput.tableTrackList = uitable( ...
    artoaGui.trajectoryOutput.frameTrackList, ...
    'Units', 'normalized', ...
    'Position', [.05, .05, .9, .9], ...
    'Data', cell(1, length(columns)), ...
    'RowName', [], ...
    'ColumnName', columns, ...
    'ColumnEditable', false, ...
    'ColumnWidth', {20, 30, 110}, ...
    'CellSelectionCallback', pCallbacks.tableGeneratedTracksSelect, ...%pCallbacks.tableSoundSourceOffsetsSelection,... %@(app,event) disp(num2str(event.Indices)) ...
    'CellEditCallback', '' ...%pCallbacks.tableSoundSourceOffsetsEdit ...
);
clear columns;

%% Control buttons frame

artoaGui.trajectoryOutput.frameControlsButtons = uipanel( ...
    'Title', 'Controls', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [rightSidebarLeft .05 rightSidebarWidth .15] ...
);

artoaGui.trajectoryOutput.buttonDeleteSingle = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameControlsButtons, ...
    'String', 'Delete selected', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .6 .8 .3], ...
    'CallBack', pCallbacks.buttonDeleteSingle ...
);

artoaGui.trajectoryOutput.buttonDeleteAll = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameControlsButtons, ...
    'String', 'Delete all', ...
    'Style', 'PushButton', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .1 .8 .3], ...
    'CallBack', pCallbacks.buttonDeleteAll ...
);



%% Generic options

artoaGui.trajectoryOutput.frameGenericOptions = uipanel( ...
    'Title', 'Options', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [rightSidebarLeft .55 rightSidebarWidth .1] ...
);

artoaGui.trajectoryOutput.checkboxUpdateTrackParameterWindow = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameGenericOptions, ...
    'String', 'Update track parameter on selection', ...
    'Tooltip', 'If checked the track parameter of the selected trajectory will be restored in the track parameter window.', ...
    'Style', 'CheckBox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .8 .8 .175], ...
    'CallBack', pCallbacks.checkboxUpdateTrackParameterWindow ...
);


%% Display options

artoaGui.trajectoryOutput.frameDisplayOptions = uipanel( ...
    'Title', 'Display options', ...
    'Units', 'normalized', ...
    'BackgroundColor', 'white', ...
    'Position', [rightSidebarLeft .25 rightSidebarWidth .25] ...
);

artoaGui.trajectoryOutput.checkboxMercator = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameDisplayOptions, ...
    'String', 'Mercator projection', ...
    'Style', 'CheckBox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .8 .8 .175], ...
    'CallBack', pCallbacks.checkboxMercator ...
);

artoaGui.trajectoryOutput.checkboxShowPositionDates = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameDisplayOptions, ...
    'String', 'Show date positions', ...
    'Style', 'CheckBox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .6 .8 .175], ...
    'CallBack', pCallbacks.checkboxShowPositionDates ...
);


artoaGui.trajectoryOutput.checkboxSynchronizeZoomToaWindow = uicontrol( ...
    'Parent', artoaGui.trajectoryOutput.frameDisplayOptions, ...
    'String', 'Sync zoom with TOA plot', ...
    'Style', 'CheckBox', ...
    'FontSize', 8, ...
    'Units', 'normalized', ...
    'Position', [.1 .4 .8 .175], ...
    'CallBack', pCallbacks.checkboxSynchronizeZoomToaWindow ...
);

%% Set current axes to trajectory output
artoaGui.figures.trajectoryOutput.CurrentAxes = artoaGui.trajectoryOutput.axesTrajectoryOutput;


end