mplayer's frame extraction

[prev] [thread] [next] [lurker] [Date index for 2006/02/21]

From: Simon Wistow
Subject: mplayer's frame extraction
Date: 14:25 on 21 Feb 2006
I want to extract some frames from a movie and mplayer has the necessary 
codec chops to cover it.

Handily it provides a video out codec of 'png' which writes each frame 
as a png. Kudos to mplayer. Kudos. 

Enjoy it though, you weasley bit of software sputum, it's the last 
you'll get.


In my handy dandy wrapper to extract movies into frames I want to 
provide the ability to extract only a range of frames. So we have five 
options


1) $start-$end (i.e 1-$end)
2) $start-$m   
3) $n-$n       (i.e a single frame)
4) $n-$end
5) $n-$m      



The first one is easy - we just extract everything. This, hwoever is 
where it stops being straight forward.

mplayer provides two relevant options: -frames which takes an integer 
and only extracts that many frames. And -ss. Which takes a floating 
point number of seconds offset. 

*sigh*

That's no problem though - we can just get the FPS of the movie subtract 
1 from our start frame and then divide by the FPS to get the start 
second of the frame we want.

Easy. Right?

No.

Let's try it shall we


----------------------------------------------
o Case 1 - $start-$end (i.e 1-$end)
----------------------------------------------

Do nothing.

----------------------------------------------
o Case 2 - $start-$m
----------------------------------------------

% mplayer -frames 1 -vo png test.mov
...
% ls *.png
00000001.png  00000002.png
%

WTF? I asked you for one frame. You gave me two.

% mplayer -frames 2 -vo png test.mov
...
% ls *.png
00000001.png  00000002.png  00000003.png
%

*breathe*

No, it's ok. We can deal with this. We just delete the extra one. 

Right that takes care of cases 1 and 2. Let's try with an offset and 
extracting only 1 frame (i.e case 3).


----------------------------------------------
o Case 3 - $n-$n       (i.e a single frame)
----------------------------------------------

Well, in the case of $start=1 and $end=1 - frame 1 is time offset 0 so 
that's just the case above.

Let's try $start=2 and $end=2.Frame 2 should be at (assuming 24 FPS) at 
time offset 0.04166666667.

% mplayer -ss 0.04166666667 -frames 1 -vo png test.mov
...
% ls *.png
00000001.png  00000002.png
%


ok, well it's generated that extra frame again so all we have to do is 
delete the last one and ...

Oh. Wait. No. the first image is actually frame 1. So we delete that, 
right? 

If only it was that simple. 00000002.png is actually ... frame, err, 4.

Well, what happens if try and get frame 3

% mplayer -ss 0.08333333334 -frames 1 -vo png test.mov
              ^^^^^^^^^^^^^ (3-1/24)

Again we get 2 frames but this time 00000002.png is actually frame 5. 
And 00000001.png is *still* frame 1.

Fortunately this progresses linearly so we can deal fairly sanely with 
case 3 with just 2 special cases for when $n is 1 or 2.


----------------------------------------------
o Case 4 - $n-$end
----------------------------------------------

'Fortunately' enough we have the same issues that we do with case 3 i.e 
the spurious frame 1 always being there and weird jump at the start of 
the frame offset but no matter - we can deal with this.

Again 'just' 2 special cases for frames 1 and 2.

Running tally so far

4 cases + 4 special cases.


----------------------------------------------
o Case 5 - $n-$m
----------------------------------------------

Let's break this down shall we.

=============================================
* 5a) $n == 1
=============================================
Same as Case 1

=============================================
* 5b) $m == $end 
=============================================

Same as Case 4

=============================================
* 5b) $n=2 $m=3
=============================================

Almost the same as Case 3 but with another special case because mplayer 
can't seek to frame 2 because ...

....

....

and this goes on with an ever increasing number of special cases. I 
think I'm up to about 10 at the moment. And my logic, written in tcsh 
(don't ask) is getting ever more complicated. And basically I can't be 
arsed.


Weirdly it turns out to usually be quicker to just dump everything out
and then nuke the stuff you don't want because see because seeking is so 
slow.

So fuck it.


-- 
the problem with private jets is that I don't get airmiles

Generated at 23:00 on 18 Mar 2006 by mariachi 0.52