How to animate rectangles - matlab

I am trying to make an animation with circles obtained with the rectangle function in Matlab2013. In order to animate the plot, I tried using clf, drawnow and pause, but it does not seem to work. On the other hand, when I work with dots or lines, I use set and pause and it works fine, but I do not see a way to use these with rectangles.
Here, I show you how I tried to do it with drawnow. There are 1000 time steps, and at every time step I have stored the x and y coordinates of four circles.
%At every time step I would like to plot 4 circles.
PosxProt = rand(1000, 4)
PosyProt = rand(1000, 4)
for i=1:1000
clf
hold on
for j=1:4
rP=0.345; %radius of the circles
cP=[PosxProt(i,j) PosyProt(i,j)]; %center of the circles
rectangle('Position',[cP-rP 2*rP 2*rP],'Curvature',[1 1],'facecolor','r') %plot circle
end
drawnow
pause(0.05)
end

You can parametrize the rectangle using the following equation:
% 2*p and 2*q are the size of the rectangle
t = 0:0.01:1;
x=p*(abs(cos(t))*cos(t)+abs(sin(t))*sin(t))
y=q*(abs(cos(t))*cos(t)-abs(sin(t))*sin(t))
Then plot the rectangle using comet:
comet(x,y)
Also you can find more options for comet here.

Related

How to animate contour plot in Matlab

I have 32x21 matrix with x axis increment of one parameter (2 to 64 in steps of 2) and y axis increment of n other parameter,in steps of two again. I can plot it as contour plot, but I was wondering if there is a way to have contour plot as animation/movie.Thanks
Did you try to place your plot in a for loop which iterates through all the contours? Use drawnow
e.g.
hold on
for ii = 2:2:64
%do your plotting here
%use "pause" if too fast
drawnow
end
This should update the figure every iteration.
Also see this

Matlab: (1) Plotting multiple canvases, (2) holding them separately, (3) montage all

