Search code examples
matlabplotrotationaxes

Updating plot while maintaining axes rotations?


So far I have a 3d plot that updates in realtime during a Monto-Carlo simulation of a Kessel Run. I want the plot to be rotatable while updating, but with the rotate3d flag enabled, when I call drawnow after updating the plot data, it resets the axes rotation to the default orientation, canceling whatever the user changed it to. My relevant code is as follows:

s = scatter3(pg(:,1), pg(:,2), pg(:,3), 'O', 'filled');
set(s, 'MarkerEdgeColor', 'none', 'MarkerFaceColor', 'k');

hold on

p_x = curr_path(:,1);
p_y = curr_path(:,2);
p_z = curr_path(:,3);

p = plot3(p_x, p_y, p_z);
set(p, 'LineWidth', 2, 'Color', 'k');

p_x = longest.path(:,1);
p_y = longest.path(:,2);
p_z = longest.path(:,3);

p = plot3(p_x, p_y, p_z);
set(p, 'LineWidth', 2, 'Color', 'r');

p_x = shortest.path(:,1);
p_y = shortest.path(:,2);
p_z = shortest.path(:,3);

p = plot3(p_x, p_y, p_z);
set(p, 'LineWidth', 2, 'Color', 'b');

sample_str = sprintf('%d samples', sample);
short_str = sprintf('shortest: %g parsecs', shortest.dist);
long_str = sprintf('longest: %g parsecs', longest.dist);

title(sprintf('%s, %s, %s', sample_str, short_str, long_str));

xlim([-10 10]);
ylim([-10 10]);
zlim([-10 10]);

hold off

drawnow

This is executed every time I update the data being drawn on the plot. What can I add to ensure that the axes rotation is maintained during an update?


Solution

  • I hope I understood you problem right. Well, here goes!

    I suppose the problem is related to using plot3, which apparently resets the view settings of the figure to their defaults.

    I verified this with the following program:

    figure; 
    x = randn(10,3);
    p = plot3(x(:,1), x(:,2), x(:,3));
    drawnow
    
    pause; %// do rotations in the figure GUI, press a button when done
    
    x = randn(10,3);
    p = plot3(x(:,1), x(:,2), x(:,3)); %// rotations reset
    drawnow;
    pause
    

    You can rotate the figure when the pause is active, but when the pause is released and the second call to plot3 made, the rotation settings are reset.

    A solution which avoids the reset is to directly update the XData, YData, and ZData in the already drawn graphics object. This can be achieved as follows:

    figure; 
    x = randn(10,3);
    p = plot3(x(:,1), x(:,2), x(:,3));
    drawnow
    
    pause; %// do rotations in the figure GUI, press a button when done
    
    x = randn(10,3);
    set(p, 'XData', x(:,1), 'YData', x(:,2), 'ZData', x(:,3)); %// no reset!
    drawnow;
    pause
    

    So whatever code you have, use the handle of the graphics object to directly update the line properties to avoid the reset.