recipes : movies : Making a movie from 2-D matrices

Problem

You have a bunch of images and want to turn them into an animation.

Solution

Say you have five 2-D matrices (the images). You turn these into a movie by "stacking" them to form a 3-D matrix. The first two dimensions of your matrix will be the rows and columns of the images. The third dimension is time: the frames of your movie.

%Let's make five frames composed of random data
R1=randn(100);
R2=randn(100);
R3=randn(100);
R4=randn(100);
R5=randn(100);

%Pre-allocate the 3-D matrix 
C=zeros([size(R1),5]); 

%We have a matrix of size 100 by 100 by 5 
>> size(C)
ans =
   100   100     5


%Loop through the 3rd dimension, adding a frame at a time
for ii=1:size(C,3)
   C(:,:,ii)=eval(['R',num2str(ii)]); %This is ugly!
end

The reason pre-allocation is described in a different recipe. The eval statement may be confusing at first. The square brackets are a concatenation operation to build a string that matches the variable name of each frame in turn. The eval statement itself evaluates this text, meaning that it accesses that variable allowing it to be placed into the appropriate location in the 3-D matrix. It's pointing out that using eval statements like this is generally not what you want to be doing: Here's why.

You can display the animation on-screen with the following code.

while 1 %loop indefinitely. Use ctrl-c to break
   for ii=1:size(C,3)
      imagesc(C(:,:,ii))
      axis off
      drawnow
      pause(0.05) %display at about 20 FPS
   end
end
Discussion

It's worth pointing out that the loop with the eval statement isn't very elegant. eval statments usually make poor use of the Matlab language. In practice, a better approach would have been to have the matrices stored in a cell array (R{1}=randn(100)) or even to make the 3-D matrix, C, more directly, without first storing the individual frames somewhere else.

If you're doing this often, you can make the animation displaying loop into its own function. Matlab also contains facilities for acquiring the whole figure window as a frame and turning these into AVI animations. Check it out!