Silverlight 4 – Yet More on Capturing Video from Webcams

In this previous post, I wrote some code that took a particular approach to saving uncompressed AVI files (i.e. just frames consisting of device-independent-bitmaps) from the webcam in Silverlight 4 by writing an application that;

  1. Saved video from the webcam to isolated storage in a “raw” file format
  2. Offered a process to take these isolated storage files in “raw” file format and convert it to an AVI file stored outside of isolated storage

I went this route because I’d originally intended to try and compress the video frames ( which would take a tonne of time and needed to be divorced from the capturing of the video ) but I never got there. Consequently, it all got a bit more complex than it perhaps needed to be and it also involved the application requiring elevated trust to do step (2) above.

Over the Christmas break, I got to rewrite that code ( on a very rainy day ) and I’ve another version of the application. It’s embedded in the page below, doesn’t require full-trust and should run in the browser with the Silverlight 4 beta ( if you’ve got a webcam that is, I don’t do much in the way of checking around that 🙂 ).

Note – you might want to right mouse and install this out-of-browser as I notice that the sizing isn’t “quite perfect” when it’s in such a small window as the one below.

This code takes a different approach in that it works something along the lines of;
  1. On start recording, use the file save dialog to grab a file stream from the user securely.
  2. Synchronously write out the RIFF AVI file headers once video capture starts.
  3. As video capture progresses, add each video frame to a queue.
  4. Drain the queue using asynchronous writes from the queue to the file selected by the user.
  5. When video capture ends, patch up a few header entries in the RIFF AVI file headers that can’t be written until capture has ended.

The basic idea being two-fold

  • To avoid doing large synchronous writes as the video frames come in as that might slow the capture process too much
  • To try and drain the queue in steps (3,4) above reasonably quickly with async IO to avoid it getting too big and becoming too much of a memory drain.

It seems to work out reasonably well – naturally, the file being written is still uncompressed video so it is still extremely large. I also chose to write out 32bpp rather than 24bpp so it’s even bigger than last time around although that’d be easy enough to change.

The application runs something like this – you click to switch on the webcam;


you get the persmissions dialog;


that enables the record button ( yes, it’s got the icon for a “play” button, sorry );


clicking that button raises the file dialog;


and then it records with a basic progress indicator;


until you click the stop button.

There’s still at least a couple of outstanding problems with this, especially;

  • I can only get the outputted AVI file to play in Quicktime. I’m not sure what’s wrong with the file I’m writing that makes it unplayable in Media Player but Media Player doesn’t like it right now.

but, once again, if the code’s of use to you then I’ve put the solution here for downloading. It’s not quite-as-shoddy code as the last variant on this theme but it’s quite a way from “production level”.