This is a document written using ReMarkable, a shorthand syntax for generating HTML.

{	"date"		:	200906012150,
	"updated"	:	201012191232,
	"tags"		:	["web-dev", "code-is-art"]
}

<section>

# Video for Everybody! #

&__TOC__;

*Video for Everybody is simply a chunk of HTML code* that embeds a video into a website using the HTML5 ``<video>`` element, falling back to Flash automatically without the use of JavaScript or browser-sniffing. It therefore works in RSS readers (no JavaScript), on the iPhone / iPad (don’t support Flash) and on <many browsers and platforms (/&__HREF__;/test.html)>.

Thanks to the rapid adoption of HTML5 video happening right now, Video for Everybody <isn’t the only solution around (//praegnanz.de/html5video/)>. It is not a neatly packaged, fully-featured solution for those unfamiliar with HTML. VfE is for developers who either want something really simple they can quickly use on their blog or websites, or as a good starting point to develop their own custom solution. It does not use JavaScript. Because of this, it <does not work on Android (#android)> versions prior to 2.3 (Gingerbread). That is Google’s fault. If you don’t care about the reasons behind this you should just use a solution like <MediaElement.js (//mediaelementjs.com)> or <VideoJS (//videojs.com)> that do work on older versions of Android.


How It Works (#video-what)
============================================================================================================================
If your browser supports it, HTML5 video is used. No Flash—no crash.

<"iPad demonstrating Video for Everybody playback"
 /&__HREF__;/screenshots/ipad.png>

If HTML5 video is not supported, Adobe Flash is used. _
You can host locally or embed any Flash player of your choice.

fig.	<"Screenshot of Internet Explorer 8 playing video using Adobe Flash"
	 /&__HREF__;/screenshots/flash.jpg>
	
	: Flash fallback in IE8

Finally, if all else fails, a placeholder image is shown and the user can download the video using the links provided.
If the user doesn’t have Flash they are *not* prompted to install it. Users have enough problems with security already without random websites prompting them to install things—and it’s even more annoying for people who don’t want or cannot use Flash anyway. This is one aspect that makes {{VfE|Video for Everybody}} different than any other Flash video embedding method.

fig.	<"Screenshot of IE without QuickTime or Flash installed, displaying a fall back message about the video"
	 /&__HREF__;/screenshots/fallback.jpg>
	
	: Final fallback image, you could use a different image that points to the download links

This is all done *without JavaScript* and requires two video encodes, one Ogg file, and one MP4 file. WebM can optionally be added. Instructions on how to convert your videos to these formats are provided <further down (#video-encode)> this article.

It’s compatible with HTML 4, HTML5 (valid markup), XHTML 1 and additionally also works when served as `application/xhtml+xml`.
¬¬
For a full browser compatibility list, see the <Video for Everybody Test Page (/&__HREF__;/test.html)>.


The Code (#video-code)
============================================================================================================================
Here follows the full source code. It’s very large because it’s fully commented. _
You can easily compact this down (one such example follows afterwards).

To save time you could use the <Video for Everybody generator (//sandbox.thewikies.com/vfe-generator/)> by Jonathan Neal to generate the code snippet according to your options.
¬¬
((Do not miss the <important notes (#notes)> below or you will be kicking yourself after wasting hours trying to get it to work.))

~~~ HTML ~~~>
<!-- first try HTML5 playback: if serving as XML, expand `controls` to `controls="controls"` and autoplay likewise -->
<!-- warning: playback does not work on iOS3 if you include the poster attribute! fixed in iOS4.0 -->
<video width="640" height="360" controls>
	<!-- MP4 must be first for iPad! -->
	<source src="__VIDEO__.MP4" type="video/mp4" /><!-- Safari / iOS video    -->
	<source src="__VIDEO__.OGV" type="video/ogg" /><!-- Firefox / Opera / Chrome10 -->
	<!-- fallback to Flash: -->
	<object width="640" height="360" type="application/x-shockwave-flash" data="__FLASH__.SWF">
		<!-- Firefox uses the `data` attribute above, IE/Safari uses the param below -->
		<param name="movie" value="__FLASH__.SWF" />
		<param name="flashvars" value="controlbar=over&amp;image=__POSTER__.JPG&amp;file=__VIDEO__.MP4" />
		<!-- fallback image. note the title field below, put the title of the video there -->
		<img src="__VIDEO__.JPG" width="640" height="360" alt="__TITLE__"
		     title="No video playback capabilities, please download the video below" />
	</object>
</video>
<!-- you *must* offer a download link as they may be able to play the file locally. customise this bit all you want -->
<p>	<strong>Download Video:</strong>
	Closed Format:	<a href="__VIDEO__.MP4">"MP4"</a>
	Open Format:	<a href="__VIDEO__.OGV">"Ogg"</a>
</p>
<~~~

(((If you would like your video to automatically start playing, check out the sample code on the <test page (/code/video_for_everybody/test.html)>.)))
¬¬
Here’s a compacted version as an example:

~~~ HTML ~~~>
<video width="640" height="360" controls>
	<source src="__VIDEO__.MP4"  type="video/mp4" />
	<source src="__VIDEO__.OGV"  type="video/ogg" />
	<object width="640" height="360" type="application/x-shockwave-flash" data="__FLASH__.SWF">
		<param name="movie" value="__FLASH__.SWF" />
		<param name="flashvars" value="controlbar=over&amp;image=__POSTER__.JPG&amp;file=__VIDEO__.MP4" />
		<img src="__VIDEO__.JPG" width="640" height="360" alt="__TITLE__"
		     title="No video playback capabilities, please download the video below" />
	</object>
</video>
<p>	<strong>Download Video:</strong>
	Closed Format:	<a href="__VIDEO__.MP4">"MP4"</a>
	Open Format:	<a href="__VIDEO__.OGV">"Ogg"</a>
</p>
<~~~

And one that auto plays: (notice the changes “``autoplay``” and “``autostart=true``”)

~~~ HTML ~~~>
<video width="640" height="360" controls autoplay>
	<source src="__VIDEO__.MP4"  type="video/mp4" />
	<source src="__VIDEO__.OGV"  type="video/ogg" />
	<object width="640" height="360" type="application/x-shockwave-flash" data="__FLASH__.SWF">
		<param name="movie" value="__FLASH__.SWF" />
		<param name="flashvars" value="autostart=true&amp;controlbar=over&amp;image=__POSTER__.JPG&amp;file=__VIDEO__.MP4" />
		<img src="__VIDEO__.JPG" width="640" height="360" alt="__TITLE__"
		     title="No video playback capabilities, please download the video below" />
	</object>
</video>
<p>	<strong>Download Video:</strong>
	Closed Format:	<a href="__VIDEO__.MP4">"MP4"</a>
	Open Format:	<a href="__VIDEO__.OGV">"Ogg"</a>
</p>
<~~~

It’s advised you <subscribe to the RSS (/code/rss)> to be kept informed of new releases in case you get caught out by new bugs introduced by vendors **cough**Apple**cough**. The version isn’t &lt;1 for no reason.


IMPORTANT Notes (#notes)
----------------------------------------------------------------------------------------------------------------------------
# (#mime)	Ensure your server is using the correct mime-types. Firefox will *not* play the Ogg video if the
		mime-type is wrong. Place these lines in your `.htaccess` file to send the correct mime-types to browsers
		
		~~~ HTACCESS ~~~>
		AddType video/ogg  .ogv
		AddType video/mp4  .mp4
		AddType video/webm .webm
		<~~~
		
#		Replace «`__VIDEO__.MP4`» with the path to your video encoded to MP4
		(<a warning on using H.264 (#h264)>) and _
		replace «`__VIDEO__.OGV`» with the path to your video encoded to Ogg. _
		Optionally you could also <include a WebM video (#webm)>.
		
#		Replace «`__POSTER__.JPG`» with the path to an image you want to act as a title screen to the video,
		it will be shown before the video plays, and as a representative image when the video is unable to play
		(Also replace “`__TITLE__`” for the poster image’s ``alt`` text). Not all browsers support the ``poster``
		attribute, it’s advisable to encode the poster image into the first frame of your video.
		
		*DO NOT INCLUDE THE ``poster`` ATTRIBUTE (``<video poster="…">``) FOR iOS 3.x SUPPORT.*
		There is a major bug with iOS 3 that means that playback will not work on any HTML5 video tag that
		uses both the ``poster`` attribute and ``<source>`` elements. This was fixed in iOS 4.0, but of
		course for now there will still be a large number of OS 3 users. This bug _does not_ affect use of the
		poster image in the ``flashvars`` parameter, which you should retain
		
#		Replace «`__FLASH__.SWF`» with the path to the Flash video player you are using.
		I use <JW Player (//longtailvideo.com/players/jw-flv-player/)> (((download and place 'player.swf' in the
		right place))), but this could be any Flash resource including YouTube. Sample code for using YouTube can
		be seen on the <Video for Everybody YouTube Test Page (/&__HREF__;/test_yt.html)>
		
# (#buffer)	Safari buffers the video automatically even if `autobuffer` is absent. This has been fixed in WebKit
		nightlies with a change to the HTML5 spec; the “`preload="none"`” attribute on the video element prevents
		autobuffering. A <current bug (https://bugs.webkit.org/show_bug.cgi?id=44010)> in WebKit causes Safari to
		perpetually display “loading” until the play button is clicked
		
#		The iPhone will not autoplay. This is done to save bandwidth which may cost some users, or be limited. _
		It is not a bug, it’s a feature
		
# (#android)	HTML5 video on Android is badly broken. Resolution support varies from one handset to the next (often just
		480x360), the fallback image usually doesn’t show and the code requires
		<special adjustments (//www.broken-links.com/2010/07/08/making-html5-video-work-on-android-phones/)>.
		The Android emulator is completely useless as it doesn’t represent any real hardware and does not play
		HTML5 video. *THERE IS NO WAY TO TEST ON ANDROID WITHOUT A PHYSICAL PHONE. BLAME GOOGLE.*
		
		Android 2.3 (Gingerbread) now finally supports the ``controls`` attribute, so that VfE can work, but this
		still leaves all previous Android versions in the lurch. Use <MediaElement.js (//mediaelementjs.com)> or
		<VideoJS (//videojs.com)> for better Android support.

# (#gzip)	Some web hosts, in trying to save bandwidth, gzip everything by default—including video files!
		In Firefox and Opera, <seeking will not be possible (https://developer.mozilla.org/en/Configuring_servers_for_Ogg_media)> or the video may not play at all if a video file is
		gzipped. If this is occurring to you please check your server / hosts and disable the gzipping of Ogg and
		other media files. You can switch off gzipping for video files in your .htaccess file by adding this line:
		
		~~~ HTACCESS ~~~>
		SetEnvIfNoCase Request_URI \.(og[gv]|mp4|m4v|webm)$ no-gzip dont-vary
		<~~~
		
		With thanks to Bas van Bergen for this tip
		
#		There are some instances where people will simply not be able to view the video inside the web-page
		({e.g.|for example,} Opera Mobile / Mini). It is absolutely essential that you provide download links
		outside of the video to ensure your message gets through

#		A <current bug (https://bugzilla.mozilla.org/show_bug.cgi?id=449358)> in Firefox means that when
		JavaScript is disabled (NoScript for example) the video controls do not display. For now, right-click
		on the video for the controls, use autoplay on your videos or rely on users allowing your site in NoScript

# (#eolas)	The Eolas ‘Click to Activate’ issue affects Flash in Internet Explorer 6 / 7 as the ActiveX controls are
		not inserted using JavaScript—however Microsoft removed ‘Click to Activate’ in a later update patch.
		This issue will not affect users who have run Windows Update.
		
		Please also note that Windows XP originally shipped with Flash v6, and H.264 playback in Flash requires
		v9 or 10. Depending on what Flash video player you use, this may cause problems if you intend to support
		users with out of date Flash versions

# (#camino)	A parsing bug in Camino 2.0 / Firefox 3.0 means that the image element inside the video element will ‘leak’
		outside of the video element. This is not visible however unless some kind of background image or colour is
		applied to that image element. You can stop this by either wrapping the video element in another element or
		modifying the code from “``<source … />``” to “``<source …></source>``”. This works, but will not validate
		as HTML5


Adding Custom Controls (#controls)
----------------------------------------------------------------------------------------------------------------------------
Since VfE doesn’t come with any JavaScript the HTML5 video will use whatever native interface the browser provides. This is in the best interest of the user because it provides an interface best tailored to that device. For example, the iPhone always plays video fullscreen so that the edges of the video are not cut off in the browser and the user does not have to pan around to get it all in view. The iPad provides finger-friendly sized controls.

fig.	<"Two screenshots of the different HTML5 controls in Opera 10.5 and Google Chrome"
	 /&__HREF__;/screenshots/controls.jpg>
	
	: Different native video controls in Opera 10.5 and Google Chrome

Designers however don’t like the inconsistency and would like a unified set of controls. Both <MediaElement.js (//mediaelementjs.com)> and <VideoJS (//videojs.com)> use VfE and custom controls you can style how you please with CSS.


Encoding the Videos (#video-encode)
============================================================================================================================
Full instructions are beyond the scope of this article, please refer to Mark Pilgrim’s <~Video on the Web~ (//diveintohtml5.info/video.html)> article for an excellent introduction to video formats and encoding instructions. As WebM is quite new, here is a quick guide to <encoding WebM video (//videoblog.michaelverdi.com/2011/01/16/making-webm-video/)>.

•	There is no restriction on the resolution of the Ogg video

•	The iPhone can play MOV and MPEG4 videos with a maximum size of 640x480 and only allows the Base Profile for H.264
	(See <Apple’s own instructions (//tinyurl.com/vfe-iphonespecs)> for the specifics). If your desired video is bigger
	than that, please read the <instructions below (#hd)> for how to adjust the code to use hi-res videos whilst
	keeping iPhone compatibility

•	The iPad <can play (//apple.com/ipad/specs/)> H.264 up to 720p, 30 FPS

•	Firefox will *only* play Ogg (<WebM (#webm)> is also supported in Firefox 4),
	and it will *not* degrade to Flash if there is no Firefox-compatible video file

•	For best results I recommend including the poster image as the first frame when you encode the video


Using {{HD|high definition}} video (#hd)
----------------------------------------------------------------------------------------------------------------------------
If you would like to use a larger video than 640x480, you can use a QuickTime reference movie to auto-select between an iPhone compatible version and the full-size video. In QuickTime Pro use the ‘<kbd>File » Export for Web…</kbd>’ option to output a reference movie (you can also use Apple’s <MakeRefMovie (//developer.apple.com/quicktime/quicktimeintro/tools/)> tool for finer control). You’ll have three files along these lines: “`video.mov`”, “`video-desktop.mp4`” (or m4v) and “`video-iphone.mp4`”. Now replace the two ``source`` elements in the code with these three: (substituting the right file paths)

~~~ HTML ~~~>
<source src="video.mov" type="video/mp4"></source>
<source src="video-desktop.mp4" type="video/mp4"></source>
<source src="video.ogv" type="video/ogg"></source>
<~~~

What happens here is that the browser will play the QuickTime reference movie (Safari / iPhone / iPad) which will auto-select between the desktop and iPhone versions of the video automatically. If the MOV format isn’t supported by the browser (Chrome for example), we point to the same MPEG4 video that the QuickTime reference movie uses.


A Warning About H.264 (#h264)
----------------------------------------------------------------------------------------------------------------------------
I made Video for Everybody because since <I don’t have Flash installed (/flash_free_week)> I wanted to create a way websites could provide me access to their videos (currently <needlessly trapped inside Flash (/end_of_vfe)>) without having to lose viewers from older browsers. VfE is not a tool I would use myself (other videos on this site are HTML5/Ogg only) because of the <threat (//0xdeadbeef.com/weblog/2010/01/html5-video-and-h-264-what-history-tells-us-and-why-were-standing-with-the-web/)> that H.264 <represents (//weblogs.mozillazine.org/roc/archives/2010/01/activex_all_ove.html)> to <freedom on the web (//osnews.com/story/23236/)>. Websites that are already serving H.264 video to users using Flash have already made the conscious decision to buy into H.264. I am not making that decision for you with Video for Everybody.

Just be aware that if you decide to use H.264 video for commercial use then you will need to purchase a licence from the MPEG-LA. Be warned that ‘commercial use’ may also include the scenario where your website has advertisements, even though your use of video is unrelated to those adverts. If you are making any any money in any way from a page that also includes an H.264 video, then you should contact the MPEG-LA for help on licencing.

On the 27th of August 2010, the MPEG-LA announced (arguably in response to growing <WebM (#webm)> support) that the terms of “free use” of H.264 Internet broadcast would not change in 2016. This <does not change a thing (//shaver.off.net/diary/2010/08/27/free-as-in-smokescreen/)>.

|	This is similar to Nikon announcing that they will not charge you if you put your pictures up on Flickr, or
|	HP promising that they will never charge you additionally if you photocopy something that you printed on a LaserJet.
|
| Mike Shaver

Using WebM Video (#webm)
----------------------------------------------------------------------------------------------------------------------------
On the 19th of May 2010 <Google released the VP8 codec as open-source and royalty free (//osnews.com/story/23322/BREAKING_Google_Opens_VP8_Codec_Enables_it_on_YouTube)> with the full intent to drive broad adoption via industry backing and switching YouTube over to the new format in the long term. <“WebM” (//webmproject.org)> is a rebranded Matroska container utilising VP8 video and [Ogg] Vorbis audio.

This represents major competition to H.264—Mozilla, Google and Opera have already added support into special builds of their browsers and even Microsoft have <about-faced (//osnews.com/story/23323/Microsoft_Internet_Explorer_9_To_Support_VP8)> on their H.264-only policy and said that IE9 will support WebM—but only if the codec has been installed by the user. Obviously absent from any support is Apple, and this means that unfortunately codec-fragmentation will continue into the foreseeable future so that you will still need to provide more than one video encode.

Adding a WebM video to Video for Everybody is easy, just add it to the source list! It has to go below the MP4 video due to an iPad bug that ignores anything but the first source element, and ideally above the Ogg source so that browsers that play both Ogg and WebM choose the WebM video first. Here is an example source stack:

~~~ HTML ~~~>
<source src="video.mp4"  type="video/mp4"  />
<source src="video.webm" type="video/webm" />
<source src="video.ogv"  type="video/ogg"  />
<~~~

Note the new mime type, which you will have to <add to your server (#mime)>.

As WebM is quite new, here is a quick guide to <encoding WebM video (//michaelverdi.com/2011/01/16/making-webm-video/)>.

On January 11th 2011, Google announced that it would be <removing H.264 support from Chrome (//blog.chromium.org/2011/01/html-video-codec-support-in-chrome.html)>. It is clear that Google’s long-term solution is to transition YouTube to HTML5/WebM. With the release of Firefox 4, a large percentage of browsers will support WebM, and others through the use of installed codecs (Safari and IE9). Only iOS is completely without WebM support at this time.

Please note that you do not _have_ to include WebM video in your HTML5 video tags as both Chrome, Firefox and Opera still support Ogg. WebM will provide you higher quality, and likely wider compatibility in the very near future, but right now it is an optional extra.


Related Projects (#video-related)
============================================================================================================================
If you’ve modified Video for Everybody to do something else, or have created an HTML5 video related project, please <let me know (mailto:kroc@camendesign.com)> and if it upholds the same <principles (/blog/letter_to_mozilla_re_video)> as Video for Everybody, I’ll list it here.

(I will _not_ list projects that cannot play the video in an RSS reader.
Using JavaScript to insert ``<video>`` defeats the entire purpose.)

:: <MediaElement.js (//mediaelementjs.com)>
	Based on Video for Everybody but uses a custom Flash or Silverlight player that mimics the native HTML5 API so that
	interacting with the video from JavaScript is the same regardless of browser. Truly a great piece of work.
	Video controls are doing using HTML / CSS for cross-browser consistency. MediaElement.js also includes support
	for sub-titling and has plugins for popular blogging engines. Its only downside is that it requires jQuery (where
	VideoJS below is library-agnostic).

:: <video.js (//videojs.com)>
	Based on Video for Everybody but adds custom video controls made of HTML that you can style anyway you please with
	a bit of CSS. VideoJS uses JavaScript to patch up browser differences and bugs, so offers much better support than
	Video for Everybody.
	
:: <External Video for Everybody (//open.pages.kevinwiliarty.com/external-video-for-everybody/)>
	A WordPress plugin that provides a shortcode to insert video using Video for Everybody. The author has also
	<provided (//kevinwiliarty.com/dokuwiki/doku.php/open/vfe_bash_script)> an excellent bash script to automate the
	process of encoding the video files.


Acknowledgements (#acknowledgements)
============================================================================================================================
•	Jonathan Neal for the <Video for Everybody generator (//sandbox.thewikies.com/vfe-generator/)>
•	Bas van Bergen for the tip on <gzipped video files (#gzip)>
•	<Steve Haffernan (//steveheffernan.com/)> for <video.js (//videojs.com)>
	and demonstrating the better ``flashvars`` method
•	Val Cohen for spotting the ASP problem with VfE_QT
•	Guido García for Blackberry Bold 9000 / Curve 8900 & Nokia N96 testing
•	Corey Weiner for iPad testing
•	<Zeno Crivelli (//zeno.name)> (<SublimeVideo (//jilion.com/sublime/video)>)
•	Terrell Kelley for spotting the Firefox 3.0 bug with self-closing ``source`` elements
•	<André M. Åslund (//webop.de/users/69)> of <Vorwärts GmbH (//vorwaerts-gmbh.de)> for the current hosting of
	the video files
•	<Mike Hadfield (//volicol.com)> for the <VfE Playback (/link/dasein)> button
•	<Chris Double (//bluishcoder.co.nz)> for previously hosting the video files
•	<LongTail Video (//longtailvideo.com)> for <JWPlayer (//longtailvideo.com/players/jw-flv-player/)>,
	the Flash fallback player
•	Everybody who has promoted it, thank you

</section>