Streaming MPEG-4 Movies From Your Own Server

posted by Stephan Brumme

No Need For YouTube

YouTube is great. Really ! You can find everything you want to watch - and probably everything you don't want to.

On my website http://photos.stephan-brumme.com are the best photos and videos I took while travelling all over world. Everybody from all over the world can watch them - that's intended and obviously the way the internet should work. Nevertheless, these are MY photos and MY videos and I want to be able to remove them if necessary. That's why I don't upload them to www.flickr.com or www.youtube.com.

There is plenty of free space on my (virtual) web server and my contract includes unlimited traffic. Even more important, my server has a better internet connection than I have at home: my 25 MBit/s VDSL connection is 100% saturated when downloading from my server. I'm not sure but I assume my server can easily achieve 100 MBit/s (it's Germany's biggest hoster, by the way). YouTube is much slower and sometimes doesn't even exceed 3-4 MBit/s, especially after 6pm.

HTML5's Video Capabilities

The upcoming HTML5 standard introduced a new <video> tag. All modern browsers (Chrome, Opera, Firefox, Internet Explorer 9+ and even Android/iPhones) can play videos embedded in a website natively without resorting to Flash. Well, almost ...
hide HMTL's 5 video tag <video width="400" height="300" controls preload="metadata" poster="http://photos.stephan-brumme.com/2009/cambodia/MOV01263.jpg"> <source src="http://photos.stephan-brumme.com/2009/cambodia/MOV01263.mp4" type="video/mp4" /> </video>
One of the most efficient video codecs is MPEG-4, also known as AVC or H.264. Most high-definition (HD) stuff is based on MPEG-4, e.g. Blu-Rays. YouTube's HD videos are encoded in the MPEG-4 file format, too.

Creating MPEG-4 Files

I love HandBrake, an all-in-one movie converter that is open source, too. All videos on http://photos.stephan-brumme.com are resized to 640x480 (30 fps) and have a bitrate between 700 and 1000 kbit/s. Lower resolutions are often very blurry even though the videos are actually displayed at 400x300. That means, if I resize to 400x300 during encoding the video quality is worse compared to 640x480 (at the same bitrate). At least in my eyes !


MPEG-4 Available On All Browsers

The only drawback of MPEG-4 is that it is covered by a massive amount of patents. Firefox and Opera aren't willing to support such a proprietary format and doesn't playback MPEG-4 videos natively - it's not a technical matter, it's a political one.

If you have a pre-HTML5 browser or Firefox/Opera, then a Flash player can take over and play MPEG-4 videos. My favorite Flash player is www.flowplayer.org which is free for non-commercial use.
The core components are two SWF files: the player (120k) and the controls (36k) (both links refer to copies on my server). The full download at www.flowplayer.org includes several Javascript files for more convenience but you can get the player working without Javascript.

That's one of my Cambodia videos (remember movie Tomb Raider ?) played through FlowPlayer:



It's 24 seconds long and 2.5 MByte big. Here's the HTML code:
hide HMTL's 5 video tag <object id="flowplayer" width="400" height="300" data="http://photos.stephan-brumme.com/flowplayer-3.2.7.swf" type="application/x-shockwave-flash"> <param name="movie" value="http://photos.stephan-brumme.com/flowplayer-3.2.7.swf" /> <param name="allowfullscreen" value="true" /> <param name="wmode" value="transparent" /> <param name="flashvars" value="config={'clip': {'baseUrl':'http://photos.stephan-brumme.com/2009/cambodia/'}, 'playlist':['MOV01263.jpg',{'url':'MOV01263.mp4', 'autoPlay':false, 'scaling':'fit'}]}" /> </object>
The HTML5 standard explicitly includes a fall-back path if the browser doesn't support the video's file format. The following combination of HTML5 and Flash should do the trick:
hide How It Should Be <video width="400" height="300" controls preload="metadata" poster="http://photos.stephan-brumme.com/2009/cambodia/MOV01263.jpg"> <source src="http://photos.stephan-brumme.com/2009/cambodia/MOV01263.mp4" type="video/mp4" /> <object id="flowplayer" width="400" height="300" data="http://photos.stephan-brumme.com/flowplayer-3.2.7.swf" type="application/x-shockwave-flash"> <param name="movie" value="http://photos.stephan-brumme.com/flowplayer-3.2.7.swf" /> <param name="allowfullscreen" value="true" /> <param name="wmode" value="transparent" /> <param name="flashvars" value="config={'clip':{'baseUrl':'/2009/cambodia/'}, 'playlist':['MOV01263.jpg', {'url':'MOV01263.mp4', 'autoPlay':false, 'scaling':'fit'}]}" /> </object> </video>
But it doesn't work in Firefox or Opera ! These browser support HTML5's <video> but not MPEG-4. They don't revert to the Flash fall-back - to me it looks like a bug but maybe it's actually a feature.
My current work-around is a PHP-based browser check:
hide MPEG4 Browser Switch $nativeMpeg4 = (stripos($_SERVER["HTTP_USER_AGENT"], "Firefox") === false) && (stripos($_SERVER["HTTP_USER_AGENT"], "Opera" ) === false); if ($nativeMpeg4) echo "<video> ... </video>"; else echo "<object> ... </object>";
Some users modify their browser's user-agent string (popular among Opera users) and then my browser detection will fail. Nevertheless, it works great for 99% of all internet surfers.
homepage