Wishful Coding

Didn't you ever wish your
computer understood you?

Make all the Star Wars memes

Normal people watch movies or play games to relax. Me on the other hand, I write code about movies or games to relax.

I came across some memes that posed the question if every line from the Star Wars prequels is meme material, accompanied by a shot from said prequel with a character confirming said question. Easily nerd-sniped as I am, I thought, surely there are lines in the movie that are completely boring?

I figured it should be doable to extract the subtitles from the movie, and use those to generate every possible Star Wars meme. Well, at least all the ones adhering to the format described above.

Extracting the subtitles and timestamps

It turns out srt subtitles are a pretty easy format to grep, but in case the subtitles are embedded inside the video file, or in some other binary format, ffmpeg got you covered. Once you have the srt file, a simple grep command can be used to extract the timestamps.

Note the extra space and lack of decimal point. I’m lazy, and this seemed the easiest way to get a timestamp that refers to a frame when the subtitle is displayed. This sometimes fails, so a mean between the start and end time is obviously better.

ffmpeg -y -txt_format text -i sw.mkv out.srt;
timestamps=$(grep -oE " [0-9]{2}:[0-9]{2}:[0-9]{2}" out.srt);

Generating images for every subtitle line

Again, ffmpeg can do the job, but it requires a bit more than a straight copy-paste from the manual. Let’s go over the options after the full command, that I run inside a for loop.

ffmpeg -y -ss $ts -copyts -i sw.mkv -vf subtitles=sw.mkv -frames:v 1 frames/out$i.jpg;
  • -y answer yes to all prompts.
  • -ss timestamp seek to the specified timestamp. It is important this comes before the input file, otherwise it’ll render the whole movie up to that point. However, doing so changes the timestamps, which we need for the subtitles.
  • -copyts preserve the timestamp. This was a life-saver, thanks to the ffmpeg IRC channel.
  • -i the input file…
  • -vf subtitles=file specifies a filter that “burns” the subtitle into the movie.
  • -frames:v 1 save a single frame to the specified output file

Add the meme caption

With the hard part behind us, now we’re back to straight copy-pasting from the ImageMagick manual. The only interesting bit I added is the pointsize.

convert frames/out$i.jpg -background White -pointsize 32 label:'Insert funny caption' +swap  -gravity Center -append memes/meme$i.jpg;

Putting it all together

The whole script can be found here. I did not expect much, but it was already at frame 6 that I was pleasantly surprised.

Yes, of course

But then I thought

Surely you can do better

So I created a Twitter bot and a search page.

The Twitter bot is just an IFTTT applet that posts an image, served up by a mind-numbingly simple PHP script that I copied from somewhere.

For the search script, I wrote a little Python script that converts the srt file to a csv file that I can import into a MySQL database, which I then query using SELECT * FROM subtitles WHERE MATCH(sub) AGAINST ('words').

That’s all for now.

May the force be with you