Making an Animation with MESA
17 Dec 2011In my last post, I showed an animation I made with MESA. Here’s a guide explaning how I made it.
The MESA SDK now comes with a movie-making script. You probably want to use that.
Step 0: Install the following software
- MESA - Because we’re going to evolve stars
- Tioga - Bill’s beautiful plotting program
- ImageMagick - Swiss-army knife for image conversion and manipulation
- png2yuv - converts PNG files to uncompressed video, part of MJPEGTools
- x264 - MPEG4 video encoder
- GNU Parallel - take advantage of your multi-core machine
Step 1: Run your MESA model
Set up your MESA inlist to study the scenario of interest. If you want
to make a movie, you’re going to want to have frequent output. Set the
parameters in the controls
namelist in your inlist correspondingly. I
dumped a profile and a log entry at every step :
profile_interval = 1
log_cnt = 1
max_num_profile_models = 30000
Be careful though, disk space could be an issue. I wrote out about 25000 profiles, which ate up about 100 GB.
Step 2: Generate your plots
You don’t have to use Tioga of course; a lot of this guide applies to any set of PNG files. But Tioga makes pretty plots, the scripts to read MESA data already exist, and Bill has a lot of great figures pre-defined. If you’re unfamiliar with Ruby and/or Tioga, this could be the most challenging part.
I made use of the existing movie_batch.rb
scripts that live in :
$MESADIR/star/test_suite/1M_pre_ms_to_wd/star_profile/
$MESADIR/star/test_suite/1M_pre_ms_to_wd/star_history/
Bill recently characterized these scripts as “out-of-date leftovers”, but they still mostly work even if they aren’t officially supported. (I made one minor change, which is to zero-pad the output files to 5 digits instead of 4.)
In movie_batch.rb
, select which figure to generate and the range of
model numbers to generate it for. I just made a pdf for every MESA step;
I’ll choose the subset to include in my movie later. Once you’ve made
these choices or perhaps defined your own new figure, execute:
ruby < movie_batch.rb
and you’ll end up with a set of pdfs in the movie_out
directory, named
plot_ddddd.pdf
, where plot
is a placeholder for the name of whatever
figure you chose and ddddd
is the zero-padded MESA step number.
Step 3: Convert plots to PNG files
Use ImageMagick to convert the .pdf files to .png. For a single file, this is as easy as :
convert -density dpi filename.pdf filename.png
The value you choose for dpi
will set the resolution of the movie. The
size (in pixels) of the resulting png file is the pdf size (in inches)
times dpi
.
If you want to convert many files, you could just write a loop in your shell of choice. But here’s where something like GNU parallel can make your day a whole lot better. (On the other hand, it means there’s less time to duck out and get a cup of coffee.)
Your pdf files have names plot_ddddd.png
. Prepare a list of the a list
of the numbers that you want to convert by whatever means you prefer.
Then just pipe it into parallel :
printf "%05d\n" {0..N} | parallel -j n --eta convert plot_{}.pdf plot_{}.png
and it takes care of the rest. n
specifies how many simultaneous jobs
you want to run. (I set n
to be the number of cores on my machine).
The --eta
flag gives a nice display of how far long it is, how much
time is left, etc.
Around this time, you can also use ImageMagick to do any number of other
things. For example, I wasn’t initially sure what information I wanted
in my movie. I generated several different plots at each step (an HR
diagram, an abundance plot, etc), but each plot was contained in its own
pdf file. Then, after converting each of those pdfs to pngs, I stitched
together the ones that I wanted using the montage
command.
For every MESA step, you should now have one file that displays the information you want to animate.
Step 4: Choose which steps to include
You probably don’t want a frame for every step MESA took. Your movie would speed through the main sequence but creep up the RGB. This choice depends on what you want to illustrate and a little bit on aesthetics, so it’s inevitable that you have to do it at least semi-manually. For me, that meant choosing a simple set of rules to generate a list of the steps that I wanted to include. For example,
- Main sequence (step 700-850): use every step
- Ascending RGB (step 1500-17300): use every 100th step
- and so on …
Regardless of how you do it, the end goal is to have a set of sequentially numbered PNG files.
For those of you who speak Python, I did something like :
Step 5: Join the frames into a movie
png2yuv
decompresses a sequence of PNG files into a YUV4MPEG2 stream.
Do :
png2yuv -f 30 -I p -j frame_%05d.png > movie.y4m
We choose the frame rate with -f
. The -j
specifies the naming
pattern of the png files to read. png2yuv
will stop once it fails to
match the pattern, which is why we want our files to be numbered
sequentially. If you want to begin with a frame that is not number 0,
investigate the -b
option. The -I p
selects progressive scan, that
is no interlacing.
Now we have an (uncompressed) video. Be careful, the y4m
file could be
many GB.
Step 6: Encode the movie
There are many ways to encode video, but I’ve found x264
to be simple
to use and give great results. It just gobbles up y4m
files, which is
of course why we bothered to generate one in the first place. Do :
x264 movie.y4m -o movie.mp4
How easy is that! I’m sure you could go down the rabbit hole and start playing with the infinite options, but I’ve been happy with the defaults. Hopefully, now you have a good looking stellar evolution movie to show in talks, lectures, etc.