I've got 10 grayscale images. I'd like to plot a simple YELLOW line over each image separately, then show them all over one plot (montage style).
I tried to draw all images first, but that made plotting lines very tricky (X,Y axes weren't standard for plotting over each separate image).
I thought about burning the line over the image, but I don't have the computer vision toolkit (easy functions to do this), otherwise it seemed complicated to both convert the grayscale to color and get it to burn the image.
I thought I might be able to use the function newplot to create a temporary plot space for each image, draw the line with a simple plot(...) call, then save it and just montage(...) all the individual plots at the end.
Is this possible? I've never played with the function newplot or tried to loop through individual plots, saving them up for a call to montage(...) this way, but it seems like a logical/simple approach.
I finally worked it out with subplot, subimage, and plot, using subplot with the position arguments does what I want easily enough. Using subplot kept the axis relative to the subplot I was on so I could plot the line with a standard fplot/plot call. The trick was normalizing the position to percentages vs. thinking of it in terms of pixels.
here's some code demoing it:
% Loop through this code, each time moving the subplot by position
LOOP {
% calculate left & bottom position as percentages (0..1)
subplot( 'Position', [ left bottom (1/cols) (1/rows) ] );
hold on
% (1) Draw the image
subimage(tmpImg, [0 255]);
axis off;
% (2) Plot the line over the original image
F = #(x) polyval(p, x);
fplot(F, [1 dimX 1 dimY], '-y');
}

Plotting shaded deviation of a line in Matlab

I would like to plot a line, and in grey-shaded X% deviation of a signal, in MATLAB. Then, I'd plot another signal and see (visually) how much of the second signal is outside the gret-shaded area.
The task I'd like to get help done is the shaded area: similar to the image attached below.
I am aware of similar solutions with errorbar, but I think this is a much clearer plot to visualize.
If for example I had:
x = 0:0.1:10;
y = 1 + sin(x);
What would the 5% grey-shaded plot of y look like? (that area?)
See this answer for an example: MATLAB fill area between lines
Do you have the error of y at each sample in x? Let's assume you have and the upper bound is in variable yu and the lower bound in variable yl. Then you could plot it using:
x = 0:0.1:10;
y = 1 + sin(x);
% I create some yu and yl here, for the example
yu = y+.1;
yl = y-.1;
fill([x fliplr(x)], [yu fliplr(yl)], [.9 .9 .9], 'linestyle', 'none')
hold all
plot(x,y)
fill(X,Y,ColorSpec,...) plots a polygon with edges specified in the first two parameters. You have to fliplr (flip left-right) the arrays, so that it correctly draws the shape of the area to be filled 'in a circle' around it. The [.9 .9 .9] is the colour specification, in this case a light grey. I removed the edge by setting no line, to make it even more similar to your desired plot. One detail: plot the filled area before plotting y, because the last plotted object goes on top of the others.

How to add a circle to simple matlab figure?

I have a plot of some data (simple 2-d line) and I would like to add circles around some more interesting spots on it. Surprisingly matlab seems to have no simple way to create a physically round circles. I looked on the internet and most answers i found was to either use rectangle('Curvature',[1 1]) or pts = linspace(0,2*pi, 100); plot(sin(pts), cos(pts)); and fixing the aspect ration of a plot to 1. In my case axes have scales that differ by several orders of magnitude so fixing the aspect ration is no option.
I was trying different ways to get the right x/y scale factor but it still seems I'm missing something. My current attempt is:
function hc = circle(x, y, xr)
gca_ylim = get(gca, 'ylim');
gca_xlim = get(gca, 'xlim');
gca_pos = get(gca, 'Position');
gcf_pos = get(gcf, 'Position');
gcf_ar = get(gca, 'DataAspectRatio');
%mod = gca_pos(4)/gca_pos(3) *abs(gca_ylim(2)-gca_ylim(1))/abs(gca_xlim(2)-gca_xlim(1))*gcf_pos(3)/gcf_pos(4);
mod = gca_pos(4)/gca_pos(3)*gcf_ar(2)/gcf_ar(1)*gcf_pos(3)/gcf_pos(4);
yr = xr*mod;
rectangle('Position',[x-xr,y-yr,xr*2,xr*mod*2], 'Curvature',[1,1]);
end
The circles that i got that way are still a bit elongated and I have no idea why. If there is any simple method to get circles in a plot - please share.
PS I know that if I resize plot or add some more stuff to it and change scaling the circles will re-scale with the entire plot. This is not a problem in my case - Figure gets printed out without manual manipulation (no window resizing) and I can add them as the last objects.
Another option:
>> h = plot(rand(1,5),rand(1,5),'o');
>> set(h, 'MarkerSize', 100);
If you want scale invariant circles, you could use scatter command. You can also set the size smaller or larger.
scatter(X,Y,S) draws each circle with the size specified by S. To plot
each circle with equal size, specify S as a scalar. To plot each
circle with a specific size, specify S as a vector with length equal
to the length of X and Y.
http://www.mathworks.com/help/matlab/ref/scatter.html

Polar gridlines on a Cartesian scatter plot

I have a script to create scatter plots (using gscatter) based on x-y data (discrete data points, not continuous) produced by another script. Since these data points are actually the locations of certain objects in a circular space, adding polar grid lines will make the plots more meaningful.
Does anyone know how to show polar grid lines on a Cartesian scatter plot, or am I better off using polar plots?
I once made this script for drawing a polar coordinate system on top of a regular plot. Perhaps it can be useful for you. It is based on this script but simplified to only draw the coordinate system and no data. If this wasn't what you were looking for, check out the linked script, perhaps it can help as well.
Be sure to tweak the radius as needed! I usually disable the axis but it's up to you to fix that if you need another look :)
R=6000; %radius
S=10; %num circ.lines
N=10; %num ang.lines
sect_width=2*pi/N;
offset_angle=0:sect_width:2*pi-sect_width;
%------------------
r=linspace(0,R,S+1);
w=0:.01:2*pi;
clf %remove if needed
hold on
axis equal
for n=2:length(r)
plot(real(r(n)*exp(j*w)),imag(r(n)*exp(j*w)),'k--')
end
for n=1:length(offset_angle)
plot(real([0 R]*exp(j*offset_angle(n))),imag([0 R]*exp(j*offset_angle(n))),'k-')
end
%------------------
You can always use the pol2cart function to generate the polar grid lines.
For example:
function DrawGridLines
x = randn(10);
y = randn(10);
figure;scatter(x(:),y(:));
hold on ;
for angle = 0:20:(360-20)
[x1,y1] = pol2cart( angle / 180 * pi , [0 2]);
plot(x1,y1,'r')
end
for rho = 0:0.1:2
[x1,y1] = pol2cart( 0:0.01:2*pi , rho);
plot(x1,y1,'b')
end
axis equal
end