help-octave
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Displaying an animation / "movie"


From: Francesco Potorti`
Subject: Re: Displaying an animation / "movie"
Date: Mon, 15 Sep 2008 13:12:17 +0200

>> >Have you tried the 'video' package from Octave-Forge? I've never used
>> >it, but I'm under the impression that it works with fairly recent
>> >versions of ffmpeg.

Allright, waiting for Debian to produce an octave-video package, I wrote
a video.m that can be generally useful (appended).  It can be vastly
improved by adding optional parameters and so on.  I used the mp4
encoder of mmpeg with '-sameq' for maximum output quality.  There are
two drawbacks:
- the only video player that I found which can easily advance the video
  frame-by-frame using the keyboard is avidemux (ok, not a big issue)
- the size of the resulting video is about four times the sum of the png
  frames
so probably some other format should be chosen instead of mp4:
suggestions?

The appended file defines a 'movie' function to be used like this:

octave> mark_as_command movie; figure("visible","off"); movie init
octave> a=zeros(100,100); a(1:20,41:60)=1;
octave> for i=1:100; a=shift(a,1); imshow(a); movie add; endfor
octave> close; movie close

The last command returns the name of the video file produced.  You only
need ffmpeg and a writable current directory.

===File ~/math/octavelib/utils/movie.m======================
function result = movie (action)
  ## Utilities for creating a movie from plots
  ## Francesco Potortì, 2008

  actions = {"init","add","close"};
  if (nargin != 1 || !ischar(action) || !any(strcmp(action, actions)))
    error("argument must be one of:%s", sprintf(" %s",actions{:}));
  endif

  verbose = false;
  movie = "octave_movie";
  persistent frameno = 0;
  persistent mdir = [movie ".d"];
  persistent mpat = [mdir filesep() "%06d.png"];
  persistent mmvi = [movie ".mp4"];

  switch (action)
    case actions{1}             # init a movie
      unlink(mmvi);
      [allgood msg] = mkdir(mdir);
      if (!allgood)
        if (frameno == 0)
          error("while creating dir '%s': %s", mdir, msg);
        else
          cleanmdir(mdir, verbose);
        endif
      endif
      if (verbose) printf("Directory '%s' created.\n", mdir); endif
    case actions{2}             # add a frame
      mfile = sprintf(mpat, ++frameno);
      drawnow("png", mfile);
      if (verbose) printf("Frame '%s' added.\n", mfile); endif
    case actions{3}             # close the movie
      globpat = strrep(sprintf(mpat,0),"0","?");
      mframes = sprintf(" %s", glob(globpat){:});
      cmd = sprintf("ffmpeg -r 5 -sameq -i %s %s 2>&1", mpat, mmvi);
      [status output] = system(cmd);
      if (status != 0)
        error("Creation of movie '%s' containing %d frames failed:\n%s",
              mmvi, frameno, output);
      endif
      if (verbose) printf("Movie '%s' contains %d frames:\n%s",
                          mmvi, frameno, output); endif
      result = mmvi;
      cleanmdir(mdir, verbose);
      frameno = 0;
  endswitch
endfunction


function cleanmdir(mdir, verbose)
  unwind_protect
    save_crr = confirm_recursive_rmdir(false);
    [allgood msg] = rmdir(mdir,"s");
    if (!allgood)
      error("while removing dir '%s': %s", mdir, msg); endif
  unwind_protect_cleanup
    confirm_recursive_rmdir(save_crr);
  end_unwind_protect
  if (verbose) printf("Directory '%s' removed\n", mdir); endif
endfunction
============================================================

-- 
Francesco Potortì (ricercatore)        Voice: +39 050 315 3058 (op.2111)
ISTI - Area della ricerca CNR          Fax:   +39 050 315 2040
via G. Moruzzi 1, I-56124 Pisa         Email: address@hidden
(entrance 20, 1st floor, room C71)     Web:   http://fly.isti.cnr.it/


reply via email to

[Prev in Thread] Current Thread [Next in Thread]