title: HTML5 Mirroring webcam canvas
body: <p>I'm trying to take a webcam feed - (landscape format), cut out the middle bit (portrait format) and have it render to a canvas so that it fills the screen portrait 1080px by 1920px (for this I scale the bit I cut out by 3.8). I then need to flip this canvas so the image is mirrored. I've succeeded in cutting out the middle bit, and rendering this to the canvas... I just cant figure out how to flip it.</p>
  
  <p><strong>Edit</strong></p>
  
  <p>Thank you to all the people who have pointed me at context.scale(-1, 1) - my problem is, I'm already using scale... I think my issues are to do with saving the context, but everything I try has failed to work?</p>
  
  <pre><code>&lt;script&gt;
         // Put event listeners into place
          window.addEventListener("DOMContentLoaded", function() {
              // Grab elements, create settings, etc.
              var canvas = document.getElementById("canvas"),
                  context = canvas.getContext("2d"),
                  video = document.getElementById("video"),
                  videoObj = { 
                      video: {
                          mandatory: {
                              minWidth: 1280,
                              minHeight: 720,
                              /*Added by Chad*/
                              maxWidth: 1280,
                              maxHeight: 720
                          }
                      }
                  },
                  errBack = function(error) {
                      console.log("Video capture error: ", error.code); 
                  };
  
              // Put video listeners into place
              if(navigator.getUserMedia) { // Standard
                  navigator.getUserMedia(videoObj, function(stream) {
                      video.src = stream;
                      video.play();
                  }, errBack);
              } else if(navigator.webkitGetUserMedia) { // WebKit-prefixed
                  navigator.webkitGetUserMedia(videoObj, function(stream){
                      video.src = window.URL.createObjectURL(stream);
                      video.play();
                  }, errBack);
              } else if(navigator.mozGetUserMedia) { // WebKit-prefixed
                  navigator.mozGetUserMedia(videoObj, function(stream){
                      video.src = window.URL.createObjectURL(stream);
                      video.play();
                  }, errBack);
              }
  
              /*
                  video : video source tag
                  320,0 : the shift coords
                  320,180 : the canvas size
                  0,0 : no shift in the canvas
                  640,360 : important ! it’s the native resolution of video source
              */
              context.scale(3.8,3.8);
  
              function loop(){
                 context.drawImage(video, 450, 0, 1080, 1920, 0, 0, 720, 1280);
                 setTimeout(loop, 1000 / 30);
              }
  
              loop();
  
  
          }, false);
  &lt;/script&gt; 
  
  
      &lt;video id="video" height="1080" width="1920" autoplay&gt;&lt;/video&gt;
      &lt;canvas id="canvas" height="1920" width="1080"&gt;&lt;/canvas&gt;
  
  
  // Put event listeners into place
  window.addEventListener("DOMContentLoaded", function() {
      // Grab elements, create settings, etc.
      var canvas = document.getElementById("canvas"),
          context = canvas.getContext("2d"),
          video = document.getElementById("video"),
          videoObj = { 
              video: {
                  mandatory: {
                      minWidth: 1280,
                      minHeight: 720,
                      /*Added by Chad*/
                      maxWidth: 1280,
                      maxHeight: 720
                  }
              }
          },
          errBack = function(error) {
              console.log("Video capture error: ", error.code); 
          };
  
      // Put video listeners into place
      if(navigator.getUserMedia) { // Standard
          navigator.getUserMedia(videoObj, function(stream) {
              video.src = stream;
              video.play();
          }, errBack);
      } else if(navigator.webkitGetUserMedia) { // WebKit-prefixed
          navigator.webkitGetUserMedia(videoObj, function(stream){
              video.src = window.URL.createObjectURL(stream);
              video.play();
          }, errBack);
      } else if(navigator.mozGetUserMedia) { // WebKit-prefixed
          navigator.mozGetUserMedia(videoObj, function(stream){
              video.src = window.URL.createObjectURL(stream);
              video.play();
          }, errBack);
      }
  
      /*
          video : video source tag
          320,0 : the shift coords
          320,180 : the canvas size
          0,0 : no shift in the canvas
          640,360 : important ! it’s the native resolution of video source
      */
  
  
  
  
      context.scale(-3.8,3.8);
      context.translate(-720,0);
      function loop(){
         context.drawImage(video, 450, 0, 1080, 1920, 0, 0, 720, 1280);
         setTimeout(loop, 1000 / 30);
      }
  
      loop();
  
  
  }, false);
  </code></pre>