6

I attempt to create a movie by looping through frames in MATLAB.

Refering to mathworks.com documentation at http://www.mathworks.com/help/techdoc/ref/movie.html, I've managed to animate a plot. However, issues arise when I attempt to save the movie in an avi file.

Both the avifile and VideoWriter methods from https://stackoverflow.com/a/8038540/818608, resulted in the same errors.

Although the animation runs fine, the saved movie consists of only one fixed frame, and at times, the screen capture includes an overlay of my background web browser.

Thank you in advance.

Below is the code I used, and the frame that's frozen on the avi is linked below.

Z = peaks; surf(Z); 
axis tight
set(gca,'nextplot','replacechildren');

vid = VideoWriter('myPeaks2.avi');
vid.Quality = 100;
vid.FrameRate = 15;
open(vid);
for k = 1:20 
    surf(sin(2*pi*k/20)*Z,Z)
    writeVideo(vid, getframe(gcf));
end
close(vid);

winopen('myPeaks2.avi')

The frame that's frozen on the avi is linked below

Community
  • 1
  • 1
flamearchon
  • 375
  • 2
  • 6
  • 16
  • 2
    Can you give us a snippet of the code you are using to construct the movie, or even better, a small working example? What error are you getting in particular? – mathematical.coffee Dec 21 '11 at 00:33
  • I have updated my post to include code used. The animation runs through the `for` loop and I see all the frames. However, when I open the saved avi, I only see one fixed frame the whole time, and I have included a screenshot of the frame above. – flamearchon Dec 21 '11 at 06:53

6 Answers6

8

I had this (well, a closely related) problem today. This stackoverflow topic was one of the top search engine results, so I thought I'd provide future searchers with some further info.

I was using a VideoWriter object, and calling frame=getframe(fig_handle) to save each frame to the video. As in the question to this topic, only 1 frame was saved. In addition, the background behind the figure could be seen through it, as if the figure was partially transparent.

Changing renders to painters or zbuffer worked. (set(gcf,'renderer','zbuffer') for example.)

I needed openGL rendering though, since the movie used transparency. The key to making this work was to use

opengl('software')

This circumvented what was probably an issue with sending the graphics to and from the video card (I don't know for sure... it worked, and I moved on).

tmpearce
  • 12,523
  • 4
  • 42
  • 60
  • 2
    +1 just ran into this today on my Win8 installation. This didn't occur on my old WinXP machine (I was trying to create an [animated GIF](http://stackoverflow.com/a/11054155/97160) file using `getframe` in a loop). Another solution is to use the undocumented [`hardcopy`](http://stackoverflow.com/a/13078532/97160) – Amro Sep 05 '13 at 23:45
  • 3
    This should be the accepted answer. To summarize, in [@Andrey's answer](http://stackoverflow.com/a/8619687/866007), replace `f = figure();` with `f = figure('renderer', 'zbuffer');`. – Peter D Mar 30 '14 at 19:13
3

This works perfectly for me.

What if you tried putting a drawnow in the loop after the surf? (This flushes all the events and updates your graphics figure).

Could it perhaps be your movie player, or codecs? Could you try VLC/Windows Media Player/etc etc?

mathematical.coffee
  • 55,977
  • 11
  • 154
  • 194
3

Try the following:

    f = figure();
    Z = peaks; surf(Z);
    a = axes('Parent',f);
    axis(a,'tight');
    set(a,'nextplot','replacechildren');
    vid = VideoWriter('myPeaks2.avi');
    vid.Quality = 100;
    vid.FrameRate = 15;
    open(vid);
    for k = 1:20
        surf(a,sin(2*pi*k/20)*Z,Z)
        writeVideo(vid, getframe(f));
    end
    close(vid);

    winopen('myPeaks2.avi')

It contains explicit handles using instead of implicit. Many chaos is caused in Matlab because people tend to use the implicit ones, like "gcf", "gca" which should have been removed completely from the language, IMHO.

Andrey Rubshtein
  • 20,795
  • 11
  • 69
  • 104
0

Have you tried changing your monitor settings to 16 bit color? http://www.mathworks.com/matlabcentral/newsreader/view_thread/257389

  • While this link may answer the question, it is better to include the essential parts of the answer here and provide the link for reference. Link-only answers can become invalid if the linked page changes. – Nazik Aug 30 '13 at 05:10
  • The link is only to show that the solution - changing your monitor settings to 16 bit color - has been shown to work in the past and has been documented on matlabcentral for several years as well as updated recently. – user2145660 Sep 11 '13 at 22:03
0

I also had the problem of only one frame being stored today. Changing the framerate from:

vid.FrameRate = round(0.2*fps/beatfreq);

which evaluated to 3, to simply:

vid.FrameRate = 10;

I can't see why this would make any difference, but it did promptly work after changing this.

EDIT: Turns out it was VLC that can't handle very low framerates. Windows Media Player played it fine no sweat.

0

I managed to get it to work by forcing the figure frames to be invisible, as per http://www.mathworks.com/support/tech-notes/1200/1204.html:

aviobj=avifile('test.avi'); %creates AVI file, test.avi 
hf= figure('visible','off'); %turns visibility of figure off 
hax=axes; 

for k=1:10
  image(k.*peaks,'parent',hax); %puts image in invisible axes 
  set(gca,'Zlim',[-20 20]);  
  aviobj=addframe(aviobj,hf); %adds frames to the AVI file 
end  

aviobj=close(aviobj); %closes the AVI file  
close(hf); %closes the handle to invisible figure 

At the end of the day, no compression was used, as I don't have Indeo5. Is it correct to to say we may rule out compression as the problem?

flamearchon
  • 375
  • 2
  • 6
  • 16