Stream Your Webcam to a Browser in JavaScript

Tweet

Opera Software recently released version 12 of its flagship web browser. With its latest release, Opera became the first of the major browsers to begin supporting the W3C’s Multimedia Stream API. The Stream API, also referred to as the getUserMedia API, allows the user’s camera and microphone inputs to be streamed to a browser window. Once passed to the browser, the stream is typically used as the “src” attribute of a <video> element. Because the Stream API is still a widely unsupported draft, it is likely to change over time. This post covers the basics of the Stream API. As the draft becomes more stable and widely supported, this post will be expanded upon.

Detecting Support

Currently, Opera is the only browser to support the Stream API. Therefore, it is absolutely necessary to detect whether or not the API is supported before trying to use it. The following function detects stream support by checking for the existence of the navigator object’s getUserMedia() method.

function isStreamSupported() {
  if (navigator.getUserMedia)
    return true;
  else
    return false;
}

The getUserMedia() Method

The Stream API is accessed via the navigator.getUserMedia() method. However, before any multimedia streams can be accessed, the user must grant explicit permission to the browser. When getUserMedia() is called, Opera uses the following dialog box to receive the user’s consent.

Opera Requesting Access to the User's Camera

The syntax for getUserMedia() is shown below. The method takes two mandatory arguments, and an optional third argument. The first argument, “constraints”, is an object that specifies which media streams (ie video and/or audio) are requested by the browser. The second argument, “successCallback”, is a callback function which is executed if getUserMedia() is successful. The resulting media stream object is passed to “successCallback” as its only argument. The optional third argument, “errorCallback”, is a callback function that executes if getUserMedia() fails. For example, a failure occurs if the user does not agree to let the browser access the multimedia streams.

navigator.getUserMedia( constraints, successCallback[, errorCallback] )

Streaming to a <video> Element

The following example shows how getUserMedia() can be used to send a camera stream directly to an HTML <video> element. The example provides play, pause, and stop buttons for controlling the multimedia streams. Note that the “constraints” variable causes the browser to request both audio and video streams.  If you are using Opera, the example is also live online here.

<!DOCTYPE html>
<html lang="en">
<head>
  <title>getUserMedia Example</title>
  <meta charset="UTF-8"/>
  <script>
    window.addEventListener("load", function() {
      var camera = document.getElementById("camera");
      var play = document.getElementById("play");
      var pause = document.getElementById("pause");
      var stop = document.getElementById("stop");
      var constraints = {audio:true, video:true};

      function success(stream) {
        camera.src = stream;
        camera.play();
        disableButtons(true, false, false);
      }

      function failure(error) {
        alert(JSON.stringify(error));
      }

      function disableButtons(disPlay, disPause, disStop) {
        play.disabled = disPlay;
        pause.disabled = disPause;
        stop.disabled = disStop;
      }

      disableButtons(true, true, true);

      if (navigator.getUserMedia)
        navigator.getUserMedia(constraints, success, failure);
      else
        alert("Your browser does not support getUserMedia()");

      play.addEventListener("click", function() {
        disableButtons(true, false, false);
        camera.play();
      }, false);

      pause.addEventListener("click", function() {
        disableButtons(false, true, false);
        camera.pause();
      }, false);

      stop.addEventListener("click", function() {
        disableButtons(true, true, true);
        camera.pause();
        camera.src = "";
      }, false);
    }, false);
  </script>
</head>
<body>
  <button id="play">Play</button>
  <button id="pause">Pause</button>
  <button id="stop">Stop</button>
  <br />
  <video id="camera"></video>
</body>
</html>

Free book: Jump Start HTML5 Basics

Grab a free copy of one our latest ebooks! Packed with hints and tips on HTML5's most powerful new features.

  • http://www.dabasinskas.net Tomas

    Doesn’t work with Opera 12 Alpha for me..

  • http://www.acewebguy.com Ace Webmaster

    Wow. Perfect help for my next project. Thank you

  • http://gotcaption.com/ Simon Males

    I’ve being playing with this as well, and it’s so much fun! I built a little photo snapping site using getUserMedia() and took a photo to celebrate the Opera 12 release (excuse the bird):

    http://gotcaption.com/p/39

    Also note that Opera 12 is also out for Android. It’s great that getUserMedia() has reached mobile devices!

  • Van Luu

    This is really much better than flash. waiting for other main browsers to apply this.

  • http://www.himalini.com anand

    very good article…it helped me alot…

  • Cameron

    Thanks! That is fantastic! I’ve didn’t know Opera support this! Just %&^*-ing fantastic.