Notes:
plotRaceTrack is a function in which I use a couple of plot- and fill-commands.
plotSimulationPredictionInteractable is the main function. Here I plot a racetrack (using plotRaceTrack), then plot 3 trajectories & add 3 buttons and an editbox. The idea is that everytime I push a button, these 3 trajectory-plots change as a result of some parameter changes.
I will add a corresponding code extract below (only first 2 functions, others are completely similar). My problems with it are twofold:
- Currently, I clear the figure made in the main function in order to redraw the racetrack (which isn't actually necessary, but I don't know how to separately clear plots from a figure, and it isn't computationally heavy to redraw, so this does not concern me too much) and update the 3 trajectory plots. Unfortunately, clearing the figure also clears my buttons (uicontrols), which I currently solved by copy pasting the code of the main function. I feel like there should be a more efficient way to do this, but I can't seem to figure out how to store the uicontrols & call them again…
- Minor problem: I currently use the callback function with a lot of input arguments. I thought I could avoid this storing the needed data: guidata(f, data) (in which f = figure in main loop) and unwrapping it in the callback function as data = guidata(hObject) as is described here (fourth option): https://nl.mathworks.com/help/matlab/creating_guis/share-data-among-callbacks.html#bt9p4xi, but I get an error 'Object must be a figure or one of its child objects.', which does not allow me to do so. This is a minor issue, but I feel like it is correlated to the first one, as if I know how to correctly pass the uicontrols to the callback functions, I should also be able to figure out an efficient way to pass the needed data.
Thank you!
function plotSimulationPredictionInteractable(track, start, N, X, Y, predX, predY, refX, refY, colors) w = 0.47; figure; set(gcf, 'units','normalized','outerposition',[0 0 1 1]); plotRaceTrack(track); axis equal; % Start at given starting position
% End at start+1 for now
eind = start+1; plot(refX(start:eind),refY(start:eind), colors(1), 'LineWidth', 2) plot(X(start:eind),Y(start:eind), colors(2), 'LineWidth', 2) plot(predX((eind-1)*N+1:(eind-1)*N+N), predY((eind-1)*N+1:(eind-1)*N+N), '*g', 'MarkerSize', 1); title('Race Track Simulation With Predictions'); xlabel('X (m)'); ylabel('Y (m)'); L(1) = plot(nan, nan, 'color', colors(1)); L(2) = plot(nan, nan, 'color', colors(2)); L(3) = plot(nan, nan, '*g'); legend(L, {'Reference track', 'NonLinear MPC', 'State Predictions'}); % Create a pushbutton to go to next state:
pb1 = uicontrol('style','push',... 'units','normalized',... 'position',[0.3 0.03 0.15 0.05],... 'fontsize',14,... 'string','Next State',... 'callback',{@(src,evnt)pb_next(track, start, eind, N, X, Y, predX, predY, refX, refY, colors, w)}); pb2 = uicontrol('style','push',... 'units','normalized',... 'position',[0.5 0.03 0.15 0.05],... 'fontsize',14,... 'string','Previous State',... 'callback',{@(src,evnt)pb_prev(track, start, eind, N, X, Y, predX, predY, refX, refY, colors, w)}); editBox = uicontrol('Style', 'Edit',... 'units','normalized',... 'String', '',... 'HorizontalAlignment', 'Center',... 'Position', [0.04 0.5 0.05 0.05]); pb3 = uicontrol('style','push',... 'units','normalized',... 'position',[0.04 0.45 0.05 0.05],... 'fontsize',10,... 'string','Change Start',... 'callback',{@(src,evnt)pb_start(track, N, X, Y, predX, predY, refX, refY, colors, w, editBox)});end% Callback function for the pushbutton to go to the next state.
function pb_next(track, start, eind, N, X, Y, predX, predY, refX, refY, colors, w) clf; plotRaceTrack(track); eind = min(length(X)-1,eind+1); plot(refX(start:eind),refY(start:eind), colors(1), 'LineWidth', 2) plot(X(start:eind),Y(start:eind), colors(2), 'LineWidth', 2) plot(predX((eind-1)*N+1:(eind-1)*N+N), predY((eind-1)*N+1:(eind-1)*N+N), '*g', 'MarkerSize', 1); axis equal; title('Race Track Simulation With Predictions'); xlabel('X (m)'); ylabel('Y (m)'); xlim([min(min(X(start:eind)), min(predX((eind-1)*N+1:(eind-1)*N+N)))-w, max(max(X(start:eind)), max(predX((eind-1)*N+1:(eind-1)*N+N)))+w]); ylim([min(min(Y(start:eind)), min(predY((eind-1)*N+1:(eind-1)*N+N)))-w, max(max(Y(start:eind)), max(predY((eind-1)*N+1:(eind-1)*N+N)))+w]); L(1) = plot(nan, nan, 'color', colors(1)); L(2) = plot(nan, nan, 'color', colors(2)); L(3) = plot(nan, nan, '*g'); legend(L, {'Reference track', 'NonLinear MPC', 'State Predictions'}); pb1 = uicontrol('style','push',... 'units','normalized',... 'position',[0.3 0.03 0.15 0.05],... 'fontsize',14,... 'string','Next State',... 'callback',{@(src,evnt)pb_next(track, start, eind, N, X, Y, predX, predY, refX, refY, colors, w)}); pb2 = uicontrol('style','push',... 'units','normalized',... 'position',[0.5 0.03 0.15 0.05],... 'fontsize',14,... 'string','Previous State',... 'callback',{@(src,evnt)pb_prev(track, start, eind, N, X, Y, predX, predY, refX, refY, colors, w)}); editBox = uicontrol('Style', 'Edit',... 'units','normalized',... 'String', '',... 'HorizontalAlignment', 'Center',... 'Position', [0.04 0.5 0.05 0.05]); pb3 = uicontrol('style','push',... 'units','normalized',... 'position',[0.04 0.45 0.05 0.05],... 'fontsize',10,... 'string','Change Start',... 'callback',{@(src,evnt)pb_start(track, N, X, Y, predX, predY, refX, refY, colors, w, editBox)});end
Best Answer