Backed out 3 changesets (bug 1271765) for win8 mochitest(5) failures a=backout
authorWes Kocher <wkocher@mozilla.com>
Tue, 15 Nov 2016 10:50:59 -0800
changeset 322642 2be680105fcd756c8789cc38571ad00d4dd20a97
parent 322641 429e0bd037aaaad037d9d8315bca0f04fae11928
child 322643 5d62e2bc7b593ed79ef048618350aaed7ab0a94a
push id21
push usermaklebus@msu.edu
push dateThu, 01 Dec 2016 06:22:08 +0000
reviewersbackout
bugs1271765
milestone53.0a1
backs out022a4a018996048fc97dc55dd5528655038df830
1d96f03289f8996da6879a30403e0c13b5a1efdc
57317a080c9998ff884aa357be58207bc3be6836
Backed out 3 changesets (bug 1271765) for win8 mochitest(5) failures a=backout Backed out changeset 022a4a018996 (bug 1271765) Backed out changeset 1d96f03289f8 (bug 1271765) Backed out changeset 57317a080c99 (bug 1271765)
accessible/tests/mochitest/tree/test_media.html
dom/media/webvtt/vtt.jsm
layout/generic/crashtests/1271765.html
layout/generic/crashtests/crashtests.list
layout/generic/nsVideoFrame.cpp
layout/style/res/html.css
toolkit/content/tests/widgets/test_audiocontrols_dimensions.html
toolkit/content/tests/widgets/test_videocontrols.html
toolkit/content/tests/widgets/test_videocontrols_standalone.html
toolkit/content/tests/widgets/test_videocontrols_vtt.html
toolkit/content/widgets/videocontrols.xml
toolkit/locales/en-US/chrome/global/videocontrols.dtd
toolkit/themes/shared/jar.inc.mn
toolkit/themes/shared/media/TopLevelVideoDocument.css
toolkit/themes/shared/media/closeCaptionButton.png
toolkit/themes/shared/media/closeCaptionButton@2x.png
toolkit/themes/shared/media/closedCaptionButton.svg
toolkit/themes/shared/media/error.png
toolkit/themes/shared/media/fullscreenButton.png
toolkit/themes/shared/media/fullscreenButton.svg
toolkit/themes/shared/media/fullscreenButton@2x.png
toolkit/themes/shared/media/muteButton.png
toolkit/themes/shared/media/muteButton.svg
toolkit/themes/shared/media/muteButton@2x.png
toolkit/themes/shared/media/noAudio.png
toolkit/themes/shared/media/noAudio@2x.png
toolkit/themes/shared/media/pauseButton.png
toolkit/themes/shared/media/pauseButton.svg
toolkit/themes/shared/media/pauseButton@2x.png
toolkit/themes/shared/media/playButton.png
toolkit/themes/shared/media/playButton.svg
toolkit/themes/shared/media/playButton@2x.png
toolkit/themes/shared/media/scrubberThumb.png
toolkit/themes/shared/media/scrubberThumb@2x.png
toolkit/themes/shared/media/scrubberThumbWide.png
toolkit/themes/shared/media/scrubberThumbWide@2x.png
toolkit/themes/shared/media/unmuteButton.png
toolkit/themes/shared/media/unmuteButton@2x.png
toolkit/themes/shared/media/videocontrols.css
toolkit/themes/shared/media/volume-empty.png
toolkit/themes/shared/media/volume-empty@2x.png
toolkit/themes/shared/media/volume-full.png
toolkit/themes/shared/media/volume-full@2x.png
--- a/accessible/tests/mochitest/tree/test_media.html
+++ b/accessible/tests/mochitest/tree/test_media.html
@@ -40,27 +40,16 @@ https://bugzilla.mozilla.org/show_bug.cg
             role: ROLE_PROGRESSBAR,
             children: []
           },
           { // slider of progress bar
             role: ROLE_SLIDER,
             //name: "0:00 of 0:02 elapsed",
             children: []
           },
-          {
-            role: ROLE_TEXT_CONTAINER,
-            children: [
-              {
-                role: ROLE_TEXT_LEAF, // position text
-              },
-              {
-                role: ROLE_TEXT_LEAF, // duration text
-              }
-            ]
-          },
           { // mute button
             role: ROLE_PUSHBUTTON,
             name: "Mute",
             children: []
           },
           { // slider of volume bar
             role: ROLE_SLIDER,
             children: []
--- a/dom/media/webvtt/vtt.jsm
+++ b/dom/media/webvtt/vtt.jsm
@@ -1146,17 +1146,17 @@ this.EXPORTED_SYMBOLS = ["WebVTT"];
       overlay.removeChild(overlay.firstChild);
     }
 
     var controlBar;
     var controlBarShown;
 
     if (controls) {
       controlBar = controls.ownerDocument.getAnonymousElementByAttribute(
-        controls, "anonid", "controlBar");
+        controls, "class", "controlBar");
       controlBarShown = controlBar ? !!controlBar.clientHeight : false;
     }
 
     var paddedOverlay = window.document.createElement("div");
     paddedOverlay.style.position = "absolute";
     paddedOverlay.style.left = "0";
     paddedOverlay.style.right = "0";
     paddedOverlay.style.top = "0";
deleted file mode 100644
--- a/layout/generic/crashtests/1271765.html
+++ /dev/null
@@ -1,8 +0,0 @@
-<html>
-<head>
-<body>
-<div id="content" class="entry">
-  <audio controls style="writing-mode: vertical-lr"></audio>
-</div>
-</body>
-</html>
--- a/layout/generic/crashtests/crashtests.list
+++ b/layout/generic/crashtests/crashtests.list
@@ -637,9 +637,8 @@ load large-border-radius-dashed.html
 load large-border-radius-dashed2.html
 load large-border-radius-dotted.html
 load large-border-radius-dotted2.html
 load 1297427-non-equal-centers.html
 load 1278461-1.html
 load 1278461-2.html
 load 1304441.html
 load 1316649.html
-skip-if(Android) load 1271765.html
--- a/layout/generic/nsVideoFrame.cpp
+++ b/layout/generic/nsVideoFrame.cpp
@@ -293,37 +293,28 @@ nsVideoFrame::Reflow(nsPresContext* aPre
                  ("enter nsVideoFrame::Reflow: availSize=%d,%d",
                   aReflowInput.AvailableWidth(),
                   aReflowInput.AvailableHeight()));
 
   NS_PRECONDITION(mState & NS_FRAME_IN_REFLOW, "frame is not in reflow");
 
   aStatus = NS_FRAME_COMPLETE;
 
-  const WritingMode myWM = aReflowInput.GetWritingMode();
-  nscoord contentBoxBSize = aReflowInput.ComputedBSize();
-
-  const nscoord borderBoxISize = aReflowInput.ComputedISize() +
-    aReflowInput.ComputedLogicalBorderPadding().IStartEnd(myWM);
-  const bool isBSizeShrinkWrapping = (contentBoxBSize == NS_INTRINSICSIZE);
+  aMetrics.Width() = aReflowInput.ComputedWidth();
+  aMetrics.Height() = aReflowInput.ComputedHeight();
 
-  nscoord borderBoxBSize;
-  if (!isBSizeShrinkWrapping) {
-    borderBoxBSize = contentBoxBSize +
-      aReflowInput.ComputedLogicalBorderPadding().BStartEnd(myWM);
-  }
-
+  // stash this away so we can compute our inner area later
   mBorderPadding   = aReflowInput.ComputedPhysicalBorderPadding();
 
-  // Reflow the child frames. We may have up to three: an image
-  // frame (for the poster image), a container frame for the controls,
-  // and a container frame for the caption.
+  aMetrics.Width() += mBorderPadding.left + mBorderPadding.right;
+  aMetrics.Height() += mBorderPadding.top + mBorderPadding.bottom;
+
+  // Reflow the child frames. We may have up to two, an image frame
+  // which is the poster, and a box frame, which is the video controls.
   for (nsIFrame* child : mFrames) {
-    nsSize oldChildSize = child->GetSize();
-
     if (child->GetContent() == mPosterImage) {
       // Reflow the poster frame.
       nsImageFrame* imageFrame = static_cast<nsImageFrame*>(child);
       ReflowOutput kidDesiredSize(aReflowInput);
       WritingMode wm = imageFrame->GetWritingMode();
       LogicalSize availableSize = aReflowInput.AvailableSize(wm);
       LogicalSize cbSize = aMetrics.Size(aMetrics.GetWritingMode()).
                              ConvertTo(wm, aMetrics.GetWritingMode());
@@ -342,77 +333,56 @@ nsVideoFrame::Reflow(nsPresContext* aPre
       }
       kidReflowInput.SetComputedWidth(posterRenderRect.width);
       kidReflowInput.SetComputedHeight(posterRenderRect.height);
       ReflowChild(imageFrame, aPresContext, kidDesiredSize, kidReflowInput,
                   posterRenderRect.x, posterRenderRect.y, 0, aStatus);
       FinishReflowChild(imageFrame, aPresContext,
                         kidDesiredSize, &kidReflowInput,
                         posterRenderRect.x, posterRenderRect.y, 0);
-
-// Android still uses XUL media controls & hence needs this XUL-friendly
-// custom reflow code. This will go away in bug 1310907.
-#ifdef ANDROID
     } else if (child->GetContent() == mVideoControls) {
       // Reflow the video controls frame.
       nsBoxLayoutState boxState(PresContext(), aReflowInput.mRenderingContext);
+      nsSize size = child->GetSize();
       nsBoxFrame::LayoutChildAt(boxState,
                                 child,
                                 nsRect(mBorderPadding.left,
                                        mBorderPadding.top,
                                        aReflowInput.ComputedWidth(),
                                        aReflowInput.ComputedHeight()));
-
-#endif // ANDROID
-    } else if (child->GetContent() == mCaptionDiv ||
-               child->GetContent() == mVideoControls) {
-      // Reflow the caption and control bar frames.
+      if (child->GetSize() != size) {
+        RefPtr<Runnable> event = new DispatchResizeToControls(child->GetContent());
+        nsContentUtils::AddScriptRunner(event);
+      }
+    } else if (child->GetContent() == mCaptionDiv) {
+      // Reflow to caption div
+      ReflowOutput kidDesiredSize(aReflowInput);
       WritingMode wm = child->GetWritingMode();
-      LogicalSize availableSize = aReflowInput.ComputedSize(wm);
-      availableSize.BSize(wm) = NS_UNCONSTRAINEDSIZE;
-
+      LogicalSize availableSize = aReflowInput.AvailableSize(wm);
+      LogicalSize cbSize = aMetrics.Size(aMetrics.GetWritingMode()).
+                             ConvertTo(wm, aMetrics.GetWritingMode());
       ReflowInput kidReflowInput(aPresContext,
                                        aReflowInput,
                                        child,
-                                       availableSize);
-      ReflowOutput kidDesiredSize(kidReflowInput);
+                                       availableSize,
+                                       &cbSize);
+      nsSize size(aReflowInput.ComputedWidth(), aReflowInput.ComputedHeight());
+      size.width -= kidReflowInput.ComputedPhysicalBorderPadding().LeftRight();
+      size.height -= kidReflowInput.ComputedPhysicalBorderPadding().TopBottom();
+
+      kidReflowInput.SetComputedWidth(std::max(size.width, 0));
+      kidReflowInput.SetComputedHeight(std::max(size.height, 0));
+
       ReflowChild(child, aPresContext, kidDesiredSize, kidReflowInput,
                   mBorderPadding.left, mBorderPadding.top, 0, aStatus);
-
-      if (child->GetContent() == mVideoControls && isBSizeShrinkWrapping) {
-        contentBoxBSize = kidDesiredSize.BSize(myWM);
-      }
-
       FinishReflowChild(child, aPresContext,
                         kidDesiredSize, &kidReflowInput,
                         mBorderPadding.left, mBorderPadding.top, 0);
     }
-
-    if (child->GetContent() == mVideoControls && child->GetSize() != oldChildSize) {
-      RefPtr<Runnable> event = new DispatchResizeToControls(child->GetContent());
-      nsContentUtils::AddScriptRunner(event);
-    }
   }
-
-  if (isBSizeShrinkWrapping) {
-    if (contentBoxBSize == NS_INTRINSICSIZE) {
-      // We didn't get a BSize from our intrinsic size/ratio, nor did we
-      // get one from our controls. Just use BSize of 0.
-      contentBoxBSize = 0;
-    }
-    contentBoxBSize = NS_CSS_MINMAX(contentBoxBSize,
-                                    aReflowInput.ComputedMinBSize(),
-                                    aReflowInput.ComputedMaxBSize());
-    borderBoxBSize = contentBoxBSize +
-      aReflowInput.ComputedLogicalBorderPadding().BStartEnd(myWM);
-  }
-
-  LogicalSize logicalDesiredSize(myWM, borderBoxISize, borderBoxBSize);
-  aMetrics.SetSize(myWM, logicalDesiredSize);
-
   aMetrics.SetOverflowAreasToDesiredBounds();
 
   FinishAndStoreOverflow(&aMetrics);
 
   NS_FRAME_TRACE(NS_FRAME_TRACE_CALLS,
                  ("exit nsVideoFrame::Reflow: size=%d,%d",
                   aMetrics.Width(), aMetrics.Height()));
   NS_FRAME_SET_TRUNCATION(aStatus, aReflowInput, aMetrics);
@@ -551,32 +521,16 @@ nsVideoFrame::ComputeSize(nsRenderingCon
                           WritingMode aWM,
                           const LogicalSize& aCBSize,
                           nscoord aAvailableISize,
                           const LogicalSize& aMargin,
                           const LogicalSize& aBorder,
                           const LogicalSize& aPadding,
                           ComputeSizeFlags aFlags)
 {
-// When in no video scenario, it should fall back to inherited method.
-// We keep old codepath here since Android still uses XUL media controls.
-// This will go away in bug 1310907.
-#ifndef ANDROID
-  if (!HasVideoElement()) {
-    return nsContainerFrame::ComputeSize(aRenderingContext,
-                                         aWM,
-                                         aCBSize,
-                                         aAvailableISize,
-                                         aMargin,
-                                         aBorder,
-                                         aPadding,
-                                         aFlags);
-  }
-#endif // ANDROID
-
   nsSize size = GetVideoIntrinsicSize(aRenderingContext);
 
   IntrinsicSize intrinsicSize;
   intrinsicSize.width.SetCoordValue(size.width);
   intrinsicSize.height.SetCoordValue(size.height);
 
   // Only video elements have an intrinsic ratio.
   nsSize intrinsicRatio = HasVideoElement() ? size : nsSize(0, 0);
@@ -584,59 +538,27 @@ nsVideoFrame::ComputeSize(nsRenderingCon
   return ComputeSizeWithIntrinsicDimensions(aRenderingContext, aWM,
                                             intrinsicSize, intrinsicRatio,
                                             aCBSize, aMargin, aBorder, aPadding,
                                             aFlags);
 }
 
 nscoord nsVideoFrame::GetMinISize(nsRenderingContext *aRenderingContext)
 {
-  nscoord result;
+  nsSize size = GetVideoIntrinsicSize(aRenderingContext);
+  nscoord result = GetWritingMode().IsVertical() ? size.height : size.width;
   DISPLAY_MIN_WIDTH(this, result);
-
-  if (HasVideoElement()) {
-    nsSize size = GetVideoIntrinsicSize(aRenderingContext);
-    result = GetWritingMode().IsVertical() ? size.height : size.width;
-  } else {
-    // We expect last and only child of audio elements to be control if
-    // "controls" attribute is present.
-    nsIFrame* kid = mFrames.LastChild();
-    if (kid) {
-      result = nsLayoutUtils::IntrinsicForContainer(aRenderingContext,
-                                                    kid,
-                                                    nsLayoutUtils::MIN_ISIZE);
-    } else {
-      result = 0;
-    }
-  }
-
   return result;
 }
 
 nscoord nsVideoFrame::GetPrefISize(nsRenderingContext *aRenderingContext)
 {
-  nscoord result;
+  nsSize size = GetVideoIntrinsicSize(aRenderingContext);
+  nscoord result = GetWritingMode().IsVertical() ? size.height : size.width;
   DISPLAY_PREF_WIDTH(this, result);
-
-  if (HasVideoElement()) {
-    nsSize size = GetVideoIntrinsicSize(aRenderingContext);
-    result = GetWritingMode().IsVertical() ? size.height : size.width;
-  } else {
-    // We expect last and only child of audio elements to be control if
-    // "controls" attribute is present.
-    nsIFrame* kid = mFrames.LastChild();
-    if (kid) {
-      result = nsLayoutUtils::IntrinsicForContainer(aRenderingContext,
-                                                    kid,
-                                                    nsLayoutUtils::PREF_ISIZE);
-    } else {
-      result = 0;
-    }
-  }
-
   return result;
 }
 
 nsSize nsVideoFrame::GetIntrinsicRatio()
 {
   if (!HasVideoElement()) {
     // Audio elements have no intrinsic ratio.
     return nsSize(0, 0);
@@ -673,30 +595,26 @@ bool nsVideoFrame::ShouldDisplayPoster()
 }
 
 nsSize
 nsVideoFrame::GetVideoIntrinsicSize(nsRenderingContext *aRenderingContext)
 {
   // Defaulting size to 300x150 if no size given.
   nsIntSize size(300, 150);
 
-// All media controls have been converted to HTML except Android. Hence
-// we keep this codepath for Android until removal in bug 1310907.
-#ifdef ANDROID
   if (!HasVideoElement()) {
     if (!mFrames.FirstChild()) {
       return nsSize(0, 0);
     }
 
     // Ask the controls frame what its preferred height is
     nsBoxLayoutState boxState(PresContext(), aRenderingContext, 0);
     nscoord prefHeight = mFrames.LastChild()->GetXULPrefSize(boxState).height;
     return nsSize(nsPresContext::CSSPixelsToAppUnits(size.width), prefHeight);
   }
-#endif // ANDROID
 
   HTMLVideoElement* element = static_cast<HTMLVideoElement*>(GetContent());
   if (NS_FAILED(element->GetVideoSize(&size)) && ShouldDisplayPoster()) {
     // Use the poster image frame's size.
     nsIFrame *child = mPosterImage->GetPrimaryFrame();
     nsImageFrame* imageFrame = do_QueryFrame(child);
     nsSize imgsize;
     if (NS_SUCCEEDED(imageFrame->GetIntrinsicImageSize(imgsize))) {
--- a/layout/style/res/html.css
+++ b/layout/style/res/html.css
@@ -758,18 +758,16 @@ audio:not([controls]) {
 
 *|*::-moz-html-canvas-content {
   display: block !important;
   /* we want to be an absolute and fixed container */
   transform: translate(0) !important;
 }
 
 video > .caption-box {
-  width: 100%;
-  height: 100%;
   position: relative;
   overflow: hidden;
 }
 
 /* datetime elements */
 
 input[type="time"] > xul|datetimebox {
   display: flex;
--- a/toolkit/content/tests/widgets/test_audiocontrols_dimensions.html
+++ b/toolkit/content/tests/widgets/test_audiocontrols_dimensions.html
@@ -12,17 +12,17 @@
 <div id="content">
   <audio id="audio" controls preload="auto"></audio>
 </div>
 
 <pre id="test">
 <script class="testbody" type="text/javascript">
   function loadedmetadata(event) {
     is(event.type, "loadedmetadata", "checking event type");
-    is(audio.clientHeight, 40, "checking height of audio element");
+    is(audio.clientHeight, 28, "checking height of audio element");
 
     SimpleTest.finish();
   }
 
   var audio = document.getElementById("audio");
 
   SpecialPowers.pushPrefEnv({"set": [["media.cache_size", 40000]]}, startTest);
   function startTest() {
--- a/toolkit/content/tests/widgets/test_videocontrols.html
+++ b/toolkit/content/tests/widgets/test_videocontrols.html
@@ -19,68 +19,63 @@
 /*
  * Positions of the  UI elements, relative to the upper-left corner of the
  * <video> box.
  */
 const videoWidth = 320;
 const videoHeight = 240;
 const videoDuration = 3.8329999446868896;
 
-const controlBarMargin = 9;
-
-const playButtonWidth = 30;
-const playButtonHeight = 40;
-const muteButtonWidth = 30;
-const muteButtonHeight = 40;
-const positionAndDurationWidth = 84;
-const fullscreenButtonWidth = 30;
-const fullscreenButtonHeight = 40;
-const volumeSliderWidth = 48;
-const volumeSliderMarginStart = 4;
-const volumeSliderMarginEnd = 6;
-const scrubberMargin = 9;
-const scrubberWidth = videoWidth - controlBarMargin - playButtonWidth - scrubberMargin * 2 - positionAndDurationWidth - muteButtonWidth - volumeSliderMarginStart - volumeSliderWidth - volumeSliderMarginEnd - fullscreenButtonWidth - controlBarMargin;
-const scrubberHeight = 40;
-
+const playButtonWidth = 28;
+const playButtonHeight = 28;
+const muteButtonWidth = 33;
+const muteButtonHeight = 28;
+const durationWidth = 34;
+const fullscreenButtonWidth = 28;
+const fullscreenButtonHeight = 28;
+const volumeSliderWidth = 32;
+const scrubberWidth = videoWidth - playButtonWidth - durationWidth - muteButtonWidth - volumeSliderWidth - fullscreenButtonWidth;
+const scrubberHeight = 28;
 
 // Play button is on the bottom-left
 const playButtonCenterX = 0 + Math.round(playButtonWidth / 2);
 const playButtonCenterY = videoHeight - Math.round(playButtonHeight / 2);
 // Mute button is on the bottom-right before the full screen button and volume slider
-const muteButtonCenterX = videoWidth - Math.round(muteButtonWidth / 2) - volumeSliderWidth - fullscreenButtonWidth - controlBarMargin;
+const muteButtonCenterX = videoWidth - Math.round(muteButtonWidth / 2) - volumeSliderWidth - fullscreenButtonWidth;
 const muteButtonCenterY = videoHeight - Math.round(muteButtonHeight / 2);
 // Fullscreen button is on the bottom-right at the far end
-const fullscreenButtonCenterX = videoWidth - Math.round(fullscreenButtonWidth / 2) - controlBarMargin;
+const fullscreenButtonCenterX = videoWidth - Math.round(fullscreenButtonWidth / 2);
 const fullscreenButtonCenterY = videoHeight - Math.round(fullscreenButtonHeight / 2);
 // Scrubber bar is between the play and mute buttons. We don't need it's
 // X center, just the offset of its box.
-const scrubberOffsetX = controlBarMargin + playButtonWidth + scrubberMargin;
+const scrubberOffsetX = 0 + playButtonWidth;
 const scrubberCenterY = videoHeight - Math.round(scrubberHeight / 2);
 
 var testnum = 1;
 var video = document.getElementById("video");
 
 const domUtil = SpecialPowers.Cc["@mozilla.org/inspector/dom-utils;1"]
                              .getService(SpecialPowers.Ci.inIDOMUtils);
 
 function getButtonByAttribute(aName, aValue) {
   var kids = domUtil.getChildrenForNode(video, true);
   var videocontrols = kids[1];
   return SpecialPowers.wrap(document)
     .getAnonymousElementByAttribute(videocontrols, aName, aValue);
 }
 
 function isMuteButtonMuted() {
-  var muteButton = getButtonByAttribute('anonid', 'muteButton');
+  var muteButton = getButtonByAttribute('class', 'muteButton');
   return muteButton.getAttribute('muted') === 'true';
 }
 
 function isVolumeSliderShowingCorrectVolume(expectedVolume) {
-  var volumeControl = getButtonByAttribute('anonid', 'volumeControl');
-  is(+volumeControl.value, expectedVolume * 100,
+  var volumeButton = getButtonByAttribute('anonid', 'volumeForeground');
+  let expectedPaddingRight = (1 - expectedVolume) * volumeSliderWidth + "px";
+  is(volumeButton.style.paddingRight, expectedPaddingRight,
      "volume slider should match expected volume");
 }
 
 function forceReframe() {
   // Setting display then getting the bounding rect to force a frame
   // reconstruction on the video element.
   video.style.display = "block";
   video.getBoundingClientRect();
@@ -229,17 +224,17 @@ function runTest(event) {
 
     /*
      * Click the slider at the 1/4 point with the mouse (jump backwards)
      */
     case 13:
       is(event.type, "seeked", "checking event type");
       ok(true, "video position is at " + video.currentTime);
       var expectedTime = videoDuration / 2;
-      ok(Math.abs(video.currentTime - expectedTime) < 0.25, "checking expected playback position");
+      ok(Math.abs(video.currentTime - expectedTime) < 0.1, "checking expected playback position");
 
       SimpleTest.executeSoon(() => {
         synthesizeMouse(video, scrubberOffsetX + (scrubberWidth / 4), scrubberCenterY, { });
       });
       break;
 
     case 14:
       is(event.type, "seeking", "checking event type");
--- a/toolkit/content/tests/widgets/test_videocontrols_standalone.html
+++ b/toolkit/content/tests/widgets/test_videocontrols_standalone.html
@@ -8,19 +8,18 @@
   <link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
 </head>
 <body>
 <p id="display"></p>
 
 <pre id="test">
 <script class="testbody" type="text/javascript">
 
-const videoBorderWidth = 1;
-const videoWidth = 320 + videoBorderWidth * 2;
-const videoHeight = 240 + videoBorderWidth * 2;
+const videoWidth = 320;
+const videoHeight = 240;
 
 function getMediaElement(aWindow) {
   return aWindow.document.getElementsByTagName("video")[0];
 }
 
 var popup = window.open("seek_with_sound.ogg");
 popup.addEventListener("load", function onLoad() {
   popup.removeEventListener("load", onLoad);
@@ -64,17 +63,17 @@ function runTestAudioPre() {
       })
     }
   })
 }
 
 function runTestAudio(aAudio) {
   info("User agent (help diagnose bug #943556): " + navigator.userAgent);
   var isAndroid = navigator.userAgent.includes("Android");
-  var expectedHeight = isAndroid ? 103 : 42;
+  var expectedHeight = isAndroid ? 103 : 28;
   var condition = function () {
     var boundingRect = aAudio.getBoundingClientRect();
     return boundingRect.height == expectedHeight;
   };
   waitForCondition(condition, function () {
     var boundingRect = aAudio.getBoundingClientRect();
     is(boundingRect.height, expectedHeight,
        "Height of audio element should be " + expectedHeight + ", which is equal to the controls bar.");
--- a/toolkit/content/tests/widgets/test_videocontrols_vtt.html
+++ b/toolkit/content/tests/widgets/test_videocontrols_vtt.html
@@ -15,17 +15,17 @@
 
 <pre id="test">
 <script clas="testbody" type="application/javascript">
   SimpleTest.waitForExplicitFinish();
 
   const domUtils = SpecialPowers.Cc["@mozilla.org/inspector/dom-utils;1"].
     getService(SpecialPowers.Ci.inIDOMUtils);
   const video = document.getElementById("video");
-  const ccBtn = getElementByAttribute("anonid", "closedCaptionButton");
+  const ccBtn = getElementByAttribute("class", "closedCaptionButton");
   const testCases = [];
 
   testCases.push(() => new Promise(resolve => {
     is(ccBtn.getAttribute("hidden"), "true", "CC button should hide");
 
     resolve();
   }));
 
@@ -41,18 +41,18 @@
     });
   }));
 
   testCases.push(() => new Promise(resolve => {
     const sub = video.addTextTrack("subtitles", "English", "en");
     sub.mode = "disabled";
 
     SimpleTest.executeSoon(() => {
-      is(ccBtn.hasAttribute("hidden"), false, "CC button should show");
-      is(ccBtn.hasAttribute("enabled"), false, "CC button should be disabled");
+      is(ccBtn.getAttribute("hidden"), "", "CC button should show");
+      is(ccBtn.getAttribute("enabled"), "", "CC button should be disabled");
 
       resolve();
     });
   }));
 
   testCases.push(() => new Promise(resolve => {
     const subtitle = video.addTextTrack("subtitles", "English", "en");
     subtitle.mode = "showing";
--- a/toolkit/content/widgets/videocontrols.xml
+++ b/toolkit/content/widgets/videocontrols.xml
@@ -41,17 +41,16 @@
         </getter>
         <setter>
           <![CDATA[
           this.setAttribute("showhours", val);
           // If the duration becomes known while we're still showing the value
           // for time=0, immediately update the value to show or hide the hours.
           // It's less intrusive to do it now than when the user clicks play and
           // is looking right next to the thumb.
-          if (!this.timeLabel) return;
           var displayedTime = this.timeLabel.getAttribute("value");
           if (val && displayedTime == "0:00")
               this.timeLabel.setAttribute("value", "0:00:00");
           else if (!val && displayedTime == "0:00:00")
               this.timeLabel.setAttribute("value", "0:00");
           ]]>
         </setter>
       </property>
@@ -127,21 +126,17 @@
             switch (which) {
               case "curpos":
                 if (this.type == "scrubber") {
                     // Update the time shown in the thumb.
                     this.thumb.setTime(newValue);
                     this.Utils.positionLabel.setAttribute("value", this.thumb.timeLabel.value);
                     // Update the value bar to match the thumb position.
                     let percent = newValue / this.max;
-                    if (!isNaN(percent) && percent != Infinity) {
-                      this.valueBar.value = Math.round(percent * 10000); // has max=10000
-                    } else {
-                      this.valueBar.removeAttribute("value");
-                    }
+                    this.valueBar.value = Math.round(percent * 10000); // has max=10000
                 }
 
                 // The value of userChanged is true when changing the position with the mouse,
                 // but not when pressing an arrow key. However, the base binding sets
                 // ._userChanged in its keypress handlers, so we just need to check both.
                 if (!userChanged && !this._userChanged)
                   return;
                 this.setAttribute("value", newValue);
@@ -203,89 +198,84 @@
 
   <binding id="videoControls">
 
     <resources>
         <stylesheet src="chrome://global/content/bindings/videocontrols.css"/>
         <stylesheet src="chrome://global/skin/media/videocontrols.css"/>
     </resources>
 
-    <xbl:content xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
-    xmlns="http://www.w3.org/1999/xhtml" class="mediaControlsFrame">
-        <div anonid="controlsContainer" class="controlsContainer" role="none">
-            <div anonid="statusOverlay" class="statusOverlay stackItem" hidden="true">
-                <div anonid="statusIcon" class="statusIcon"></div>
-                <span class="errorLabel" anonid="errorAborted">&error.aborted;</span>
-                <span class="errorLabel" anonid="errorNetwork">&error.network;</span>
-                <span class="errorLabel" anonid="errorDecode">&error.decode;</span>
-                <span class="errorLabel" anonid="errorSrcNotSupported">&error.srcNotSupported;</span>
-                <span class="errorLabel" anonid="errorNoSource">&error.noSource2;</span>
-                <span class="errorLabel" anonid="errorGeneric">&error.generic;</span>
-            </div>
+    <xbl:content xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
+                 class="mediaControlsFrame">
+        <stack flex="1">
+            <vbox flex="1" class="statusOverlay" hidden="true">
+                <box class="statusIcon"/>
+                <label class="errorLabel" anonid="errorAborted">&error.aborted;</label>
+                <label class="errorLabel" anonid="errorNetwork">&error.network;</label>
+                <label class="errorLabel" anonid="errorDecode">&error.decode;</label>
+                <label class="errorLabel" anonid="errorSrcNotSupported">&error.srcNotSupported;</label>
+                <label class="errorLabel" anonid="errorNoSource">&error.noSource2;</label>
+                <label class="errorLabel" anonid="errorGeneric">&error.generic;</label>
+            </vbox>
 
-            <div anonid="controlsOverlay" class="controlsOverlay stackItem">
-                <div class="controlsSpacerStack" aria-hideen="true">
-                  <div anonid="controlsSpacer" class="controlsSpacer stackItem" role="none"></div>
-                  <div anonid="clickToPlay" class="clickToPlay" hidden="true"></div>
-                </div>
-                <div anonid="controlBar" class="controlBar" hidden="true">
-                    <button anonid="playButton"
-                            class="playButton"
+            <vbox class="controlsOverlay">
+                <stack flex="1">
+                    <spacer class="controlsSpacer" flex="1"/>
+                    <box class="clickToPlay" hidden="true" flex="1"/>
+                    <vbox class="textTrackList" hidden="true" offlabel="&closedCaption.off;"></vbox>
+                </stack>
+                <hbox class="controlBar" hidden="true">
+                    <button class="playButton"
                             playlabel="&playButton.playLabel;"
                             pauselabel="&playButton.pauseLabel;"/>
-                    <div anonid="scrubberStack" class="scrubberStack progressContainer" role="none">
-                      <div class="progressBackgroundBar stackItem" role="none">
-                        <div class="progressStack" role="none">
-                          <progress anonid="bufferBar" class="bufferBar" value="0" max="100"></progress>
-                          <progress anonid="progressBar" class="progressBar" value="0" max="100"></progress>
-                        </div>
-                      </div>
-                      <input type="range" anonid="scrubber" class="scrubber"/>
-                    </div>
-                    <span anonid="positionLabel" class="positionLabel" role="presentation"></span>
-                    <span anonid="durationLabel" class="durationLabel" role="presentation"></span>
-                    <span anonid="positionDurationBox" class="positionDurationBox" aria-hidden="true">
-                      &positionAndDuration.nameFormat;
-                    </span>
-                    <div anonid="controlBarSpacer" class="controlBarSpacer" hidden="true" role="none"></div>
-                    <button anonid="muteButton"
-                            class="muteButton"
+                    <stack class="scrubberStack" flex="1">
+                        <box class="backgroundBar"/>
+                        <progressmeter class="bufferBar"/>
+                        <progressmeter class="progressBar" max="10000"/>
+                        <scale class="scrubber" movetoclick="true"/>
+                    </stack>
+                    <vbox class="durationBox">
+                        <label class="positionLabel" role="presentation"/>
+                        <label class="durationLabel" role="presentation"/>
+                    </vbox>
+                    <button class="muteButton"
                             mutelabel="&muteButton.muteLabel;"
                             unmutelabel="&muteButton.unmuteLabel;"/>
-                    <div anonid="volumeStack" class="volumeStack progressContainer" role="none">
-                      <input type="range" anonid="volumeControl" class="volumeControl" min="0" max="100" step="1"/>
-                    </div>
-                    <button anonid="closedCaptionButton" class="closedCaptionButton"/>
-                    <button anonid="fullscreenButton"
-                            class="fullscreenButton"
+                    <stack class="volumeStack">
+                      <box class="volumeBackground"/>
+                      <box class="volumeForeground" anonid="volumeForeground"/>
+                      <scale class="volumeControl" movetoclick="true"/>
+                    </stack>
+                    <button class="closedCaptionButton"/>
+                    <button class="fullscreenButton"
                             enterfullscreenlabel="&fullscreenButton.enterfullscreenlabel;"
                             exitfullscreenlabel="&fullscreenButton.exitfullscreenlabel;"/>
-                </div>
-                <div anonid="textTrackList" class="textTrackList" hidden="true" offlabel="&closedCaption.off;"></div>
-            </div>
-        </div>
+                </hbox>
+            </vbox>
+        </stack>
     </xbl:content>
 
     <implementation>
 
         <constructor>
             <![CDATA[
-            this.isTouchControls = false;
+            this.isTouchControl = false;
             this.randomID = 0;
 
             this.Utils = {
                 debug : false,
                 video : null,
                 videocontrols : null,
                 controlBar : null,
                 playButton : null,
                 muteButton : null,
                 volumeControl  : null,
                 durationLabel  : null,
                 positionLabel  : null,
+                scrubberThumb  : null,
                 scrubber       : null,
                 progressBar    : null,
                 bufferBar      : null,
                 statusOverlay  : null,
                 controlsSpacer : null,
                 clickToPlay    : null,
                 controlsOverlay : null,
                 fullscreenButton : null,
@@ -298,27 +288,26 @@
                                "playing", "waiting", "canplay", "canplaythrough",
                                "seeking", "seeked", "emptied", "loadedmetadata",
                                "error", "suspend", "stalled",
                                "mozinterruptbegin", "mozinterruptend" ],
 
                 firstFrameShown : false,
                 timeUpdateCount : 0,
                 maxCurrentTimeSeen : 0,
-                isPausedByDragging: false,
                 _isAudioOnly : false,
                 get isAudioOnly() { return this._isAudioOnly; },
                 set isAudioOnly(val) {
                     this._isAudioOnly = val;
                     this.setFullscreenButtonState();
 
                     if (!this.isTopLevelSyntheticDocument)
                         return;
                     if (this._isAudioOnly) {
-                        this.video.style.height = this.controlBar.minHeight + "px";
+                        this.video.style.height = this._controlBarHeight + "px";
                         this.video.style.width = "66%";
                     } else {
                         this.video.style.removeProperty("height");
                         this.video.style.removeProperty("width");
                     }
                 },
                 suppressError : false,
 
@@ -372,17 +361,16 @@
 
                     this.setFullscreenButtonState();
 
                     var duration = Math.round(this.video.duration * 1000); // in ms
                     var currentTime = Math.round(this.video.currentTime * 1000); // in ms
                     this.log("Initial playback position is at " + currentTime + " of " + duration);
                     // It would be nice to retain maxCurrentTimeSeen, but it would be difficult
                     // to determine if the media source changed while we were detached.
-                    this.initPositionDurationBox();
                     this.maxCurrentTimeSeen = currentTime;
                     this.showPosition(currentTime, duration);
 
                     // If we have metadata, check if this is a <video> without
                     // video data, or a video with no audio track.
                     if (this.video.readyState >= this.video.HAVE_METADATA) {
                         if (this.video instanceof HTMLVideoElement &&
                             (this.video.videoWidth == 0 || this.video.videoHeight == 0))
@@ -403,92 +391,41 @@
 
                     // If the first frame hasn't loaded, kick off a throbber fade-in.
                     if (this.video.readyState >= this.video.HAVE_CURRENT_DATA)
                         this.firstFrameShown = true;
 
                     // We can't determine the exact buffering status, but do know if it's
                     // fully loaded. (If it's still loading, it will fire a progress event
                     // and we'll figure out the exact state then.)
-                    this.bufferBar.max = 100;
+                    this.bufferBar.setAttribute("max", 100);
                     if (this.video.readyState >= this.video.HAVE_METADATA)
                         this.showBuffered();
                     else
-                        this.bufferBar.value = 0;
+                        this.bufferBar.setAttribute("value", 0);
 
                     // Set the current status icon.
                     if (this.hasError()) {
                         this.clickToPlay.hidden = true;
                         this.statusIcon.setAttribute("type", "error");
                         this.updateErrorText();
                         this.setupStatusFader(true);
                     }
 
                     // An event handler for |onresize| should be added when bug 227495 is fixed.
                     this.controlBar.hidden = false;
-
-                    let layoutControls = [
-                      ...this.controlBar.children,
-                      this.durationSpan,
-                      this.controlBar,
-                      this.clickToPlay
-                    ];
-
-                    for (let control of layoutControls) {
-                      if (!control) {
-                        break;
-                      }
-
-                      Object.defineProperties(control, {
-                        minWidth: {
-                          value: control.clientWidth,
-                          writable: true
-                        },
-                        minHeight: {
-                          value: control.clientHeight,
-                          writable: true
-                        },
-                        isAdjustableControl: {
-                          value: true
-                        },
-                        isWanted: {
-                          value: true,
-                          writable: true
-                        },
-                        hideByAdjustment: {
-                          set: (v) => {
-                            if (v) {
-                              control.setAttribute("hidden", "true");
-                            } else {
-                              control.removeAttribute("hidden");
-                            }
-
-                            control._isHiddenByAdjustment = v;
-                          },
-                          get: () => control._isHiddenByAdjustment
-                        },
-                        _isHiddenByAdjustment: {
-                          value: false,
-                          writable: true
-                        }
-                      });
-                    }
-                    // Cannot get minimal width of flexible scrubber and clickToPlay.
-                    // Rewrite to empirical value for now.
-                    this.controlBar.minHeight = 40;
-                    this.scrubberStack.minWidth = 64;
-                    this.volumeControl.minWidth = 48;
-                    this.clickToPlay.minWidth = 48;
-
-                    if (this.positionDurationBox) {
-                      this.positionDurationBox.minWidth -= this.durationSpan.minWidth;
-                    }
-
+                    this._playButtonWidth = this.playButton.clientWidth;
+                    this._durationLabelWidth = this.durationLabel.clientWidth;
+                    this._muteButtonWidth = this.muteButton.clientWidth;
+                    this._volumeControlWidth = this.volumeControl.clientWidth;
+                    this._closedCaptionButtonWidth = this.closedCaptionButton.clientWidth;
+                    this._fullscreenButtonWidth = this.fullscreenButton.clientWidth;
+                    this._controlBarHeight = this.controlBar.clientHeight;
+                    this.controlBar.hidden = true;
                     this.adjustControlSize();
-                    this.controlBar.hidden = true;
 
                     // Can only update the volume controls once we've computed
                     // _volumeControlWidth, since the volume slider implementation
                     // depends on it.
                     this.updateVolumeControls();
                 },
 
                 setupNewLoadState : function() {
@@ -501,20 +438,18 @@
                     // so that they don't get in the way of the playing video. Otherwise we'll
                     // go ahead and reveal the controls now, so they're an obvious user cue.
                     //
                     // (Note: the |controls| attribute is already handled via layout/style/html.css)
                     var shouldShow = !this.dynamicControls ||
                       (this.video.paused &&
                        !(this.video.autoplay && this.video.mozAutoplayEnabled));
                     // Hide the overlay if the video time is non-zero or if an error occurred to workaround bug 718107.
-                    let shouldClickToPlayShow = shouldShow && !this.isAudioOnly &&
-                                                this.video.currentTime == 0 && !this.hasError();
-                    this.startFade(this.clickToPlay, shouldClickToPlayShow, true);
-                    this.startFade(this.controlsSpacer, shouldClickToPlayShow, true);
+                    this.startFade(this.clickToPlay, shouldShow && !this.isAudioOnly &&
+                                   this.video.currentTime == 0 && !this.hasError(), true);
                     this.startFade(this.controlBar, shouldShow, true);
                 },
 
                 get dynamicControls() {
                     // Don't fade controls for <audio> elements.
                     var enabled = !this.isAudioOnly;
 
                     // Allow tests to explicitly suppress the fading of controls.
@@ -524,43 +459,39 @@
                     // If the video hits an error, suppress controls if it
                     // hasn't managed to do anything else yet.
                     if (!this.firstFrameShown && this.hasError())
                         enabled = false;
 
                     return enabled;
                 },
 
-                updateVolume() {
-                  const volume = this.volumeControl.value;
-                  this.setVolume(volume / 100);
-                },
-
                 updateVolumeControls() {
                     var volume = this.video.muted ? 0 : this.video.volume;
                     var volumePercentage = Math.round(volume * 100);
                     this.updateMuteButtonState();
                     this.volumeControl.value = volumePercentage;
+                    this.volumeForeground.style.paddingRight = (1 - volume) * this._volumeControlWidth + "px";
                 },
 
                 handleEvent : function (aEvent) {
                     this.log("Got media event ----> " + aEvent.type);
 
                     // If the binding is detached (or has been replaced by a
                     // newer instance of the binding), nuke our event-listeners.
                     if (this.videocontrols.randomID != this.randomID) {
                         this.terminateEventListeners();
                         return;
                     }
 
                     switch (aEvent.type) {
                         case "play":
                             this.setPlayButtonState(false);
                             this.setupStatusFader();
-                            if (!this._triggeredByControls && this.dynamicControls && this.videocontrols.isTouchControls)
+                            if (!this._triggeredByControls && this.dynamicControls && this.videocontrols.isTouchControl)
                                 this.startFadeOut(this.controlBar);
                             if (!this._triggeredByControls)
                                 this.clickToPlay.hidden = true;
                             this._triggeredByControls = false;
                             break;
                         case "pause":
                             // Little white lie: if we've internally paused the video
                             // while dragging the scrubber, don't change the button state.
@@ -649,21 +580,20 @@
                             // statusOverlay while we wait for HAVE_ENOUGH_DATA).
                             // If we've seen more than 2 timeupdate events,
                             // the count is no longer relevant to setupStatusFader.
                             if (this.timeUpdateCount <= 2)
                                 this.setupStatusFader();
 
                             // If the user is dragging the scrubber ignore the delayed seek
                             // responses (don't yank the thumb away from the user)
-                            if (this.scrubber.isDragging || this.scrubber.startToDrag)
+                            if (this.scrubber.isDragging)
                                 return;
 
                             this.showPosition(currentTime, duration);
-                            this.showBuffered();
                             break;
                         case "emptied":
                             this.bufferBar.value = 0;
                             this.showPosition(0, 0);
                             break;
                         case "seeking":
                             this.showBuffered();
                             this.statusIcon.setAttribute("type", "throbber");
@@ -809,120 +739,41 @@
                             mins = "0" + mins;
                         timeString = hours + ":" + mins + ":" + secs;
                     } else {
                         timeString = mins + ":" + secs;
                     }
                     return timeString;
                 },
 
-                initPositionDurationBox : function () {
-                  if (this.videocontrols.isTouchControls) {
-                    return;
-                  }
-
-                  const positionTextNode = Array.prototype.find.call(
-                    this.positionDurationBox.childNodes, (n) => !!~n.textContent.search("#1"));
-                  const durationSpan = this.durationSpan;
-                  const durationFormat = durationSpan.textContent;
-                  const positionFormat = positionTextNode.textContent;
-
-                  durationSpan.classList.add("duration");
-                  durationSpan.setAttribute("role", "none");
-
-                  Object.defineProperties(this.positionDurationBox, {
-                    durationSpan: {
-                      value: durationSpan
-                    },
-                    position: {
-                      set: (v) => {
-                        positionTextNode.textContent = positionFormat.replace("#1", v);
-                      }
-                    },
-                    duration: {
-                      set: (v) => {
-                        durationSpan.textContent = v ? durationFormat.replace("#2", v) : "";
-                      }
-                    }
-                  });
-                },
-
                 showDuration : function (duration) {
                     let isInfinite = (duration == Infinity);
                     this.log("Duration is " + duration + "ms.\n");
 
                     if (isNaN(duration) || isInfinite)
                         duration = this.maxCurrentTimeSeen;
 
                     // Format the duration as "h:mm:ss" or "m:ss"
                     let timeString = isInfinite ? "" : this.formatTime(duration);
-                    if (this.videocontrols.isTouchControls) {
-                      this.durationLabel.setAttribute("value", timeString);
-                    } else {
-                      this.positionDurationBox.duration = timeString;
-                    }
+                    this.durationLabel.setAttribute("value", timeString);
 
                     // "durationValue" property is used by scale binding to
                     // generate accessible name.
                     this.scrubber.durationValue = timeString;
 
                     // If the duration is over an hour, thumb should show h:mm:ss instead of mm:ss
+                    this.scrubberThumb.showHours = (duration >= 3600000);
 
                     this.scrubber.max = duration;
                     // XXX Can't set increment here, due to bug 473103. Also, doing so causes
                     // snapping when dragging with the mouse, so we can't just set a value for
                     // the arrow-keys.
                     this.scrubber.pageIncrement = Math.round(duration / 10);
                 },
 
-                pauseVideoDuringDragging: function() {
-                  if (!this.video.paused &&
-                      !this.isPausedByDragging &&
-                      this.scrubber.isDragging) {
-                    this.isPausedByDragging = true;
-                    this.video.pause();
-                  }
-                },
-
-                onScrubberInput: function(e) {
-                  const duration = Math.round(this.video.duration * 1000); // in ms
-                  let time = this.scrubber.value;
-
-                  if (!this.scrubber.startToDrag || this.scrubber.isDragging) {
-                    this.seekToPosition(time);
-                    this.showPosition(time, duration);
-                  }
-
-                  this.scrubber.startToDrag = true;
-                },
-
-                onScrubberChange: function(e) {
-                  this.scrubber.startToDrag = false;
-                  this.scrubber.isDragging = false;
-
-                  if (this.isPausedByDragging) {
-                    this.video.play();
-                    this.isPausedByDragging = false;
-                  }
-                },
-
-                updateScrubberProgress() {
-                  if (this.videocontrols.isTouchControls) {
-                    return;
-                  }
-
-                  const positionPercent = this.scrubber.value / this.scrubber.max * 100;
-
-                  if (!isNaN(positionPercent) && positionPercent != Infinity) {
-                    this.progressBar.value = positionPercent;
-                  } else {
-                    this.progressBar.value = 0;
-                  }
-                },
-
                 seekToPosition : function(newPosition) {
                     newPosition /= 1000; // convert from ms
                     this.log("+++ seeking to " + newPosition);
                     if (this.videocontrols.isGonk) {
                         // We use fastSeek() on B2G, and an accurate (but slower)
                         // seek on other platforms (that are likely to be higher
                         // perf).
                         this.video.fastSeek(newPosition);
@@ -942,25 +793,18 @@
                     // it, or the video is a stream), then we want to fudge the duration
                     // by using the maximum playback position that's been seen.
                     if (currentTime > this.maxCurrentTimeSeen)
                         this.maxCurrentTimeSeen = currentTime;
                     this.showDuration(duration);
 
                     this.log("time update @ " + currentTime + "ms of " + duration + "ms");
 
-                    let positionTime = this.formatTime(currentTime);
-
+                    this.positionLabel.setAttribute("value", this.formatTime(currentTime));
                     this.scrubber.value = currentTime;
-                    if (this.videocontrols.isTouchControls) {
-                      this.positionLabel.setAttribute("value", positionTime);
-                    } else {
-                      this.positionDurationBox.position = positionTime;
-                      this.updateScrubberProgress();
-                    }
                 },
 
                 showBuffered : function() {
                     function bsearch(haystack, needle, cmp) {
                         var length = haystack.length;
                         var low = 0;
                         var high = length;
                         while (low < high) {
@@ -982,19 +826,18 @@
                             return 1;
                         } else if (time >= buffered.start(i)) {
                             return 0;
                         }
                         return -1;
                     }
 
                     var duration = Math.round(this.video.duration * 1000);
-                    if (isNaN(duration) || duration == Infinity) {
+                    if (isNaN(duration))
                         duration = this.maxCurrentTimeSeen;
-                    }
 
                     // Find the range that the current play position is in and use that
                     // range for bufferBar.  At some point we may support multiple ranges
                     // displayed in the bar.
                     var currentTime = this.video.currentTime;
                     var buffered = this.video.buffered;
                     var index = bsearch(buffered, currentTime, bufferedCompare);
                     var endTime = 0;
@@ -1022,19 +865,18 @@
                         Utils.startFade(Utils.controlBar, false);
                         Utils._hideControlsTimeout = 0;
                         Utils._controlsHiddenByTimeout = true;
                     }
                 },
                 HIDE_CONTROLS_TIMEOUT_MS : 2000,
                 onMouseMove : function (event) {
                     // Pause playing video when the mouse is dragging over the control bar.
-                    if (this.scrubber.startToDrag) {
-                      this.scrubber.isDragging = true;
-                      this.pauseVideoDuringDragging();
+                    if (this.scrubber.isDragging) {
+                      this.scrubber.pauseVideoDuringDragging();
                     }
 
                     // If the controls are static, don't change anything.
                     if (!this.dynamicControls)
                         return;
 
                     clearTimeout(this._hideControlsTimeout);
 
@@ -1112,29 +954,25 @@
                 },
 
                 startFade : function (element, fadeIn, immediate) {
                     if (element.classList.contains("controlBar") && fadeIn) {
                         // Bug 493523, the scrubber doesn't call valueChanged while hidden,
                         // so our dependent state (eg, timestamp in the thumb) will be stale.
                         // As a workaround, update it manually when it first becomes unhidden.
                         if (element.hidden)
-                          if (this.videocontrols.isTouchControls) {
                             this.scrubber.valueChanged("curpos", this.video.currentTime * 1000, false);
-                          } else {
-                            this.scrubber.value = this.video.currentTime * 1000;
-                          }
                     }
 
                     if (immediate)
                         element.setAttribute("immediate", true);
                     else
                         element.removeAttribute("immediate");
 
-                    if (fadeIn && !(element.isAdjustableControl && element.hideByAdjustment)) {
+                    if (fadeIn) {
                         element.hidden = false;
                         // force style resolution, so that transition begins
                         // when we remove the attribute.
                         element.clientTop;
                         element.removeAttribute("fadeout");
                         if (element.classList.contains("controlBar"))
                             this.controlsSpacer.removeAttribute("hideCursor");
                     } else {
@@ -1152,19 +990,17 @@
                         return;
 
                     var element = event.originalTarget;
 
                     // Nothing to do when a fade *in* finishes.
                     if (!element.hasAttribute("fadeout"))
                         return;
 
-                    if (this.videocontrols.isTouchControls) {
-                      this.scrubber.dragStateChanged(false);
-                    }
+                    this.scrubber.dragStateChanged(false);
                     element.hidden = true;
                 },
 
                 _triggeredByControls: false,
 
                 startPlay : function () {
                     this._triggeredByControls = true;
                     this.hideClickToPlay();
@@ -1261,27 +1097,24 @@
                 hideClickToPlay : function () {
                     let videoHeight = this.video.clientHeight;
                     let videoWidth = this.video.clientWidth;
 
                     // The play button will animate to 3x its size. This
                     // shows the animation unless the video is too small
                     // to show 2/3 of the animation.
                     let animationScale = 2;
-                    let animationMinSize = this.clickToPlay.minWidth * animationScale;
-
-                    if (animationMinSize > videoWidth ||
-                        animationMinSize > (videoHeight - this.controlBar.minHeight)) {
-                      this.clickToPlay.setAttribute("immediate", "true");
-                      this.clickToPlay.hidden = true;
+                    if (this._overlayPlayButtonHeight * animationScale > (videoHeight - this._controlBarHeight)||
+                        this._overlayPlayButtonWidth * animationScale > videoWidth) {
+                        this.clickToPlay.setAttribute("immediate", "true");
+                        this.clickToPlay.hidden = true;
                     } else {
                         this.clickToPlay.removeAttribute("immediate");
                     }
                     this.clickToPlay.setAttribute("fadeout", "true");
-                    this.controlsSpacer.setAttribute("fadeout", "true");
                 },
 
                 setPlayButtonState : function(aPaused) {
                   if (aPaused)
                       this.playButton.setAttribute("paused", "true");
                   else
                       this.playButton.removeAttribute("paused");
 
@@ -1415,48 +1248,43 @@
                     event.preventDefault(); // Prevent page scrolling
                 },
 
                 isSupportedTextTrack : function(textTrack) {
                   return textTrack.kind == "subtitles" ||
                          textTrack.kind == "captions";
                 },
 
-                get isClosedCaptionAvailable() {
-                  return this.overlayableTextTracks.length && !this.videocontrols.isTouchControls;
-                },
-
                 get overlayableTextTracks() {
                   return Array.prototype.filter.call(this.video.textTracks, this.isSupportedTextTrack);
                 },
 
                 isClosedCaptionOn : function () {
                   for (let tt of this.overlayableTextTracks) {
                     if (tt.mode === "showing") {
                       return true;
                     }
                   }
 
                   return false;
                 },
 
                 setClosedCaptionButtonState : function () {
-                  if (!this.isClosedCaptionAvailable) {
+                  if (!this.overlayableTextTracks.length || this.videocontrols.isTouchControl) {
                     this.closedCaptionButton.setAttribute("hidden", "true");
                     return;
                   }
 
                   this.closedCaptionButton.removeAttribute("hidden");
 
                   if (this.isClosedCaptionOn()) {
                     this.closedCaptionButton.setAttribute("enabled", "true");
                   } else {
                     this.closedCaptionButton.removeAttribute("enabled");
                   }
-                  this.adjustControlSize();
 
                   let ttItems = this.textTrackList.childNodes;
 
                   for (let tti of ttItems) {
                     const idx = +tti.getAttribute("index");
 
                     if (idx == this.currentTextTrackIndex) {
                       tti.setAttribute("on", "true");
@@ -1520,21 +1348,43 @@
                 },
 
                 onControlBarTransitioned : function () {
                   this.textTrackList.setAttribute("hidden", "true");
                   this.video.dispatchEvent(new CustomEvent("controlbarchange"));
                 },
 
                 toggleClosedCaption : function () {
+                  if (this.overlayableTextTracks.length === 1) {
+                    const lastTTIdx = this.overlayableTextTracks[0].index;
+                    this.changeTextTrack(this.isClosedCaptionOn() ? 0 : lastTTIdx);
+                    return;
+                  }
+
                   if (this.textTrackList.hasAttribute("hidden")) {
                     this.textTrackList.removeAttribute("hidden");
                   } else {
                     this.textTrackList.setAttribute("hidden", "true");
                   }
+
+                  let maxButtonWidth = 0;
+
+                  for (let tti of this.textTrackList.childNodes) {
+                    if (tti.clientWidth > maxButtonWidth) {
+                      maxButtonWidth = tti.clientWidth;
+                    }
+                  }
+
+                  if (maxButtonWidth > this.video.clientWidth) {
+                    maxButtonWidth = this.video.clientWidth;
+                  }
+
+                  for (let tti of this.textTrackList.childNodes) {
+                    tti.style.width = maxButtonWidth + "px";
+                  }
                 },
 
                 onTextTrackAdd : function (trackEvent) {
                   this.addNewTextTrack(trackEvent.track);
                   this.setClosedCaptionButtonState();
                 },
 
                 onTextTrackRemove : function (trackEvent) {
@@ -1559,21 +1409,16 @@
                       this.video.dispatchEvent(new CustomEvent("texttrackchange"));
                     }
                   }
 
                   this.setClosedCaptionButtonState();
                 },
 
                 initTextTracks : function () {
-                  if (!this.isClosedCaptionAvailable) {
-                    this.closedCaptionButton.setAttribute("hidden", "true");
-                    return;
-                  }
-
                   const offLabel = this.textTrackList.getAttribute("offlabel");
 
                   this.addNewTextTrack({
                     label: offLabel,
                     kind: "subtitles"
                   });
 
                   for (let tt of this.overlayableTextTracks) {
@@ -1601,156 +1446,118 @@
                 },
 
                 get isTopLevelSyntheticDocument() {
                   let doc = this.video.ownerDocument;
                   let win = doc.defaultView;
                   return doc.mozSyntheticDocument && win === win.top;
                 },
 
+                _playButtonWidth : 0,
+                _durationLabelWidth : 0,
+                _muteButtonWidth : 0,
+                _volumeControlWidth : 0,
+                _closedCaptionButtonWidth : 0,
+                _fullscreenButtonWidth : 0,
+                _controlBarHeight : 0,
+                _overlayPlayButtonHeight : 64,
+                _overlayPlayButtonWidth : 64,
+                _controlBarPaddingEnd: 8,
                 adjustControlSize : function adjustControlSize() {
-                  if (!this.controlBar.minWidth || this.videocontrols.isTouchControls) {
-                    return;
-                  }
-
-                  let videoWidth = this.video.clientWidth;
-                  let videoHeight = this.video.clientHeight;
-                  const minControlBarPaddingWidth = 18;
-
-                  if (this.video.readyState >= this.video.HAVE_METADATA) {
-                    if (!this.isAudioOnly && this.video.videoWidth && this.video.videoHeight) {
-                      let rect = this.video.getBoundingClientRect();
-                      let widthRatio = rect.width / this.video.videoWidth;
-                      let heightRatio = rect.height / this.video.videoHeight;
-                      let resizedWidth = this.video.videoWidth * Math.min(widthRatio, heightRatio);
-
-                      this.controlsContainer.style.width = `${resizedWidth}px`;
-                      this.controlsContainer.style.left = `${(videoWidth - resizedWidth) / 2}px`;
+                    let doc = this.video.ownerDocument;
 
-                      videoWidth = resizedWidth;
-                    } else {
-                      this.controlsContainer.style.width = "";
-                      this.controlsContainer.style.left = "";
-                    }
-                  }
-                  // Hide and show control in order.
-                  const prioritizedControls = [
-                    this.playButton,
-                    this.muteButton,
-                    this.fullscreenButton,
-                    this.closedCaptionButton,
-                    this.positionDurationBox,
-                    this.scrubberStack,
-                    this.durationSpan,
-                    this.volumeStack
-                  ];
+                    // The scrubber has |flex=1|, therefore |minScrubberWidth|
+                    // was generated by empirical testing.
+                    let minScrubberWidth = 25;
+                    let minWidthAllControls = this._playButtonWidth +
+                                              minScrubberWidth +
+                                              this._durationLabelWidth +
+                                              this._muteButtonWidth +
+                                              this._volumeControlWidth +
+                                              this._closedCaptionButtonWidth +
+                                              this._fullscreenButtonWidth;
 
-                  if (this.controlBar.hasAttribute("fullscreen-unavailable")) {
-                    this.fullscreenButton.isWanted = false;
-                  }
-                  if (!this.isClosedCaptionAvailable) {
-                    this.closedCaptionButton.isWanted = false;
-                  }
-                  if (this.muteButton.hasAttribute("noAudio")) {
-                    this.volumeStack.isWanted = false;
-                  }
-
-                  let widthUsed = minControlBarPaddingWidth;
-                  let preventAppendControl = false;
-
-                  for (let control of prioritizedControls) {
-                    if (!control.isWanted) {
-                      control.hideByAdjustment = true;
-                      continue;
+                    let isFullscreenUnavailable = this.controlBar.hasAttribute("fullscreen-unavailable");
+                    if (isFullscreenUnavailable) {
+                        // When the fullscreen button is hidden we add margin-end to the volume stack.
+                        minWidthAllControls -= this._fullscreenButtonWidth - this._controlBarPaddingEnd;
                     }
 
-                    control.hideByAdjustment = preventAppendControl ||
-                                               widthUsed + control.minWidth > videoWidth;
+                    let minHeightForControlBar = this._controlBarHeight;
+                    let minWidthOnlyPlayPause = this._playButtonWidth + this._muteButtonWidth;
+
+                    let isAudioOnly = this.isAudioOnly;
+                    let videoHeight = isAudioOnly ? minHeightForControlBar : this.video.clientHeight;
+                    let videoWidth = isAudioOnly ? minWidthAllControls : this.video.clientWidth;
 
-                    if (control.hideByAdjustment) {
-                      preventAppendControl = true;
-                    } else {
-                      widthUsed += control.minWidth;
-                    }
-                  }
-
-                  if (this.durationSpan.hideByAdjustment) {
-                    this.positionDurationBox.setAttribute("positionOnly", "true");
-                  } else {
-                    this.positionDurationBox.removeAttribute("positionOnly");
-                  }
+                    // Adapt the size of the controls to the size of the video
+                    if (this.video.readyState >= this.video.HAVE_METADATA) {
+                      if (!this.isAudioOnly && this.video.videoWidth && this.video.videoHeight) {
+                        var rect = this.video.getBoundingClientRect();
+                        var widthRatio = rect.width / this.video.videoWidth;
+                        var heightRatio = rect.height / this.video.videoHeight;
+                        var width = this.video.videoWidth * Math.min(widthRatio, heightRatio);
 
-                  if (videoHeight < this.controlBar.minHeight ||
-                      widthUsed === minControlBarPaddingWidth) {
-                    this.controlBar.setAttribute("size", "hidden");
-                    this.controlBar.hideByAdjustment = true;
-                  } else {
-                    this.controlBar.removeAttribute("size");
-                    this.controlBar.hideByAdjustment = false;
-                  }
-
-                  // Use flexible spacer to separate controls when scrubber is hidden.
-                  // As long as muteButton hidden, which means only play button presents,
-                  // hide spacer and make playButton centered.
-                  this.controlBarSpacer.hidden = !this.scrubberStack.hidden || this.muteButton.hidden;
+                        this.controlsOverlay.setAttribute("scaled", true);
+                        this.controlsOverlay.style.width = width + "px";
+                        this.controlsSpacer.style.width = width + "px";
+                        this.controlBar.style.width = width + "px";
+                      } else {
+                        this.controlsOverlay.removeAttribute("scaled");
+                        this.controlsOverlay.style.width = "";
+                        this.controlsSpacer.style.width = "";
+                        this.controlBar.style.width = "";
+                      }
+                    }
 
-                  // Adjust clickToPlayButton size.
-                  const minVideoSideLength = Math.min(videoWidth, videoHeight);
-                  const clickToPlayViewRatio = 0.15;
-                  const clickToPlayScaledSize = Math.max(
-                    this.clickToPlay.minWidth, minVideoSideLength * clickToPlayViewRatio);
-
-                  if (clickToPlayScaledSize >= videoWidth ||
-                    (clickToPlayScaledSize + this.controlBar.minHeight / 2 >= videoHeight / 2 )) {
+                    if ((this._overlayPlayButtonHeight + this._controlBarHeight) > videoHeight ||
+                        this._overlayPlayButtonWidth > videoWidth) {
+                        this.clickToPlay.hidden = true;
+                    } else if (this.clickToPlay.hidden &&
+                               !this.video.played.length &&
+                               this.video.paused) {
+                        // Check this.video.paused to handle when a video is
+                        // playing but hasn't processed any frames yet
+                        this.clickToPlay.hidden = false;
+                    }
 
-                    this.clickToPlay.hideByAdjustment = true;
-                  } else {
-                    if (this.clickToPlay.hidden && !this.video.played.length && this.video.paused) {
-                      this.clickToPlay.hideByAdjustment = false;
-                    }
-                    this.clickToPlay.style.width = `${clickToPlayScaledSize}px`;
-                    this.clickToPlay.style.height = `${clickToPlayScaledSize}px`;
-                  }
+                    let size = "normal";
+                    if (videoHeight < minHeightForControlBar)
+                        size = "hidden";
+                    else if (videoWidth < minWidthOnlyPlayPause)
+                        size = "hidden";
+                    else if (videoWidth < minWidthAllControls)
+                        size = "small";
+                    this.controlBar.setAttribute("size", size);
                 },
 
                 init : function (binding) {
                     this.video = binding.parentNode;
                     this.videocontrols = binding;
 
-                    this.controlsContainer    = document.getAnonymousElementByAttribute(binding, "anonid", "controlsContainer");
-                    this.statusIcon    = document.getAnonymousElementByAttribute(binding, "anonid", "statusIcon");
-                    this.controlBar    = document.getAnonymousElementByAttribute(binding, "anonid", "controlBar");
-                    this.playButton    = document.getAnonymousElementByAttribute(binding, "anonid", "playButton");
-                    this.controlBarSpacer    = document.getAnonymousElementByAttribute(binding, "anonid", "controlBarSpacer");
-                    this.muteButton    = document.getAnonymousElementByAttribute(binding, "anonid", "muteButton");
-                    this.volumeStack   = document.getAnonymousElementByAttribute(binding, "anonid", "volumeStack");
-                    this.volumeControl = document.getAnonymousElementByAttribute(binding, "anonid", "volumeControl");
-                    this.progressBar   = document.getAnonymousElementByAttribute(binding, "anonid", "progressBar");
-                    this.bufferBar     = document.getAnonymousElementByAttribute(binding, "anonid", "bufferBar");
-                    this.scrubberStack = document.getAnonymousElementByAttribute(binding, "anonid", "scrubberStack");
-                    this.scrubber      = document.getAnonymousElementByAttribute(binding, "anonid", "scrubber");
-                    this.durationLabel = document.getAnonymousElementByAttribute(binding, "anonid", "durationLabel");
-                    this.positionLabel = document.getAnonymousElementByAttribute(binding, "anonid", "positionLabel");
-                    this.positionDurationBox   = document.getAnonymousElementByAttribute(binding, "anonid", "positionDurationBox");
-                    this.statusOverlay = document.getAnonymousElementByAttribute(binding, "anonid", "statusOverlay");
-                    this.controlsOverlay = document.getAnonymousElementByAttribute(binding, "anonid", "controlsOverlay");
-                    this.controlsSpacer     = document.getAnonymousElementByAttribute(binding, "anonid", "controlsSpacer");
-                    this.clickToPlay        = document.getAnonymousElementByAttribute(binding, "anonid", "clickToPlay");
-                    this.fullscreenButton   = document.getAnonymousElementByAttribute(binding, "anonid", "fullscreenButton");
-                    this.closedCaptionButton = document.getAnonymousElementByAttribute(binding, "anonid", "closedCaptionButton");
-                    this.textTrackList = document.getAnonymousElementByAttribute(binding, "anonid", "textTrackList");
+                    this.statusIcon    = document.getAnonymousElementByAttribute(binding, "class", "statusIcon");
+                    this.controlBar    = document.getAnonymousElementByAttribute(binding, "class", "controlBar");
+                    this.playButton    = document.getAnonymousElementByAttribute(binding, "class", "playButton");
+                    this.muteButton    = document.getAnonymousElementByAttribute(binding, "class", "muteButton");
+                    this.volumeControl = document.getAnonymousElementByAttribute(binding, "class", "volumeControl");
+                    this.progressBar   = document.getAnonymousElementByAttribute(binding, "class", "progressBar");
+                    this.bufferBar     = document.getAnonymousElementByAttribute(binding, "class", "bufferBar");
+                    this.scrubber      = document.getAnonymousElementByAttribute(binding, "class", "scrubber");
+                    this.scrubberThumb = document.getAnonymousElementByAttribute(this.scrubber, "class", "scale-thumb");
+                    this.durationLabel = document.getAnonymousElementByAttribute(binding, "class", "durationLabel");
+                    this.positionLabel = document.getAnonymousElementByAttribute(binding, "class", "positionLabel");
+                    this.statusOverlay = document.getAnonymousElementByAttribute(binding, "class", "statusOverlay");
+                    this.controlsOverlay = document.getAnonymousElementByAttribute(binding, "class", "controlsOverlay");
+                    this.controlsSpacer     = document.getAnonymousElementByAttribute(binding, "class", "controlsSpacer");
+                    this.clickToPlay        = document.getAnonymousElementByAttribute(binding, "class", "clickToPlay");
+                    this.fullscreenButton   = document.getAnonymousElementByAttribute(binding, "class", "fullscreenButton");
+                    this.volumeForeground   = document.getAnonymousElementByAttribute(binding, "anonid", "volumeForeground");
+                    this.closedCaptionButton = document.getAnonymousElementByAttribute(binding, "class", "closedCaptionButton");
+                    this.textTrackList = document.getAnonymousElementByAttribute(binding, "class", "textTrackList");
 
-                    if (this.positionDurationBox) {
-                      this.durationSpan = this.positionDurationBox.getElementsByTagName("span")[0];
-                    }
-
-                    // XXX controlsContainer is a desktop only element. To determine whether
-                    // isTouchControls or not during the whole initialization process, get
-                    // this state overridden here.
-                    this.videocontrols.isTouchControls = !this.controlsContainer;
                     this.isAudioOnly = (this.video instanceof HTMLAudioElement);
                     this.setupInitialState();
                     this.setupNewLoadState();
                     this.initTextTracks();
 
                     // Use the handleEvent() callback for all media events.
                     // Only the "error" event listener must capture, so that it can trap error
                     // events from <source> children, which don't bubble. But we use capture
@@ -1767,47 +1574,40 @@
 
                     // Helper function to add an event listener to the given element
                     function addListener(elem, eventName, func) {
                       let boundFunc = func.bind(self);
                       self.controlListeners.push({ item: elem, event: eventName, func: boundFunc });
                       elem.addEventListener(eventName, boundFunc, { mozSystemGroup: true });
                     }
 
-                    addListener(this.muteButton, "click", this.toggleMute);
-                    addListener(this.closedCaptionButton, "click", this.toggleClosedCaption);
-                    addListener(this.fullscreenButton, "click", this.toggleFullscreen);
+                    addListener(this.muteButton, "command", this.toggleMute);
+                    addListener(this.closedCaptionButton, "command", this.toggleClosedCaption);
                     addListener(this.playButton, "click", this.clickToPlayClickHandler);
+                    addListener(this.fullscreenButton, "command", this.toggleFullscreen);
                     addListener(this.clickToPlay, "click", this.clickToPlayClickHandler);
                     addListener(this.controlsSpacer, "click", this.clickToPlayClickHandler);
                     addListener(this.controlsSpacer, "dblclick", this.toggleFullscreen);
 
                     addListener(this.videocontrols, "resizevideocontrols", this.adjustControlSize);
                     addListener(this.videocontrols, "transitionend", this.onTransitionEnd);
                     addListener(this.video.ownerDocument, "mozfullscreenchange", this.onFullscreenChange);
-                    addListener(this.controlBar, "transitionend", this.onControlBarTransitioned);
+                    addListener(this.videocontrols, "transitionend", this.onControlBarTransitioned);
                     addListener(this.video.ownerDocument, "fullscreenchange", this.onFullscreenChange);
                     addListener(this.video, "keypress", this.keyHandler);
+                    addListener(this.video.textTracks, "addtrack", this.onTextTrackAdd);
+                    addListener(this.video.textTracks, "removetrack", this.onTextTrackRemove);
 
                     addListener(this.videocontrols, "dragstart", function(event) {
                         event.preventDefault(); // prevent dragging of controls image (bug 517114)
                     });
 
-                    if (!this.videocontrols.isTouchControls) {
-                      addListener(this.scrubber, "input", this.onScrubberInput);
-                      addListener(this.scrubber, "change", this.onScrubberChange);
-                      addListener(this.volumeControl, "input", this.updateVolume);
-                      addListener(this.video.textTracks, "addtrack", this.onTextTrackAdd);
-                      addListener(this.video.textTracks, "removetrack", this.onTextTrackRemove);
-                    }
-
                     this.log("--- videocontrols initialized ---");
                 }
             };
-
             this.Utils.init(this);
             ]]>
         </constructor>
         <destructor>
             <![CDATA[
             this.Utils.terminateEventListeners();
             // randomID used to be a <field>, which meant that the XBL machinery
             // undefined the property when the element was unbound. The code in
@@ -1816,91 +1616,89 @@
             delete this.randomID;
             ]]>
         </destructor>
 
     </implementation>
 
     <handlers>
         <handler event="mouseover">
-            if (!this.isTouchControls)
+            if (!this.isTouchControl)
                 this.Utils.onMouseInOut(event);
         </handler>
         <handler event="mouseout">
-            if (!this.isTouchControls)
+            if (!this.isTouchControl)
                 this.Utils.onMouseInOut(event);
         </handler>
         <handler event="mousemove">
-            if (!this.isTouchControls)
+            if (!this.isTouchControl)
                 this.Utils.onMouseMove(event);
         </handler>
     </handlers>
   </binding>
 
   <binding id="touchControls" extends="chrome://global/content/bindings/videocontrols.xml#videoControls">
 
     <xbl:content xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul" class="mediaControlsFrame">
         <stack flex="1">
-            <vbox anonid="statusOverlay" flex="1" class="statusOverlay" hidden="true">
-                <box anonid="statusIcon" class="statusIcon"/>
+            <vbox flex="1" class="statusOverlay" hidden="true">
+                <box class="statusIcon"/>
                 <label class="errorLabel" anonid="errorAborted">&error.aborted;</label>
                 <label class="errorLabel" anonid="errorNetwork">&error.network;</label>
                 <label class="errorLabel" anonid="errorDecode">&error.decode;</label>
                 <label class="errorLabel" anonid="errorSrcNotSupported">&error.srcNotSupported;</label>
                 <label class="errorLabel" anonid="errorNoSource">&error.noSource2;</label>
                 <label class="errorLabel" anonid="errorGeneric">&error.generic;</label>
             </vbox>
 
-            <vbox anonid="controlsOverlay" class="controlsOverlay">
-                <spacer anonid="controlsSpacer" class="controlsSpacer" flex="1"/>
+            <vbox class="controlsOverlay">
+                <spacer class="controlsSpacer" flex="1"/>
                 <box flex="1" hidden="true">
-                    <box anonid="clickToPlay" class="clickToPlay" hidden="true" flex="1"/>
-                    <vbox anonid="textTrackList" class="textTrackList" hidden="true" offlabel="&closedCaption.off;"></vbox>
+                    <box class="clickToPlay" hidden="true" flex="1"/>
+                    <vbox class="textTrackList" hidden="true" offlabel="&closedCaption.off;"></vbox>
                 </box>
-                <vbox anonid="controlBar" class="controlBar" hidden="true">
+                <vbox class="controlBar" hidden="true">
                     <hbox class="buttonsBar">
-                        <button anonid="playButton"
-                                class="playButton"
+                        <button class="playButton"
                                 playlabel="&playButton.playLabel;"
                                 pauselabel="&playButton.pauseLabel;"/>
-                        <label anonid="positionLabel" class="positionLabel" role="presentation"/>
-                        <stack anonid="scrubberStack" class="scrubberStack">
+                        <label class="positionLabel" role="presentation"/>
+                        <stack class="scrubberStack">
                             <box class="backgroundBar"/>
                             <progressmeter class="flexibleBar" value="100"/>
-                            <progressmeter anonid="bufferBar" class="bufferBar"/>
-                            <progressmeter anonid="progressBar" class="progressBar" max="10000"/>
-                            <scale anonid="scrubber" class="scrubber" movetoclick="true"/>
+                            <progressmeter class="bufferBar"/>
+                            <progressmeter class="progressBar" max="10000"/>
+                            <scale class="scrubber" movetoclick="true"/>
                         </stack>
-                        <label anonid="durationLabel" class="durationLabel" role="presentation"/>
-                        <button anonid="muteButton"
-                                class="muteButton"
+                        <label class="durationLabel" role="presentation"/>
+                        <button class="muteButton"
                                 mutelabel="&muteButton.muteLabel;"
                                 unmutelabel="&muteButton.unmuteLabel;"/>
-                        <stack anonid="volumeStack" class="volumeStack">
-                          <box anonid="volumeBackground" class="volumeBackground"/>
-                          <box anonid="volumeForeground" class="volumeForeground"/>
-                          <scale anonid="volumeControl" class="volumeControl" movetoclick="true"/>
+                        <stack class="volumeStack">
+                          <box class="volumeBackground"/>
+                          <box class="volumeForeground" anonid="volumeForeground"/>
+                          <scale class="volumeControl" movetoclick="true"/>
                         </stack>
-                        <button anonid="castingButton" class="castingButton" hidden="true"
+                        <button class="castingButton" hidden="true"
                                 aria-label="&castingButton.castingLabel;"/>
-                        <button anonid="closedCaptionButton" class="closedCaptionButton" hidden="true"/>
-                        <button anonid="fullscreenButton"
-                            class="fullscreenButton"
+                        <button class="closedCaptionButton" hidden="true"/>
+                        <button class="fullscreenButton"
                             enterfullscreenlabel="&fullscreenButton.enterfullscreenlabel;"
                             exitfullscreenlabel="&fullscreenButton.exitfullscreenlabel;"/>
                     </hbox>
                 </vbox>
             </vbox>
         </stack>
     </xbl:content>
 
     <implementation>
+
         <constructor>
           <![CDATA[
-          this.isTouchControls = true;
+          this.isTouchControl = true;
           this.TouchUtils = {
             videocontrols: null,
             video: null,
             controlsTimer: null,
             controlsTimeout: 5000,
             positionLabel: null,
             castingButton: null,
 
@@ -2025,17 +1823,17 @@
               this.Utils.scrubber.addEventListener("touchstart", function() {
                 self.clearTimer();
               }, false);
               this.Utils.scrubber.addEventListener("touchend", function() {
                 self.delayHideControls(self.controlsTimeout);
               }, false);
               this.Utils.muteButton.addEventListener("click", function() { self.delayHideControls(self.controlsTimeout); }, false);
 
-              this.castingButton = document.getAnonymousElementByAttribute(binding, "anonid", "castingButton");
+              this.castingButton = document.getAnonymousElementByAttribute(binding, "class", "castingButton");
               this.castingButton.addEventListener("command", function() {
                 self.startCasting();
               }, false);
 
               this.video.addEventListener("media-videoCasting", function (e) {
                 if (!e.isTrusted)
                   return;
                 self.updateCasting(e.detail);
@@ -2055,18 +1853,17 @@
               // transitioned into or out of fullscreen mode, and we don't want
               // the controls to remain visible. this.controlsTimeout is a full
               // 5s, which feels too long after the transition.
               if (this.video.currentTime !== 0) {
                 this.delayHideControls(this.Utils.HIDE_CONTROLS_TIMEOUT_MS);
               }
             }
           };
-
-          this.TouchUtils.init(this)
+          this.TouchUtils.init(this);
           this.dispatchEvent(new CustomEvent("VideoBindingAttached"));
       ]]>
       </constructor>
       <destructor>
           <![CDATA[
           // XBL destructors don't appear to be inherited properly, so we need
           // to do this here in addition to the videoControls destructor. :-(
           delete this.randomID;
--- a/toolkit/locales/en-US/chrome/global/videocontrols.dtd
+++ b/toolkit/locales/en-US/chrome/global/videocontrols.dtd
@@ -32,18 +32,8 @@
 <!ENTITY error.generic "Video playback aborted due to an unknown error.">
 
 <!-- LOCALIZATION NOTE (scrubberScale.nameFormat): the #1 string is the current
 media position, and the #2 string is the total duration. For example, when at
 the 5 minute mark in a 6 hour long video, #1 would be "5:00" and #2 would be
 "6:00:00", result string would be "5:00 of 6:00:00 elapsed".
 -->
 <!ENTITY scrubberScale.nameFormat "#1 of #2 elapsed">
-
-<!-- LOCALIZATION NOTE (positionAndDuration.nameFormat): the #1 string is the current
-media position, and the #2 string is the total duration. For example, when at
-the 5 minute mark in a 6 hour long video, #1 would be "5:00" and #2 would be
-"6:00:00", result string would be "5:00 / 6:00:00".
-Note that #2 is not always avaiable. For example, when at the 5 minute mark in an
-unknown duration video, #1 would be "5:00" and string which is surrounded by <span>
-would be deleted, result string would be "5:00".
--->
-<!ENTITY positionAndDuration.nameFormat "#1<span> / #2</span>">
--- a/toolkit/themes/shared/jar.inc.mn
+++ b/toolkit/themes/shared/jar.inc.mn
@@ -59,24 +59,41 @@ toolkit.jar:
   skin/classic/global/reader/RM-Content-Width-Plus-44x16.svg             (../../shared/reader/RM-Content-Width-Plus-44x16.svg)
   skin/classic/global/reader/RM-Line-Height-Minus-38x14.svg            (../../shared/reader/RM-Line-Height-Minus-38x14.svg)
   skin/classic/global/reader/RM-Line-Height-Plus-38x24.svg             (../../shared/reader/RM-Line-Height-Plus-38x24.svg)
   skin/classic/global/media/TopLevelImageDocument.css      (../../shared/media/TopLevelImageDocument.css)
   skin/classic/global/media/TopLevelVideoDocument.css      (../../shared/media/TopLevelVideoDocument.css)
   skin/classic/global/media/imagedoc-lightnoise.png        (../../shared/media/imagedoc-lightnoise.png)
   skin/classic/global/media/imagedoc-darknoise.png         (../../shared/media/imagedoc-darknoise.png)
 * skin/classic/global/media/videocontrols.css              (../../shared/media/videocontrols.css)
-  skin/classic/global/media/pauseButton.svg                (../../shared/media/pauseButton.svg)
-  skin/classic/global/media/playButton.svg                 (../../shared/media/playButton.svg)
-  skin/classic/global/media/muteButton.svg                 (../../shared/media/muteButton.svg)
-  skin/classic/global/media/closedCaptionButton.svg        (../../shared/media/closedCaptionButton.svg)
-  skin/classic/global/media/fullscreenButton.svg           (../../shared/media/fullscreenButton.svg)
+  skin/classic/global/media/pauseButton.png                (../../shared/media/pauseButton.png)
+  skin/classic/global/media/pauseButton@2x.png             (../../shared/media/pauseButton@2x.png)
+  skin/classic/global/media/playButton.png                 (../../shared/media/playButton.png)
+  skin/classic/global/media/playButton@2x.png              (../../shared/media/playButton@2x.png)
+  skin/classic/global/media/muteButton.png                 (../../shared/media/muteButton.png)
+  skin/classic/global/media/muteButton@2x.png              (../../shared/media/muteButton@2x.png)
+  skin/classic/global/media/unmuteButton.png               (../../shared/media/unmuteButton.png)
+  skin/classic/global/media/unmuteButton@2x.png            (../../shared/media/unmuteButton@2x.png)
+  skin/classic/global/media/noAudio.png                    (../../shared/media/noAudio.png)
+  skin/classic/global/media/noAudio@2x.png                 (../../shared/media/noAudio@2x.png)
+  skin/classic/global/media/closeCaptionButton.png         (../../shared/media/closeCaptionButton.png)
+  skin/classic/global/media/closeCaptionButton@2x.png      (../../shared/media/closeCaptionButton@2x.png)
+  skin/classic/global/media/fullscreenButton.png           (../../shared/media/fullscreenButton.png)
+  skin/classic/global/media/fullscreenButton@2x.png        (../../shared/media/fullscreenButton@2x.png)
+  skin/classic/global/media/scrubberThumb.png              (../../shared/media/scrubberThumb.png)
+  skin/classic/global/media/scrubberThumb@2x.png           (../../shared/media/scrubberThumb@2x.png)
+  skin/classic/global/media/scrubberThumbWide.png          (../../shared/media/scrubberThumbWide.png)
+  skin/classic/global/media/scrubberThumbWide@2x.png       (../../shared/media/scrubberThumbWide@2x.png)
   skin/classic/global/media/error.png                      (../../shared/media/error.png)
   skin/classic/global/media/throbber.png                   (../../shared/media/throbber.png)
   skin/classic/global/media/stalled.png                    (../../shared/media/stalled.png)
+  skin/classic/global/media/volume-empty.png               (../../shared/media/volume-empty.png)
+  skin/classic/global/media/volume-empty@2x.png            (../../shared/media/volume-empty@2x.png)
+  skin/classic/global/media/volume-full.png                (../../shared/media/volume-full.png)
+  skin/classic/global/media/volume-full@2x.png             (../../shared/media/volume-full@2x.png)
   skin/classic/global/media/clicktoplay-bgtexture.png      (../../shared/media/clicktoplay-bgtexture.png)
   skin/classic/global/media/videoClickToPlayButton.svg     (../../shared/media/videoClickToPlayButton.svg)
 #ifdef MOZ_PLACES
   skin/classic/mozapps/places/defaultFavicon.png           (../../shared/places/defaultFavicon.png)
   skin/classic/mozapps/places/defaultFavicon@2x.png        (../../shared/places/defaultFavicon@2x.png)
   skin/classic/mozapps/places/defaultFavicon-inverted.png  (../../shared/places/defaultFavicon-inverted.png)
   skin/classic/mozapps/places/defaultFavicon-inverted@2x.png (../../shared/places/defaultFavicon-inverted@2x.png)
 #endif
--- a/toolkit/themes/shared/media/TopLevelVideoDocument.css
+++ b/toolkit/themes/shared/media/TopLevelVideoDocument.css
@@ -3,11 +3,10 @@
  * You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 body {
   background-image: url("chrome://global/skin/media/imagedoc-darknoise.png");
   background-color: rgb(33,33,33); /* Average color of that ^ image. */
 }
 
 video {
-  border: 1px #000000 solid;
-  box-shadow: 0 0 5px rgba(0,0,0,0.6);
+  box-shadow: 0 0 15px #000;
 }
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..469310fb1b21ed705925decd18710dd0df37d915
GIT binary patch
literal 583
zc$@)80=WH&P)<h;3K|Lk000e1NJLTq000~S000~a1ONa4*aR0J0006GNkl<ZcmeH_
zKWGzS7{;HWWDq2_UZH9T=^)YuOG`9SDy8)=Hh<duyKu?feMb@vv1wYdT)?42a1mWy
zTy=DE5phU6NWoM~#X=Mp!6_6AHa%!kdA$qS@=;fZKELI?=jF!@-;1OCpRw&0>G9$0
z7GXnI1j>_Uv8{b)8|;(1qO2(E=JZXgTfIdd0=nWPM(pX`zAR)U5JLpBCJ}Q=AZ5=!
z$ys|i(G?e|4R$<a_f*rZ^4{{h2pl-`I<U9gDu2$Mx^OJ`n~@3^PgFKljC>4Jv7t6K
zdhlxO<$2N%v>ir;FA_%987X{GUen<IHP=)e*=re+-)n0c$;piU&W^I3huiw%i^&Re
z_=weHO!QpopFVkgGeb#l0KQ)Tz$DxiMoGRXt*WQTN&2c_(9xG0zU=*=k#y6CUisX;
zA-GmmlK7%nRdMNu*i`&Ol~H=Q!Cs_De10oF&?*`87_6!!^2KN^1y5O|*nX*bpQ2Lm
zMx3I5ibl!Q18{GpD9RVZ2h#9Z&-kN6J@zv;C&Gt|lDHMG$DbumOq?AxBntDz5Y5!m
zx>uNLKfe$C5a7Wq;`Xca-ddVwD8v{2CK4@>-qMYw#-dR$3XKJ0X<sLu7D=-9Jkj|k
zM7KLkQ^5Lvn}8{F`nN&e$qAT*46O}=3I%c-6|B?BnBpC|%`Ba89fA`AZ1{JM@)uMS
V3)yh#?6?2`002ovPDHLkV1fX94?q9_
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..03350789221b94d830ebc4dafb1b6e4447f79f71
GIT binary patch
literal 1335
zc$@(@1<3k|P)<h;3K|Lk000e1NJLTq001}u001}$1ONa40*~{R000F3Nkl<ZcmeIz
zTWB0_9metR%saE^O`2?zHqEK6w8_6`C6U&)Y6Yu^rCM90h)`OKih5BH!Mj4mB7$NM
zH-##Q7fPj4L9`x_YS9wf(r6FqHmA+TY?E}eNoIFvX6Nt<n*=Gry1Th_KR?)oxq0}#
z&pW%+)z#J2)%{Njt08+hMVz%UxW!9WQRM1J!uz%wW6k`$xQtiHhB0}83@&S<(Wd;6
z{OZT6#ovx|lwpw)Gr~~vYE}hHu@%aMj7ezl<1#K=y>4%t8<MPW$q=tBFo46dpND_2
zZZJ^t@$iuN_)z{{qLfFVmPgZ+oz6EF&lOnW5P(Vo6(nWXqhF7)ND+$?4(?mA0LpTd
zKtm_!1_vWwidph&h5ufd$~$~t<rM?m-#swoS-tY0w|{ZVU*>tj;L6;7o$K}v$b<II
zQSI}Oxz7N}@2Xyvuf=A07$B+k%<+`z2U`DGwUrgP_qa=$?9)Gk`kz}l_mh?dTG=(w
z((eK&e`UOi4WB@Y4CdaG>Uw4wVTdGY^4dp?-3A7W9r|%>CP^~H2-9k4-RX-ZGNcAs
zQCWu|0Supc?6IEEX2!5RejDoc%1MdP$0E;>i=V_GgPahLf=8`rmIbZr?E5c1Bv*8i
zlvUNC?PH^aKFAa{d|~~u4f{6zIt*mP;j0^dx<1}U200@3w4Z1_&<40nian^<whPq-
zN+eQxxP;;f4CHI|md%)-z7{|tncdX2sfQVS<dyJ3hLL~H|2}}k4u=TgN(Wh<>W&m2
z|KsbT77_*&Kgk&3zrVMm!w-h1rTwE$41nPRPs!1Kepk3fwKk3up%n0u)pc0rxX3LH
z6an%+DJBTz11~fhFp#AnK7cpJ1oPMvQ96(>@_;OOHC-B2!a|S|KvbcCi%E(+AuK#o
zA^{RbOg!d!&Lk=Z1%y`hh8{pnMS0}n0W|4&fPdHS4;NKEa-%roA_2N29$-xgp*u>X
zu{lkoLEzPJqyiXr(@Lj=_p}(0r+;hHi6-FCAAeOs2k37AKxsWH+QBz?Mp<=%K0ruC
z;{HiF<3Wr3O)oRobghpCfUCtJ%M$`P(s?<8edK+ji3Lbc6M?XbUqgq@I#BurXCz>L
z_@jRBp@<3-@KCueFm5-UvZ0A@otJNvHd2`IJ%<QpLc^;eFd<Mde>Z=t`IJS8oVo!R
zN5VHFSeW10`e{2X$*PUCQ=|xg3;fu|M`_k^YY5z?At*Bam5v5JVKPY;7YDwaxHn4{
z{~y`UcK&iEW|Jg{iF~P_j@zS{1hxk$*3e<xx!Hd1DX-_Ij`e)XK9lRS;1AL3iAQ<T
zEZ{S7H_^N0Z0@+xX{N=`8gDijBV;hIbhWrObx84ZAL<+4J4ez{?{wYiLI-TJydsT-
zWRmc|{7WsDHX`sSkRnO;&-&iOyg}BmA%3I2>%4sYYWBwX&0H=)6p6tUljQJ#MUoh_
z(}Yeb^yXyl0((B7?o&1FYX5+DvLwV-1Z8f?a~xNebW8Vz!~%3gNp%7;D0Drb=_mmB
zjIA`NJY&4Fz#Xj6XeL5{01EFWaVSw_4u@sRbH*z=(v;Hev&3PVB?5t39smJI{N+y%
zk5#{)DYeoL<rm{O3cU_*b8)G{GySVkWMv(;v7haPP^g{6BFO_Xm27A*0>n|NozEhp
t7*I)|$tbe~*0^B_1C##;b#--h{|0<^JW)j^8BzcM002ovPDHLkV1f*Ie}e!3
deleted file mode 100644
--- a/toolkit/themes/shared/media/closedCaptionButton.svg
+++ /dev/null
@@ -1,55 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="18px" height="18px" viewBox="0 0 18 18">
-  <style>
-    use:not(:target) {
-      display: none;
-    }
-    use {
-      fill: #ffffff;
-    }
-    use[id$="-hover"] {
-      fill: #48a0f7;
-    }
-    use[id$="-active"] {
-      fill: #2d89e6;
-    }
-    use[id$="-focus"] {
-      fill: #48a0f7;
-    }
-    use[id$="-disabled"] {
-      fill: #ffffff;
-    }
-  </style>
-  <symbol id="cc-off-shape">
-    <path fill-rule="evenodd" clip-rule="evenodd" d="M16.531,16.107H5.267l1.982-2H15c0.6,0,1-0.4,1-1V5.274
-      l1.946-1.964C17.963,3.399,18,3.483,18,3.576v11.031C18,15.407,17.331,16.107,16.531,16.107z M14.016,8.506h-1.218l1.005-1.014
-      C13.913,7.789,13.984,8.128,14.016,8.506z M11.786,12.361c-0.828,0-1.476-0.326-1.913-0.902l1.09-1.101
-      c0.136,0.323,0.374,0.541,0.796,0.541c0.514,0,0.695-0.44,0.756-1.014h1.535C13.908,11.43,13.071,12.361,11.786,12.361z
-       M1.496,16.106C0.697,16.104,0,15.406,0,14.607V3.576c0-0.8,0.7-1.5,1.5-1.5h12.846L16.299,0l1.316,1.283L2.615,17.13L1.496,16.106
-      z M3,4.107c-0.6,0-1,0.4-1,1v8c0,0.6,0.4,1,1,1h0.029l2.031-2.16c-0.757-0.503-1.191-1.457-1.191-2.744
-      c0-1.936,1.069-3.14,2.428-3.14c1.357,0,2.136,0.76,2.361,2.059l3.777-4.016H3z M8.298,8.506H7.355
-      c-0.047-0.623-0.49-1.23-0.99-1.23c-0.561,0-1.337,0.84-1.337,1.995c0,0.674,0.381,1.427,0.95,1.702L8.298,8.506z"/>
-  </symbol>
-
-  <symbol id="cc-shape">
-    <path d="M16.531,1.984H1.5c-0.8,0-1.5,0.7-1.5,1.5v11.031c0,0.8,0.7,1.5,1.5,1.5h15.031
-      c0.8,0,1.469-0.7,1.469-1.5V3.484C18,2.684,17.331,1.984,16.531,1.984z M16,13.016c0,0.6-0.4,1-1,1H3c-0.6,0-1-0.4-1-1v-8
-      c0-0.6,0.4-1,1-1h12c0.6,0,1,0.4,1,1V13.016z M6.426,10.807c-0.811,0-0.96-0.789-0.96-1.628c0-1.155,0.338-1.745,0.899-1.745
-      c0.5,0,0.818,0.357,0.866,0.98h1.484C8.585,6.877,7.785,5.972,6.297,5.972c-1.359,0-2.428,1.205-2.428,3.14
-      c0,1.944,0.974,3.157,2.583,3.157c1.285,0,2.153-0.93,2.295-2.476H7.244C7.183,10.367,6.94,10.807,6.426,10.807z M11.759,10.807
-      c-0.811,0-0.96-0.789-0.96-1.628c0-1.155,0.338-1.745,0.899-1.745c0.5,0,0.756,0.357,0.803,0.98h1.515
-      c-0.129-1.537-0.898-2.443-2.385-2.443c-1.359,0-2.396,1.205-2.396,3.14c0,1.944,0.943,3.157,2.552,3.157
-      c1.285,0,2.122-0.93,2.264-2.476h-1.535C12.454,10.367,12.273,10.807,11.759,10.807z"/>
-  </symbol>
-  <use id="cc" xlink:href="#cc-shape"/>
-  <use id="cc-hover" xlink:href="#cc-shape"/>
-  <use id="cc-active" xlink:href="#cc-shape"/>
-  <use id="cc-focus" xlink:href="#cc-shape"/>
-  <use id="cc-disabled" xlink:href="#cc-shape"/>
-
-  <use id="cc-off" xlink:href="#cc-off-shape"/>
-  <use id="cc-off-hover" xlink:href="#cc-off-shape"/>
-  <use id="cc-off-active" xlink:href="#cc-off-shape"/>
-  <use id="cc-off-focus" xlink:href="#cc-off-shape"/>
-  <use id="cc-off-disabled" xlink:href="#cc-off-shape"/>
-</svg>
index 362a293f223fe1c29751b711de8c48de950ebd49..58e37283a73eff086420d0969544fa8bc5dd7924
GIT binary patch
literal 433
zc$@*T0Z#sjP)<h;3K|Lk000e1NJLTq001Na001Ni1^@s6;Q*MJ0004aNkl<ZSi`m0
zQLcj^5Cu@0v;<A+0!(b${V%}o&SEndKon-?`f)#AV&H`G^n&@$v!UF4I-jRcPk);{
z%d)Ui8iU5}X|67wD?D)b8GSxcCLebJ$kEvGTq7Aw(B_zscaBnm9F19;Yc<>qE!pQJ
z2}%Jv!-RC}gG1$^1SJHuVAc#RE0mxFpjOPbLT7uZx~D4PV75K9=Hc@Kqd1rs8B9EY
zm7;_jIL6rgJ)}YjH}DQq0*O$<4ZOn~fut*CwU|HX<lmKp;^dDxnz!~sL!-8pk%Ew@
z<Y&@=5UAar(SkIn;s!>50*VWAoTA4CIRVIC1>(H)s^2~>NQz-MPgK(re~`H#6sEa(
zqM9BXbqE5Ms}51}5Ev``AQw?;OrfBuP>|XQ>Qe~_iBX}#F=zr~B&aDIgL*{M12xay
z(3Oa~>4BQ(v*jq=)bv2jvwD<nZhC;`nH;4{7gl39-hwZz9tU&X^Y>7=(i`$?wu`Rx
bigWz{uoo^%o)rPO00000NkvXXu0mjfb>P7_
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..ffbc3d5ae4627d9beb7c4e8c6ef80542e7e1414c
GIT binary patch
literal 733
zc$@*<0wVp1P)<h;3K|Lk000e1NJLTq001BW000mO1ONa4-3hhQ0000PbVXQnQ*UN;
zcVTj606}DLVr3vnZDD6+Qe|Oed2z{QJOBU!e@R3^R5(wKQr}C{Q4~L8`_eL~udZa(
zw|%$RVAF?wJoF$T5)vzsxgRPu-H)$Bm^I9)o8UHWLiy07U@u|p-S>!~haiZcs4TUK
zN%fHUw2kH;a60#X{f<DW&Ic~{bI!fzo_o#*;9sV%bv|za-2uPu#j#o!=mCtltYUWn
z3_N7m9ngGmWUU7adv{AGK&ba=aoPz*)7~5w%Dn()oMBi|zyU^nzzB{NMfHNE<NWtK
zn62eE6<h?7$3<K$M{4t!`#EvtB7has4BxW7?I7?2Lbq!>qk6#(vg|ESVg~PF3M3wv
zFhwl8J!KDol_f|$NUcp{rk1Bdb)YMnD0_C3ymZ9|hoNox7EUp+<G^lk_GAp&p^5U9
z!Vow;Tu$Qb8z0pmy!PPi*Q8|_0u+%z_<R!=aFU^sfHPe97-Thz^miMy$=-YfT=f4#
z;LJzP`YF4OA|iS0;D#ZH&}!xh%(RP;=Nd(*YX({bDpaQHt;7tpy6CMY@)|i8sSYc_
z+-S0ybBQAAT*!3$$C;@q4^IBCrh9g@dYQ?BOke4E+Wh|s48N{}u+&nY#<>kQy{=!q
ziu3jK<KrMugubxj!Ga3y3mV_?u$o1jS-(+DVd96<d4V<Y(z&fD-ma!Mf+Qr?L`P{5
zV+>joRaP2Qr6-|6Qyu#<BKxQ@G)9om^nDt^IC&K|#x7?$fl-FW7&+TYbi3FXtr%i>
z6y~xZAu;JJg;g)u?l)H^aCBA4#ffPNLb>?cD2`T=MH8b#9OLi&nv~!Ba9s6*{iPdY
z>!FiD2t4#_Ql?#?HTWTfu~$6@WWk#Bhjc99O!iCOhOC(FOYf8?*$=MY`h^(+ky7qW
P00000NkvXXu0mjfwAEM1
deleted file mode 100644
--- a/toolkit/themes/shared/media/fullscreenButton.svg
+++ /dev/null
@@ -1,47 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="18px" height="18px" viewBox="0 0 18 18">
-  <style>
-    use:not(:target) {
-      display: none;
-    }
-    use {
-      fill: #ffffff;
-    }
-    use[id$="-hover"] {
-      fill: #48a0f7;
-    }
-    use[id$="-active"] {
-      fill: #2d89e6;
-    }
-    use[id$="-focus"] {
-      fill: #48a0f7;
-    }
-    use[id$="-disabled"] {
-      fill: #ffffff;
-    }
-  </style>
-  <symbol id="fullscreen-shape">
-    <path d="M6.728,10.188l-3.235,3.094l0.017-2.267l-1.513-0.016l0,5l4.987-0.008l0.011-1.537l-2.281-0.022
-  l3.097-3.158L6.728,10.188z M14.453,11.004l-0.022,2.281l-3.158-3.097l-1.086,1.083l3.094,3.235l-2.267-0.017l-0.016,1.514l5,0
-  l-0.008-4.988L14.453,11.004z M11.015,2.01l-0.011,1.537l2.281,0.022l-3.097,3.158l1.083,1.086l3.235-3.094L14.49,6.986
-  l1.513,0.016v-5L11.015,2.01z M6.986,3.511l0.016-1.514l-5,0L2.01,6.985l1.537,0.011l0.022-2.281l3.158,3.097l1.086-1.083
-  L4.718,3.494L6.986,3.511z"/>
-  </symbol>
-  <symbol id="unfullscreen-shape">
-    <path d="M2.047,11.135l-0.011,1.537l2.281,0.022L1.22,15.851l1.083,1.086l3.235-3.094l-0.017,2.268l1.513,0.016
-  l0-5L2.047,11.135z M13.781,12.587l2.267,0.017l0.016-1.514l-5,0l0.008,4.988l1.537,0.011l0.022-2.281l3.158,3.097l1.086-1.083
-  L13.781,12.587z M16.058,5.578l-2.281-0.021l3.097-3.158l-1.083-1.086l-3.235,3.094l0.017-2.267L11.06,2.123v5l4.988-0.008
-  L16.058,5.578z M5.516,2.098L5.494,4.379L2.336,1.283L1.25,2.365L4.344,5.6L2.077,5.583L2.06,7.097l5,0L7.053,2.109L5.516,2.098z"/>
-  </symbol>
-  <use id="fullscreen" xlink:href="#fullscreen-shape"/>
-  <use id="fullscreen-hover" xlink:href="#fullscreen-shape"/>
-  <use id="fullscreen-active" xlink:href="#fullscreen-shape"/>
-  <use id="fullscreen-focus" xlink:href="#fullscreen-shape"/>
-  <use id="fullscreen-disabled" xlink:href="#fullscreen-shape"/>
-
-  <use id="unfullscreen" xlink:href="#unfullscreen-shape"/>
-  <use id="unfullscreen-hover" xlink:href="#unfullscreen-shape"/>
-  <use id="unfullscreen-active" xlink:href="#unfullscreen-shape"/>
-  <use id="unfullscreen-focus" xlink:href="#unfullscreen-shape"/>
-  <use id="unfullscreen-disabled" xlink:href="#unfullscreen-shape"/>
-</svg>
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..b09ebbd43ce8dd62741992a0d00df1018897d164
GIT binary patch
literal 1759
zc$@*>1|a!~P)<h;3K|Lk000e1NJLTq002M$001Be1^@s6qMd$(000K2Nkl<Zc-q}r
zTTfJ17{yDYPdWm%v?VQRe4zFcY*VXk+SsO*!34BHf`tKL26V8<pdE$*2Bj_DT9}fw
zf~ARx`e5Wi5_!`%{)34R#uyWgJ{XA?6w%nVCf`Z6o4sex#2TX~Sz*pO-(|10_t}?^
zoF`A7yb#ExKVSa5^XfUC_4?n0n4O*d9{2w|eE9IQ=S6;IX67UO9eMQVQH7qLH~(gU
z3YP%1$t0HAfCmpAtS5QkFmPmgdU~~mM7jC7+ve`wyC384u;dtp7#mdq7P}gJ;lhOg
z?0mpNn*j38M_X4s$(eKc^5r*48u$a~0+J>Xq`{-iVIwc^gq)H5kmNW-!EfBS@t(({
z01x6e3=IwKfQ=tm!G@<1V6oWv>60!da{}{#WrKr*RgWJ(?!<F~?+1Yq5rHG5LPp3z
z3Y<m&A8lw$ABFs3As=TBVq|2b7WR1_k0M(`Pn|l|h4*1#oiy4t0t&=7eEj(Ft~3G^
z0Skb)fr>3#wsc}1i0dL?PH6GS^Brsp(+E&V8&3rIHtFOcbiBE_nQ?vq-cbeUG=V+S
z-{1eEiM$A46rrP|qY8v#wzwj|Jo&6v1Hr1QsyKZ3-t!xj&*K1}5%fzVK#^xhAMyQD
zV#UZM6bi9Jn}D@It|~yxf?t5)>({TZ$#fOCdiClmB%|`b>hW|UG79p5HHrwd=@8pK
z{`TM!K(&>&r(&T!v0yM57xG^MuQRt%fRiUrb{l$PnBSyJ0Qu(r)|DS0AMdgVFh>OB
z@6?E7Er5>Gr%!k4<h}e)IVKVb4w3H7n>TlBJuzSq!A3r*D&N@H$e2BhtrOv;ig4!4
znUL5-O~^ois14|ZkV;+`AllQ@!y)n$5CFn59KFVL$WnFq)~#Dbx&X4A{RIqq1VFw+
zhFuF#$JorF5>eyazI}V6ELVGhpG|NHKpPA8Ft+5#nIk|lndD4Qd;=8APzhoraCVML
zkm%&(Wb=|GOE`JV_Zlvf+0wIT&o<D8wjdu>zPYb}mB6>m!CaaET<Xe&{66|W2LTAi
z9%e3GfI`5pEOm>#Z&DQj>vdFFJ{EWasLNSjUtg5u4HM2HWr_4Nr})lUK7j<#XF!8X
z0NPl56Z&$l3g81)crQ#7Q%Ok)C$1e5Am1<oa;2xkv^7pRLR513<k?djC?G%*7WnCJ
z6F_47)A$F}4V@~$LOxK)>$CIc?0F&o7Vw(9H*JEx7TdKdc@JtXZ3OsaBo?JXf!A;o
zByNEtMxo@A{O*e)ER$iMPx6kPV4m3K(l?7^@e4tw*L)FTzH1+#+VcJ-7U0?I0k4t(
zG|taLfc#fU0G`EHawmwT(C-oeHtV<<!bxn^%On7AN=@YN+`03C>;Mk|No*p@Yy#ZB
ze?LWDYzOY$yZ4DDaj8K7K1;gbCgqM{%D<2e2RXk+o<0A&oa(|rH;G-lcI{nVfJ>Jy
zy&*y+#I}$3x(Lj{T&894{Q2`$e3uTcWzgl%9HwQ^Ck2B6Hc%mdNRE`-fMx=f9tOxW
zY=oBW-@kto3XUl|@!3NGA;Kz!`~Y*=HbRKeNPin#8=-W*jBVQpaa$S!I@w@+^R-e?
z*b6lA9f&mr0)dEYD_mY)-Y%7xkofij2k~qxV@r-ux~(wERju?j!L=2(`5irawAH#5
z7RR6<COyALNCZJXgp$=R+1`Eu%sC9Hm7NV6HtYi7l&{1{NX(d*M?DOwBDA))Zh|ju
zjBp8H@gs*IPNJ16d0l`81#Lhhf5Wk{y1KgER!LzHQ)Nd)NX3v?JJlSf<M5R$S3bl+
ziX$&V9}`>x*!+ak0nA^Y($*wEy$Q#T9oudrFAcYfFgiLKw#Aj4>V*3~?)!m+h_n^r
zH=H<eqJ_UbxCBsbk$(p|Ar(tvb^-fPxG6CSP-g>5R5d2@B7jkZv9Yll61Bxt1YjYg
z7{7l5dZe-SAiovIaE`p5wzjsNx^O0_9Z4Tnw)}qoZkd1TC3Y8urU<$K0Sj8F+SJt4
z`b>9%w51PyZE-y!7cX91F66sC!9czq)u@PCNfHt2TmsOBwrXXotgMU^b1Jsvh*N}{
zH*XfI0@S8KI~}l$ediK@HnbHVYfPmqzI0+@qFRKh1^GZ_Wo4VGl7wPQz$E}}OqH$D
z($WZ4w}9jioI7`}Mk-r5Syxgl0%Tp;QJ2q1B(fdkYlXbCl4O9hvLzza_V)H}Q~xoN
zbtT0jK-QHVy^>U1T)aEeN|FhBWy>@%GlyE)`VWy^tf?a8TR;E+002ovPDHLkV1msR
BI7I*e
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..894480761d0742015ffcfcc2d28bc10e88cbe4a9
GIT binary patch
literal 619
zc$@)i0+juUP)<h;3K|Lk000e1NJLTq001EX000~a1^@s6?*P^u0006qNkl<Zc-rlj
z-Ah_w9LIY(%OX$I#i(R0!Lb?Dx^NKDMO_RAyO8Q;C2T~^g#{f-ds`}!_A(fFw?Dv3
z{|hg@QP5j2L=Y8JP*D*t-1j%019GT!@fe4;gb)5+4(Iut=R7`-U9DD2b)F<1r$mQ8
z3JLCk)t3;;<?<?ht0f^M5{Y$O_XF{;8WOU=4LCvmqOI4HOeUuag~A7q$J75%5+v{m
z{cCVcpr&u@4`j31ebj$eDwT_1FgS)<cPAxefh%w%qmUT(dc7;TT+V@>t5hmon9XL9
zSE45ti_KQ6)pOK-flFX-M<Fo?W^_8;Mk<w}{&_eY{<C;_BnIpCx)1qxaCjR`Lepq8
z&M@E{Tc|Tut96ScA>%+U@<@y$c7TJsU=q&}pF!A*SPO>qdi@gho6Y7a@-ZHXNyO6M
zU=lAW&gb*{Y(T+iG|p13R;x+W=aR@|GP}t4?t)27LcnIRSk`5UKp^mu`jJS)hJ1qS
zb<mB|=`@MhZi7jTf(7svXeCJ+Ef$L>=<oP^zR$d`L(6Ww3bve1Cq4bQcI1T#M!*mj
z=R5qG+$0!}$G1gMT%<aWL@yH=2XDZ8x7%$+e_KYmS%pHOHL6FW(M^NFu)@}Z(6P;m
zP3yAD<@$<iHVNfEVKSNK?RNWyMx!w!e@$W?-?n8Dyc(K`FA9l1paauv1_pSy?R!Q1
ze*c={0P6<NKtB*3{3vH4uT(h76(a13|NFmp|CWU6{04~YFpk{n7DWI6002ovPDHLk
FV1jWc9RdIV
deleted file mode 100644
--- a/toolkit/themes/shared/media/muteButton.svg
+++ /dev/null
@@ -1,56 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="18px" height="18px" viewBox="0 0 18 18">
-  <style>
-    use:not(:target) {
-      display: none;
-    }
-    use {
-      fill: #ffffff;
-    }
-    use[id$="-hover"] {
-      fill: #48a0f7;
-    }
-    use[id$="-active"] {
-      fill: #2d89e6;
-    }
-    use[id$="-focus"] {
-      fill: #48a0f7;
-    }
-    use[id$="-disabled"] {
-      fill: #ffffff;
-    }
-  </style>
-  <symbol id="unmute-shape">
-    <path d="M3.52,5.367c-1.332,0-2.422,1.09-2.422,2.422v2.422c0,1.332,1.09,2.422,2.422,2.422h1.516l4.102,3.633
-    V1.735L5.035,5.367H3.52z M12.059,9c0-0.727-0.484-1.211-1.211-1.211v2.422C11.574,10.211,12.059,9.727,12.059,9z M14.48,9
-    c0-1.695-1.211-3.148-2.785-3.512l-0.363,1.09C12.422,6.82,13.27,7.789,13.27,9c0,1.211-0.848,2.18-1.938,2.422l0.484,1.09
-    C13.27,12.148,14.48,10.695,14.48,9z M12.543,3.188l-0.484,1.09C14.238,4.883,15.691,6.82,15.691,9c0,2.18-1.453,4.117-3.512,4.601
-    l0.484,1.09c2.422-0.605,4.238-2.906,4.238-5.691C16.902,6.215,15.086,3.914,12.543,3.188z"/>
-  </symbol>
-  <symbol id="mute-shape">
-    <path d="M3.52,5.367c-1.332,0-2.422,1.09-2.422,2.422v2.422c0,1.332,1.09,2.422,2.422,2.422h1.516l4.102,3.633
-      V1.735L5.035,5.367H3.52z"/>
-    <path fill-rule="evenodd" clip-rule="evenodd" d="M12.155,12.066l-1.138-1.138l4.872-4.872l1.138,1.138
-      L12.155,12.066z"/>
-    <path fill-rule="evenodd" clip-rule="evenodd" d="M10.998,7.204l1.138-1.138l4.872,4.872l-1.138,1.138L10.998,7.204
-		z"/>
-  </symbol>
-  <symbol id="noaudio-shape">
-	  <path d="M14.901,3.571l-4.412,3.422V1.919L6.286,5.46H4.869c-1.298,0-2.36,1.062-2.36,2.36v2.36
-		c0,1.062,0.708,1.888,1.652,2.242l-2.242,1.77l1.18,1.416L16.081,4.987L14.901,3.571z M10.489,16.081V11.36l-2.669,2.36
-		L10.489,16.081z"/>
-  </symbol>
-  <use id="unmute" xlink:href="#unmute-shape"/>
-  <use id="unmute-hover" xlink:href="#unmute-shape"/>
-  <use id="unmute-active" xlink:href="#unmute-shape"/>
-  <use id="unmute-focus" xlink:href="#unmute-shape"/>
-  <use id="unmute-disabled" xlink:href="#unmute-shape"/>
-
-  <use id="mute" xlink:href="#mute-shape"/>
-  <use id="mute-hover" xlink:href="#mute-shape"/>
-  <use id="mute-active" xlink:href="#mute-shape"/>
-  <use id="mute-focus" xlink:href="#mute-shape"/>
-  <use id="mute-disabled" xlink:href="#mute-shape"/>
-
-  <use id="noaudio" xlink:href="#noaudio-shape"/>
-</svg>
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..b2cd21c5ebc271dbe97d72207827cb48e0b0fa05
GIT binary patch
literal 1185
zc$@*D1YY}zP)<h;3K|Lk000e1NJLTq002S&001}$1^@s6N$oCA000DNNkl<Zc-rln
z-Ahwp9LLk?9Q0mh1CtgFN)WV*7^q}LRtQ-Z2&wtHayqxUt(=w3AgqjvP<p@f9}v9q
zN^it_@lx@^8*juHRPYu1{@^D(9A?j)+3~RFfe-WSoIU6G`Td^P?ZD>drUJyh03||+
zP$HBFB|?c%BKDt%D9c{oM~V3FBDN_?M2sTt#Jz}>m6f}w=QsXLidzvZ;TPz{;jy?B
zAxZ$Pc<W5uiCA7<F2-kng7+Xq;B8wJ_d5qt4Jbk`AzBeAi5nXm?VLrA!3o2PU<p6K
zJJ2E`6EQqIY{zRC_{K82S65dZ#t<QwAQ!>eFgZC{gTG&aR`3RVrTS3sO{0hqCA<aC
zA|VlB>Fw<;otT(-Dm16(;1kt5KR@r-_aY#HCQIKz2Y9+25)ns0ZgO(6+w1kdTw7Zc
zv#Aq(N7vZc*r|OZ0>^3K3HS`Y36O-~-;jtn2(rL^;3+IDd;!5?MtxjZSZKhx1l>g}
zE-qRT85SUsuyYY6&WdxO0MxnN?vRjCEud>~aL}r^h=ir3r3M^-0bzc)z)pxD;xlJg
znsBcqkO~|olc{!ebo7}ZvweJgyo8=bPZ1Wh+Yh3E-H4$2XjCAOWuGY9#1RCX1O>rh
z&?nRpoSK@VzQ(Mlh*Tch{IQ}Dahjt{b$+32qeyEq!<LtqS1#6pexi+<ke(tk=)wP?
z2%B&&NZH0&BHs5{dV2bGu?}4Kf+XrDf*;(s8?++Cb6B9!qD;HSNXf~`xh!4>5dm7f
z=`EsZH)utO=lc8mUE0+tiYXKd<%-v#k8tDtv$~2v`)tIqJ60lya1+zh(@ojg*%gsQ
z3=9lB5bMD3>C#<9UteE6jvHe|D}p9SJv}|mcDtSWk6YTNVYAsRb8~Yv&2HGDqobo%
z@1~JKQA6|^>49QFD*`+M0Z<AqYCB7;J8t5&4b&4DX6v)EvP$&sEK|WPiXKIAW@d(j
zxORee_ypIePL^;OByOFD@J#&Uo!lfI6Syzck+1jgY2gPh<tVm+cJSKo_XlZ)C__7;
z0;gE8MVLb*Vq~}i3GaCISx2CWIMGyUa9yU}6RJdx+C`4yLr?{rpcykjKSyp`qS&gt
z00Aw$#~B8-poS<eE^gxcrs+Dx=8^y`9K{S^V=*^?D-Z}YQ}nh&w&)rf8oD5C>QsZO
z_4V~?r_<@h`EtHj%6{FCNCH-H6}Zq$d=$w@NJON7^CKf8RXDCBW@l%si;9Z;oOKRx
zRPSZ@j%4_JJ}*U7i$sJOWR{hcRU!*2y1TnwR;x9{67sn}G3mWA6RV6W5!s$4NH?3!
z_prY3bBA0G94sNpFq^kp8Q603P>OF6#diK7a0!$M!|G9BGTe5)R))vpp*2DUArrx$
zJ<c6*8uuFs#@f!8%P1E`NScU=1Q_s}F1d_wILspA^V@Jy#_jm{5?C(79v?pokjt>}
zYpliiBE+IZC=q*J)Gu$<Pmq-eB|?c%BKCkk?$)5_&XOr_00000NkvXXu0mjfP7Nu<
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..3db8c973b6594cb8820661564eb8dacb673c09b9
GIT binary patch
literal 930
zc$@*E16}-yP)<h;3K|Lk000e1NJLTq001EX000~a1ONa4MF}34000ANNkl<ZILqCX
z?@v=_6vqz%v=&iHOG-DP0(OCJD#{=Q1&xu!IO0M`VQ8~WGmX(8lMX7gI4G@GdV5>i
zTie@T^vAvTINcVvw|ljB+x~;SAWP<p=kM^eh(D5BaWD2}=OoR|^Ynb4bH2|x55WK3
zeETwE#k-1xsLFDzcsDcV+xIWRuj{f-bpyYD)76cvb9T?W#Mkf^S-?m5D9+DZ>;I%-
zxZ&i$`I&1XUtW_1-U2l{0KBbo5;6O5d=h%03*Lhku;2~&0D8wKvkwvFq__30kO_T(
zLnR(GJHQG}po3bd|NZhmkHHLvV@ESFR8T2!7aOV*YGadF%81qh3fWybtM1P)7&3$d
zw~d7mmLxG9$5MQf(Asv%q@*za>3IUwR~G92_?#(B`8Cvgq_~EKbfn|VxpB-ZsY|9R
zIS3apC;FhBGS~vRSdkTfiP$Ej2<Fm)Z3x<+OY~t*xS*YfPFlds+%#!W_uIg;DBCFe
z&qBv%>v1KQ<_S<PuW4=?Gm?jN(y+#YfT^>6w7K{1b(SvsQ=R}ZC6ivO0CtrRI@^b-
zf&h(L2!kqO!rVqFT3E8|KN27kRirf6HTVKR<(k_tp^9M8LNv<}6hC~QZo<k$CO&!4
zJ{1nj2`SKX;w6AOr==A|H44p|i0mpxr+dnXzd}FUCqPJ!Oa4P6Kh40aPN;F(Fq-GI
z5ls;{hL=X64q7KBtm6VNN2QfRBc-o5*Ix^$T^hx3<Qwfm8r@C|C1**_hNJeFUyexM
z5ny&xU_rXfSNArHA-7XoPF=UX6u`9w`<KS-qROY1tV8o-n?c4g4i0XYv0%rwQlQ(e
zeW|t3;&vgI_vGi1lfLb6zyavyXPBS)w-M9(^9#tiT{L`ET3m1HNiJdl1JWV^%&>?4
zdTM!|t!yDK@6Fwyy*s8J&{rKZF!l}QmT)!gaeZ8AbCMQLi(gSbHQ~;}9IocPeM4ZZ
zI%Z_Mz;a|HaR+_4lE0F42&Q3Od;3X;cQk(mSJ0R6d^8M}mp!8W<j~m`!|_|Lq8FF9
zT=o_HvJaPw-diriaRTh#@!g_9H-gPPcy%gxGwV_BsrRy;;LWR3=0UL0PW?`RZB6tf
zWG5VkesGZY(^n_0=-;M+7Dh+yW1zllrr*ZOBlut0a}?V-%PVhp)&Kwi07*qoM6N<$
Ef)`c7YybcN
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..7de728b2d7a17a75cc0e5b44da308e7a9e8db013
GIT binary patch
literal 1756
zc$@*;1|#{2P)<h;3K|Lk000e1NJLTq002S&001}$1ONa4<K*VV000J~Nkl<ZSi|j@
zT~HHO6oAhzL?{><LB)tkDbrF~Ae9Qn$_Qa7h^P(1SWz&@U&s&@NI(z}sTv(o!T`a<
z(iz54Dvk{y*|$FRNBi7&`_i|*wm$TM>D-=WcazPZ%|hr*XE^6&=l*_s?>Xn*djPg%
zOSUAg!Xz>IOdZqBj5Bs-4%Lod-B^;(B>flDQ#es4<6s^}Q3uxMGt_1x6#1@2onEBa
zYX9Z{?DF--0^kSfWp>3G!CS&ii>G)xWg9k_4mT_7ll94ZW&Po1gUL4hbSemB+FKGw
zJMh(s{?Ijfz0yF{LKRfN5h#VjsHON-0aa9OrD5{A&n0SI7Z>|rDDSzzpe|d{8K{Ob
zD29B<fh@>`ov4|RwQvqgim|4;=#0x2=;3XS1I9|dFx-mMXhwiiC;$~?z;;N2M4*8}
zrGKyb<0dGuRE4#rP;E4Oo&J9H8$@txg`u9$mY)M1XkZ_tfeeEF?ym}Ros1#`g*9o|
zLep*#Z;D&H0ffa&A8(G|&U|tj_x?TD5egt6kRhC$6$F{qi4o8;W)?Ho%RqT7+#sF@
zm1p4~E_Es{KZGHSkr6UT1|gd(@su!5!H7Nlm&XF@vy7!;;ZM3uh_DZm!v_i=2oPd~
zrmoIzVT`5Xbs!Ydo^jqIZsA6#A|mL>H8M=Du=<OIg%Bg0?|@3Eblu|DV!V)+46(3Z
z80^sJXbY)tM)-Ls!vN|Kgi^?ZeC<iWJ{F3kGSJV=T-T{l^aw=+ThO5~UL^ypz8qBa
zLCx*z5QH3%Lpo@tM!C{wW{|cP2DxvJ>#DCqYmkK@l%pjKk$zTRUO@!CrQY*Z2m))y
zGT3*LkGH-#gItndIC!I6veSj=`TSOpbkabqxCN{Z;uq?Rfj1zq4x2_7F4?&{N3j$i
zp%<FCZuhNdlKeXSx$|!UAXWrcWT3il<*lMg%7(}m`?+pCjTnkKdg}ETYa3uC7C~S1
z|0@E!7U?~WT>WBy_{K(;l;?N2ZuR9jAScPIRxv<~2&|+w==jio2U22(kbC%Wy+0p>
zTjNed=nH7f2mnc%kN8+I4H8UK;p3fcw;E4MPE`2!Z$M~{h5(SbTg|s}qO->==>mju
zuYb^N(j(|k76}Mw=E}W(i1gSYGL~n!Zl9_BPL)kAa{6O$T5mW)ZeA1wG|dWrC6;H<
z%wvamI>B}8(*z)1cM~%)|IiZ&;r+bdTBEuj)u-WarV~;i(&tC`I8hbY4qq4P{{C`g
zgkRfMEfDSDL))vk*7GA$wnH&t;=@a4z%V~<UWta#y4pv~5bcVexX{V9pD;-=Ou6v{
ze=)n8mMpj^-mg2NAoP-MVghyK!P1i5cex(M6H;6>C97bC_YZr45UlV(KWIG_jPP#W
ztCrOsVj@Oj6mC|bVlNOb%2@?cf|U%^j$!@?>*h_9hPP&Q5fCnsF4D<r6bR}Wf4g!F
z<621w+cfMt-ylr)Kox#>WD)k{zB<2Z#_8KRjSTTXC0uF@4QMqI4loMjbirfZP2K(M
zT7)8CXv+AmhIEiNK_fy?ZvF&)Jb{-2xwPx<Hc+=V`7fzu5fHYcsa6ab$pt|pK`fOC
zW3)BlW^9vqy~7tq(Ziek#EvioHaflypMtUHGHKy79KxOB<1-l#Z$c4{DEX?J1lb2_
zJ##^inBX%a5%%Dl%yjt@F|Zm6@m%Sf<WJAJ;##a-M;3?1z@oX(78L;k7?&=RX3`uC
z;d#e*U+CG|9{I8yo1-d0J7x_$h%K#QCuIPmNetmD3#63Btf0k_WUwxwFtp^*M{Gl)
zr>*rHWoS_5Fvk24Or|)ebLT2mhUh7<?gRmiPL)gPMyw*sa55cCPEgK)!>C~&#8}hL
zI0LOmtdtHuz)@(}fF$5v=0SOjaXH9D85?t!DPdGhDwDt@e5o)U7&!H)gRzO*EYG!c
zA>4;JLc&I~BrHZQ9MPP1*`lY(yz`!~z4PJ{mrZjTlSsMoKoB-12aT(`vGdWrSTc8y
z?lpE|PDi`;5TqeaLZe|R(ap-JWBS&q@fByZ=~tXn<N8*r26I;$?2!^b1U~<Q3!9B`
z4^v|by}oT^VD`q7Nw>r6^19rPC-&JJqXYUjg?=rqR)j4T;W?f7tVa@tUNxr14&g+V
za1@TgaX5i`9KViYNg37@V2d5tl7>wa8V?~k9?5ESJPjPceLsY%#V-w(sIf+lEjAG#
yur=(HKLw{#;KelqH66d?SRz|XDQ?OCS^fckY0t>?7H#MN0000<MNUMnLSTYomOA$U
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..944098ca19a4f63331ae852606c3907285e7e203
GIT binary patch
literal 269
zc%17D@N?(olHy`uVBq!ia0vp^G9b*s1|*Ak?@s|zS3F%DLn>~)oo2{&C_sc|ZBbJ^
zd;X+m78e1QjRMM9x8@wKev<O?arLI7VbMD#Iq~xR`O`R8FU9oy=S6>-<7NIF_#C!j
z*0PoT-`yuY-^0D6yh-((^Mz)`_e?M6CdfXwo?PDe#jim2xipB8_u*7RK!trpqJhR9
z`8N_gT<_V>^RTskZ&qh(KJ@#ba<k*ZzYiJ@F8EMaa2}*^M>0s^9U}>md;EDI<*cs@
zWo}p0PfV|wvlM7kMw6Jyj>-2p!z5NX9-RBd?Ly@={(mp>9|>1!@A!0CZPs?6{}?=7
L{an^LB{Ts5-H&uP
deleted file mode 100644
--- a/toolkit/themes/shared/media/pauseButton.svg
+++ /dev/null
@@ -1,36 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="18px" height="18px" viewBox="0 0 18 18">
-  <style>
-    use:not(:target) {
-      display: none;
-    }
-    use {
-      fill: #ffffff;
-    }
-    use[id$="-hover"] {
-      fill: #48a0f7;
-    }
-    use[id$="-active"] {
-      fill: #2d89e6;
-    }
-    use[id$="-focus"] {
-      fill: #48a0f7;
-    }
-    use[id$="-disabled"] {
-      fill: #ffffff;
-    }
-  </style>
-
-
-  <symbol id="pause-shape">
-    <path fill-rule="evenodd" clip-rule="evenodd" d="M6.002,1.953C5.172,1.953,4.5,2.626,4.5,3.455v11.08
-        c0,0.83,0.672,1.502,1.502,1.502c0.829,0,1.502-0.672,1.502-1.502V3.455C7.504,2.626,6.831,1.953,6.002,1.953z M12,1.953
-        c-0.828,0-1.5,0.672-1.5,1.5v11.094c0,0.828,0.672,1.5,1.5,1.5s1.5-0.672,1.5-1.5V3.453C13.5,2.625,12.828,1.953,12,1.953z"/>
-  </symbol>
-
-  <use id="pause" xlink:href="#pause-shape"/>
-  <use id="pause-hover" xlink:href="#pause-shape"/>
-  <use id="pause-active" xlink:href="#pause-shape"/>
-  <use id="pause-focus" xlink:href="#pause-shape"/>
-  <use id="pause-disalbed" xlink:href="#pause-shape"/>
-</svg>
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..df22919419082d251064811ac730eea234008ad6
GIT binary patch
literal 434
zc$@*U0ZsmiP)<h;3K|Lk000e1NJLTq001}u001}$1^@s6sD?Wp0004bNkl<ZXx{Cb
z!D@p*5Qg0q3OR(F+oO=4d@0|@H^`HCYj5o%wAgA+9(qh5P@>zJW(vhdH`ESW<RAEm
zI8O9)Tobdg&besL*l6YfK?p(+f)Iot1R?k{j4_`~jj#8)ln@<EiJaK<$R#%#^nEcU
za$?hi*QKE^(YWinj9yn~ax2c!S&v7$=dI^`gcMv@Yxw|b;-yC|xrJiAy5N#{Bib{$
zR&q<ldUe4o;>bg3fTL`qRj)2+CT?T?XdkL~QRhLs9v}4RAOtZ6F$U2=bPyf<eRLkQ
z>(vEY58Cw@gAjz^%mrtE7exorL39uugdi@_p=g?B@a#)YwO(7$Wm#scs*3vuSC*ya
zoaZu|TCXnnUKGVXNs?=t3R@Gm!kXfSbG(gWy}IBoI!$#w6IFDY2CHTHNpd^IdUe4A
z@k%@p_r#sR%a4*fj7&#gR3B21pSbxlYKZN(4s2!J-t$yGwH`k@L2&T?9_Syu=pY0k
c2*H09A5LBk_5_wn8UO$Q07*qoM6N<$f{=f{<^TWy
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..11e2731df64f9dd00623f263150d8a651ee1b1bc
GIT binary patch
literal 448
zc$@*i0YCnUP)<h;3K|Lk000e1NJLTq000~S000~a1^@s6at+^<0004pNkl<Zc-rmO
z%}c^y90%}Tuu)B96&6G|iY^{HL_!1uFF~iEF2RO1$OILN-W0@v9zuj(=qUSF93FQO
z{{#^Pck!@`2peMGK?e_6>Yj}b4nFWa&z^@bJkR#qX8QfUtEPeO1QNdfZy;rwX0hFF
zM@prV5B*uE1N~@cp<o!sTfJUC#@M`*fdRDB-!kyp>2&h7S}llsb4~=ZXs2LM7Cy1f
ziAtriVQn+%z~>?Iy<YF5*=(NYa=9fdm{j27FP`9~+wB%`zMOTwBmy5skb<JF>*;E>
zx?`QMoxuAsWZ=EkYVla>nKbZjT#BMZu+}?iU~*LDa``qC3W->EU?(vC7d$XYp6BD3
ze+qlBW@k%d!=MPnBuPrpG<|`&hp-8Yb|0GSpUAQtXIb_NbHcC<UQ(}xI7n61D93S8
z+&h6Ftbm8)i+^d+G))u);Ra)8un+4%kuGh4Mx!C1bVV74;n6>WEm(G{c>95aFzkZQ
q>CY1dtH8j5jSukjpT_w>SA7AyaD`eO0!@Gb0000<MNUMnLSTZ}pUTbv
deleted file mode 100644
--- a/toolkit/themes/shared/media/playButton.svg
+++ /dev/null
@@ -1,37 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="18px" height="18px" viewBox="0 0 18 18">
-  <style>
-    use:not(:target) {
-      display: none;
-    }
-    use {
-      fill: #ffffff;
-    }
-    use[id$="-hover"] {
-      fill: #48a0f7;
-    }
-    use[id$="-active"] {
-      fill: #2d89e6;
-    }
-    use[id$="-focus"] {
-      fill: #48a0f7;
-    }
-    use[id$="-disabled"] {
-      fill: #ffffff;
-    }
-    use[id$="-clicktoplay"] {
-      fill: #000000;
-    }
-  </style>
-
-  <symbol id="play-shape">
-    <path d="M3.243,15.155c0,0.845,0.593,1.157,1.317,0.707l9.659-6.041c0.727-0.453,0.722-1.193,0-1.645L4.556,2.137
-    C3.827,1.682,3.237,2.014,3.237,2.844v12.312H3.243z"/>
-  </symbol>
-
-  <use id="play" xlink:href="#play-shape"/>
-  <use id="play-hover" xlink:href="#play-shape"/>
-  <use id="play-active" xlink:href="#play-shape"/>
-  <use id="play-focus" xlink:href="#play-shape"/>
-  <use id="play-clicktoplay" xlink:href="#play-shape"/>
-</svg>
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..fb20075b24af20c17d2ab0f301e04b74c0fbdb50
GIT binary patch
literal 831
zc$@)01Hk-=P)<h;3K|Lk000e1NJLTq001}u001}$1^@s6sD?Wp00099Nkl<Zc-rmS
z+e=e%0KoA!*Ot{<UTDg2NDzaFq8Smw$|xj>ZbpOBRGj8*$IIsCv{h=5RO=$!@)G_9
zJ_)}2=97Pb55D;*zUYg1!M-O33mKvAdJew>AAUa{^!UZ!&VD<`6Z`x7swM(Opa>L!
zB2Wa1KoJ;s;7IxxIOZV&lMZC=#dlOetF}Nr^J)B+?d|Q2Fxu1<Sj>C`ZxO;2rU~t2
zELKCHmH8k7G4C;sX+-f91|<iUGapD`6j4m^*Zi`*y?v9pMyY}Rgb2kLCNN28fU#UX
zfpJ6lhDl89?(Q}+nv@jiJEV6Q$0Wvgc6O>6bxH{AKLQ^{5y1q@_9Np}^#sQGF@|5U
zP>HcLR|CCC2;gfhG{Woi1!I1$1$t5-h#!dJGq2A(j2iU>0$z+Dj3~=?knvJ31oov^
zKRzLXD9g5mu~0pMaRG!7#ZNqfJ{y6(X%&BcMp(9f&Z)_Cpp*gK_^`gd?&X|@Ob5Et
zZF6%|3I>B+CX?wt=Pb%}U{|`ZB;7MJGaie@GQ_z$aW@-*o$0W+xY$!sQ8CClym*b<
zD9gqY?MS87)m69C>GW&0TKR&~f(N*aLY&OTMW!tkwzjs~hlhtfMx${cwj7_~I?OOY
zldbo`H_4ivot3OsYk;5EgO{j88BRl+?VU`^aV;$^bvPUjc`5dz3HNXbCgkPHUet9|
zYinz*93GucC&#tnA+DepdT4U#(?s)Ov9D|ng+fw6L4mv+-FS{0D8;G7Vc8FCI*hrw
zxpte)Ho*7vp$-m|<1F%W`4fHP|12*ryJ~7`<o7ZkT&RW(=b?yuG7X7rY-}`1lGLr&
z>*eLxfycOp3(!NOl)Gy62Zh7ocC*<mhjqh=Td*J>T1DL#<-$?N*MBW6EV%4;yDzrA
zYCsh(!iYRY-r1g?pRZq8S!t-Pt?gxdC0|5Z6K$^)`|t&?@bC7@juIH4QT*dGIPe6O
zu;L7~s(Ap4B9!19bV%aJslddC2o!-wI>bK$i9iu30!3g(`~j6mQ6C+}d$#}p002ov
JPDHLkV1f(jg=_!-
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..f159627631c536f0def829f45f3715f198db1a5e
GIT binary patch
literal 562
zc$@(;0?qx2P)<h;3K|Lk000e1NJLTq001EX000~a1^@s6?*P^u0005`Nkl<Zc-rlk
zJxe1|6o#+Sh#MmkWI<RVjX%IDorNIz0T%fK5!ogKZVD?QA0%W#Cf_6>O~68ljj(Lv
zk5MaO3$bt}*1j(sG6WevP!0$lcye>kJ-N?e?ky(fI|3r4$85}lJz#-DkX3*li(c`Y
zOfs45_j<kS@p$~G1%33=56sbMG`brM241JrQG-5u=?A7T91bV#cH7g2UiyKt`~Ci;
z)oOX#&`UosHJs0+*=%~+&`ZDJN4MMc>h-#-4ZYJQcu^e3akYWhZ-SSkR;#(%!0R``
z^Ql&=t~T)cO*9$}&$ew>8+iRDa7nyMrQ&J>uipg1E0@czHt^0iQ7V;OWoDYNbGh6d
zk`KjVQ4RX&r5~7lB9XW(6bkpRT_m0(e~j8dxX!xQ_M(qo`hkf92b_Ql@Hc>e;4+m;
zT~U<J=bynm*ICE<7xuakpCf*=B44(^HrNSZ7aV}IbUJ;5N6N=Jg>&Y)E_J&v?6obv
zxcJQi_yJbI8u%H&I@kpJ;c)mglgZpdJZ*q;=D99)>w$aGLm$2L<Hh1lAm+dl*Z_Z`
z(dc<LoBhvQ&XIHGWqpbDZ`{|&<Xw$K<S`z{VzG0}vTitXF8PSxz-KohAVOeSgug*u
z#<=7|@7V9de+?pXzQ1IQNM1E4TmXwQV*Z8W36?vi;x!bAB>(^b07*qoM6N<$f|;uc
A!vFvP
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..f8790f46724c449f053f490ff840f279da03964b
GIT binary patch
literal 1354
zc$@)B1-1H#P)<h;3K|Lk000e1NJLTq002S&001}$1^@s6N$oCA000FMNkl<ZXx{Cb
zO;1}#6o&onbd@Y2U9`LI;7{}ibPtNeqEef#5vZumA7GC_d=wI5T*Zh53qzZxP=!{c
zV2nbgkWwg>t(Z9R_Xqa%y*aOSCOUC&WE(J*?;YupF`k(_?|aXg8IP~SFbtc8VRP85
zQZ1Gd$_TsNZnLmk5g}8<F2H*y;S#tz1gXhctKA_CL4{ky*UW9=n-1f)(07Y9J8U8X
zJ|?~*ZV+DL8u3wwa*Z|KV9n6(RFUun;pyq=xj8yI+CM)(|E=Heze9XaeAgjB%N=Ng
zMreg**6xB4{m7x--rk#ogM(jocXxkA8w_u`T()&0&<2gr3e7x!^uvhj2$jCRzR%%M
zCX+Fe$)ui0BsvmkgGOj&%}A5$DmA=aU0t7~QYnL6GqC0C)B<hL2(6^~Q#PWS8VC&!
zedyM8-8A1Vpp`Vc*a){;HQbt}nQjxsnq6wus2X9WXpm9C8BsN&YKB?Aeyd%k+-91!
zytBo&nK&YB$_P6fVaj41%+x!fGI?rP5n)9{y@;@ku#B+g2y2e8Qo~9OD>batuu`M-
z)G*8%74_x_Gk*;?R7BtyUo%@o(BW-G>4y<G!K_51(G!QmJW~d=Mk0|Iw8H}^&l2V3
z<>fHBRKY_NogN9Su>#G|4i8|&B98cvj*j9J6BBFXQrziu>RzwceqKBtkDdCeUby9x
zRcebq(APzb3EH3$TA>-*;Q@>&5-UXE`1m+BHa4~~GBWb>(9qB$;y2<kvC$-d5Ko4O
zhqtN35r!>4?M7`wp->!sp-=9++3`GPEsvlL8le@MS$h#ioD%;M_Xs$YCQ?kY1yX|a
z;^N}-gM)(v?rO6IZO}Fl2t2PD*Lla5X07*F`>8S_%M})gIpQu?x=;A{wGn*W$B#q+
z7pJ?Lo|~I{8jHm;%|r(3q7B-j4;B*Oz86{;*L~J>mo+Z1=BzTJ#OaYC6719o@q&mF
z5q@oihyd^XxEL){sp;wI9r`&w-^j{@I`k8MZgO%mgtk0jf1PVII<6>dI$@0o)(q_>
z2TvA=ioA#nRC>h?UUK6T{<{%SH^$&@WOBJ&VtjmjyHF^UK4b<yL!GIqsSv#;IgEXx
zzh=jw>c?4ALPSEIwQCMuM>UQNOddIQDs={p<Y9t&%@=;jVVR|85?;^F&TdzzoVAj`
z1o}ur9n|G<__&W(+^6cl+4)M5VT}dW4DA(lYjplcnH?$$Q(7S_%uKR~2lzj2+~Pi;
zFHE9!X$G(DI?V|?sKb3c;I>I2B72T;6<FITYt>l$+b>-TT||f`%&E)F%*;E~n3)%b
zAgqIUzrVj9U0Pb&qgBCBPrkZbE`wHw-NVDf7u+VuVXX|vOA)o#Z2(PBA#}o!TkH!h
z+_{RfvY3C6>xaZIxT{-RTSu#_t9x#@+YVM%R`zyxcaK^0PsBgmCMWKoUUQBA_e1Hz
zX=O%1OvKNKUm<dRef`<y=H_4Y8phvj!W!|nn9z#C1miMHxYUCgVTMYzqA=qr@dRd2
ziu@T22E%;!*Z8v}M}jh;a+xMvh!Fz=19cH|PlW|ZGd76dc{2Qucu4G=5eaX<Du3u&
zt<uh;Iyni~rU{Jrfp?2xF)_YpLfcNU+hj)VekEPA|5uSv5=&cK9{OzONsNq)60Zb>
z8cIy1ohDq>DYi_LvJhVu>CjdauEGeT&IV43H`;B&RsXJG)Zt3X8zB&mj=E<~Gynhq
M07*qoM6N<$f-jwbcmMzZ
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..96d2ed75140584a92940e65b4f5d1f7a60a133c3
GIT binary patch
literal 563
zc$@(<0?hr1P)<h;3K|Lk000e1NJLTq001oj000~a1^@s6^*lC`0005{Nkl<Zc-rlj
z%}N4c6ox0uC^JGN2nyVE0j=D%2*L|!;SCtkMxk7^3j9HF#PJ^$H$scTHbJ!MVyacp
zB3d+K>)tm`4N@(fg3h7?56AC(=bP_=IRhI1@kim)%XmzK9gqSCAgz!C@!Jt!BN>au
zx}8qvb~qfqXoY_Cq%Wn927|$4uh(;0t(IEoM^E}vI@j;_N6lu_(GET7OKG#)?T#9a
zhNB&N(wEW|%*&`=uRGeICw<?f+wHbftyXRA(DOr@gKk-ttsQu}(j4+irDAIbo~|_K
zrCcuC+JUDlU8~g`(==`Ez|)n+kUOPP$<_`$U1@|<EEa9;z;j%>P$<~S8Iv|Mnam@K
z&-r{_E%c)&eJP!dMx)ocT<*#12f}&dL-CAn;XeDk-a$Wl(wEW^V1W~G0WK%x3S7tI
z@f(U|v)NCu&VBZ=-@_dj;%AAku_!+_z$Vz5kZrIB&Ju~l9bP40;|E-`&VA|I_Hf6h
z_(jCmm;v)(353D&gsgydu<Q5xPm{^y{ku3b*Q|42`c^#L5f(pq!WVz6e*|I*%z-s<
z7z_r_)9LgBzjkJ>S(p7e_K%(S5Ip!>;sJSm$DvT@Je5k_F>@{TfGey(njm~&K?L_f
zRdPh?zOT+{2#N<}4p$`yq^>$BI0I%S`;7lEj92mUjv&D^yS)Ga002ovPDHLkV1jJ=
B4P5{L
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..52c9d72727e8d6c263c288454003b06cb2e819b9
GIT binary patch
literal 1396
zc$@)r1&jKLP)<h;3K|Lk000e1NJLTq003G5001}$1^@s6eU$H0000F$Nkl<Zc-rlo
zOHUhD6vzE`x=NOiF4|pp@Fn^Ix(7vKQK?PW2vpSO3$RBZ9)*M$S21G2!qBuSRG}3q
z7^6@rq!dbJD<)3-et_rE^LNjsHx8s=Ji}1kBmHC>&%M6)H)qb=85@sjnl6R)cw8!M
z2_@Pt(QdcfrLZ2A(KeP2w*+2$37>>taVBJE-bS|`NjNsRMSRZOCcaRdi`$aFTkO>1
zk}~*x;xpm~5hSh=?<tz%8auqfPT|%oGWioC(9zLxb8v95dwP2M%Wyb+hxnTKN^vIO
z>JHq&AzZ>KyY)eIH)>30XXnk{-ri5!+uJ{)1$MAjtGN{C2kzhyF5#5xcQ-^|N2+&q
zb$yIIP$(44Y&L6TG8sh^z#SaIB|AkKxh_gau&u4_gIq3W(q1uf$*7{afIB#ZOLF=l
zi>{Xrq;`Pb^c#ku?n|@?xFn}O7VQ_S4!@>pDji!K?9?Y#9d*$vo2|)et{8REb=gXc
zHHfQ3`7%+3HSxwJxXM23GTJ3XyIHgf3qqJyw@GaZRXXe`9V(+$M*m+kT1io&RgG4m
zYP2dHs&uGOr9+htg(@9REFGrGYHPE(v2>`gAcS6#(fFBxrn0cL(3i8i@C(uS22oEY
zlLsD;D%mZo$>cJTNTlEvj$yV))aK{s<Fpra{AgNb<HcZyI-J5S97FUhq3!MMrAJ0a
zmS``ey<V>o3<lkH69@#{^x5@+HXCS*KG4@?%mMD;5H8^qZs8cBtHc6P+27w!4Gj&g
z3=9lB?Ca}$MEpcNCRQxw7vf2OfB!l~8i!r8*@U*SSS*dc&?on8_4psNt4DALhj0m}
z?6wNghs2-6Jpy|mPvn@a4df*9v$M0$cXoC%$jb8u+MsPD5_#S*54-1*XP5Wb?V%7|
z<PBzsDdH|~be{<EqZNesGruJw7%XLFerjs!X)2W}oF}ufE!v<h`rwI2xbGPo=5e2$
z-DQU}?6fFEA94985E<SR2gC~^NhJ8u3K9}{9me2jS(F<eAK###zn0Ik62dn0liAYf
z=x7XWd4l0nKEtYcB-z;kJIt_CxIOZ4u|`&xrOd`gueiZWZhXMctpI(e7-UDGR4QeL
zhlkfImCDh(WaB+-Gd4CBqsJ^CwjrrMtH&++PqVX(l*wgwt9f{xr*USZc$auj<W9hf
zx|U&H^FUwnVOXT!7{8vJoLtu_PFjgTGQFi?8*Izt4sjo^xKGi))#n#MfgM)ZDctHJ
zRSf<^jrTxRl5Ph@Y3F8H(gXaRE~L_-P$*7P4Oup?RSl}i8`y^Xc))G5(xi(v&ZENa
z4%wx~ZjWy&2@EO2HA()dOiWB%h=!e8mW1Q5kK*<A_I7e^Zf=WK6{h%4RG-gh(&}P!
zcX#&%w~6v$ECiS3NndoF|1thrgEO679=pBtYi=5>DIHZc>3o4&yG#6ltXx}L+gn^*
z-17VVZm_Vhu(i3lxzAF+BmUqvB`KqfhR?XPaKz0G7GX-VE7FPi8Sx_|E-x=XTU}lK
zjUMB8&XSji-=z~!Rg!EvL9$~+H^>&Ht18KUN<4vVDj~l{qtQ5L?-IY4<xCcmbtg$~
ziRhl5o|YliG@XUXvR8<o`DFJO@jbC|LM9*Inr!9R-ZAE@mC;hjC*{U60@2^N{<+$V
zyZ$}#y(QUclXB_}Xd%0CeJ|g?$V-_l)~kjSB|BMkV`f9-Aq$r|Vss}<cDiU0av7;f
za%)n#aJ1yBAlh`Dd_ncr1%cDE<tlwiXr98Ah`#}5iLUnmTcrm80000<MNUMnLSTZf
CC8NOr
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..5b76e2fa45d8481ca0a81e524c4a20508adfc284
GIT binary patch
literal 324
zc$@)50lWT*P)<h;3K|Lk000e1NJLTq001EX000~a1^@s6?*P^u0003CNkl<Zc-rmO
zKZ}B30LSs;&f%bj#)6=RgQj{74ZQ(d3Wqql3aTOc52a4s)lF`_FlSeB7sSzi4-^QG
z1sBK9Md6FjqtEbBL4Ap$DD^T#hWHcW$&HRseBW2aJ}rdeI8GPqelafa5HjF|wwRaM
z2m$Ee{1I(LI94SfB)|_^-(nzMZQHH~L9oZMGx|o$cnm}?48sHFJG4lOfhb|TLi2ku
z5EYDPkD?$v&zoRAy%*(iXqwh_T~|QHNih(4)Icig>$)zkeiV;^c)LPMsD@gmX%2Dz
z>lXcGg^H+Y7{&l=K1D=?48fxjccMo|$Pml2+WZfg4Ef-H%4Ntq@u%kTmLdKNk$M-z
WIy6#<EqF%&0000<MNUMnLSTa1(TaZn
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..86f21859eee91db51bab2e89ce0b05f2378f2dd3
GIT binary patch
literal 542
zc$@(q0^$9MP)<h;3K|Lk000e1NJLTq002S&001}$1^@s6N$oCA0005yNkl<Zc-rmS
zJ8QyF7{>8hGGr+@NO7p(;Ly#l(4k-#+pSP4we(`uHi=2>WoXkby$+>QubUsi&m}G@
zC?fU=M35de7%9kk-@qSo!a0HbKp}b-`u#qK$OAA0LoftGFa$#|1Vb>yyg>ZZK@$S^
zNt1`@bUItO&ks%&S`Z?_H+se}ObkLqKv%f5LJp$cZf|1k7kWaMZnzvL1R)~Ofe;Zs
z(IdJTjtGQ^Knp@dctGc)k{$vGY0UdT_ozHBsUR?3Mmh9~-UoRI_N1hNXf~VCUa#i?
zhzL|5LakP-fbko0P#Ia%BnyPv?RH-T0D=$^oZlcbXtF@WaBedM9s=jaEXf3MHcQe#
zG#ZT}#-~A(2BKQ6o?u)InlxXQ$z(E9tJU0xDg;RuhzLq05(%?Xsg&yVx(kw@CRrd<
zw2HQog|5*px-(7F#=M+gvOp}NB@ZKoc2E`_p^|OeCgvVbN~X8Z5K>VD#ZcUXSx0%x
zvPzhLI4;?Lk5Et)t)V<VCI;3Vj7o9{5yLPH9qac0CNG3PMs_$N5F&=I>l)VY4I%^~
zVrZJ?zGr0IXh8U5>=J|!F&xJs3L#=_(D)PBA0vUn)OXA%NJR>D2;M`*5dH`6v*Zn@
g48af#!4PxYFHV{r5hiD{MgRZ+07*qoM6N<$f^IC@J^%m!
--- a/toolkit/themes/shared/media/videocontrols.css
+++ b/toolkit/themes/shared/media/videocontrols.css
@@ -1,479 +1,440 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
-@namespace xul url("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul");
-@namespace url("http://www.w3.org/1999/xhtml");
-
-
-video > xul|videocontrols,
-audio > xul|videocontrols {
-  writing-mode: horizontal-tb;
-  width: 100%;
-  height: 100%;
-  display: inline-block;
-}
-
-.controlsContainer [hidden="true"],
-.controlBar[hidden] {
-  display: none;
-}
-
-.controlBar[size="hidden"] {
-  display: none;
-}
-
-.controlsContainer,
-.progressContainer {
-  position: relative;
-  height: 100%;
-}
-
-.stackItem {
-  position: absolute;
-  left: 0;
-  bottom: 0;
-  width: 100%;
-  height: 100%;
-}
-
-.statusOverlay {
-  display: flex;
-  flex-direction: column;
-  justify-content: center;
-  align-items: center;
-  background-color: rgb(80,80,80);
-}
-
-.controlsOverlay {
-  display: flex;
-  flex-direction: column;
-  justify-content: center;
-  position: relative;
-}
-
-.controlsSpacerStack {
-  display: flex;
-  flex-direction: column;
-  flex-grow: 1;
-  justify-content: center;
-  align-items: center;
-}
-
-.controlsSpacer {
-  background-color: rgba(255,255,255,.4);
-}
+@namespace url("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul");
+@namespace html url("http://www.w3.org/1999/xhtml");
 
 .controlBar {
-  position: relative;
-  display: flex;
-  justify-content: center;
-  align-items: center;
-  overflow: hidden;
-  height: 40px;
-  padding: 0 9px;
-  background-color: rgba(26,26,26,.8);
+  height: 28px;
+  background-color: rgba(35,31,32,.74);
 }
 
 .playButton,
 .muteButton,
 .closedCaptionButton,
 .fullscreenButton {
-  height: 100%;
-  min-height: 30px;
-  min-width: 30px;
-  padding: 6px;
-  border: 0;
-  margin: 0;
   background-color: transparent;
   background-repeat: no-repeat;
   background-position: center;
-  background-origin: content-box;
-  background-clip: content-box;
+  -moz-appearance: none;   /* Remove the native button appearance and styling */
+  margin: 0;
+  padding: 0;
+  min-height: 28px;
+  min-width: 28px;
+  border: none;
+  opacity: 0.7;
+}
+
+.playButton:hover,
+.muteButton:hover,
+.closedCaptionButton:hover,
+.fullscreenButton:hover {
+  opacity: 1;
+}
+
+.playButton:hover:active,
+.muteButton:hover:active,
+.closedCaptionButton:hover:active,
+.fullscreenButton:hover:active {
+  opacity: 0.4;
 }
 
 .playButton {
-  background-image: url(chrome://global/skin/media/pauseButton.svg#pause);
-}
-.playButton:hover {
-  background-image: url(chrome://global/skin/media/pauseButton.svg#pause-hover);
-}
-.playButton:hover:active {
-  background-image: url(chrome://global/skin/media/pauseButton.svg#pause-active);
+  background-image: url(chrome://global/skin/media/pauseButton.png);
+  margin-right: -22px; /* 1/2 of scrubber thumb width, for overhang. */
+  position: relative; /* Trick to work around negative margin interfering with clicking on the button. */
 }
+
 .playButton[paused] {
-  background-image: url(chrome://global/skin/media/playButton.svg#play);
-}
-.playButton[paused]:hover {
-  background-image: url(chrome://global/skin/media/playButton.svg#play-hover);
-}
-.playButton[paused]:hover:active {
-  background-image: url(chrome://global/skin/media/playButton.svg#play-active);
+  background-image: url(chrome://global/skin/media/playButton.png);
 }
 
 .muteButton {
-  background-image: url(chrome://global/skin/media/muteButton.svg#unmute);
-}
-.muteButton:hover {
-  background-image: url(chrome://global/skin/media/muteButton.svg#unmute-hover);
-}
-.muteButton:hover:active {
-  background-image: url(chrome://global/skin/media/muteButton.svg#unmute-active);
+  background-image: url(chrome://global/skin/media/muteButton.png);
+  min-width: 33px;
 }
 .muteButton[muted] {
-  background-image: url(chrome://global/skin/media/muteButton.svg#mute);
-}
-.muteButton[muted]:hover {
-  background-image: url(chrome://global/skin/media/muteButton.svg#mute-hover);
+  background-image: url(chrome://global/skin/media/unmuteButton.png);
 }
-.muteButton[muted]:hover:active {
-  background-image: url(chrome://global/skin/media/muteButton.svg#mute-active);
+
+.muteButton[noAudio] {
+  background-image: url(chrome://global/skin/media/noAudio.png);
 }
-.muteButton[noAudio],
-.muteButton[noAudio]:hover,
-.muteButton[noAudio]:hover:active {
-  background-image: url(chrome://global/skin/media/muteButton.svg#noaudio);
-}
+
 .muteButton[noAudio] + .volumeStack {
   display: none;
 }
 
 .closedCaptionButton {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc-off);
-}
-.closedCaptionButton:hover {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc-off-hover);
-}
-.closedCaptionButton:hover:active {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc-off-active);
+  background-image: url(chrome://global/skin/media/closeCaptionButton.png);
+  background-position: 4px;
 }
+
 .closedCaptionButton[enabled] {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc);
+  opacity: 1;
 }
-.closedCaptionButton[enabled]:hover {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc-hover);
-}
-.closedCaptionButton[enabled]:hover:active {
-  background-image: url(chrome://global/skin/media/closedCaptionButton.svg#cc-active);
+
+.closedCaptionButton[hidden] {
+  display: none;
 }
 
 .fullscreenButton {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#fullscreen);
+  background-image: -moz-image-rect(url("chrome://global/skin/media/fullscreenButton.png"), 0, 16, 16, 0);
 }
-.fullscreenButton:hover {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#fullscreen-hover);
-}
-.fullscreenButton:hover:active {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#fullscreen-active);
+
+.fullscreenButton[fullscreened] {
+  background-image: -moz-image-rect(url("chrome://global/skin/media/fullscreenButton.png"), 0, 32, 16, 16);
 }
-.fullscreenButton[fullscreened] {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#unfullscreen);
+
+.volumeControl {
+  width: 32px;
+  opacity: 0;
 }
-.fullscreenButton[fullscreened]:hover {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#unfullscreen-hover);
-}
-.fullscreenButton[fullscreened]:hover:active {
-  background-image: url(chrome://global/skin/media/fullscreenButton.svg#unfullscreen-active);
+
+.volumeBackground,
+.volumeForeground {
+  background-repeat: no-repeat;
+  background-position: center;
+  width: 32px;
 }
 
-.controlBarSpacer {
-  flex-grow: 1;
+.volumeBackground {
+  background-image: url(chrome://global/skin/media/volume-empty.png);
+}
+
+.volumeForeground {
+  background-image: url(chrome://global/skin/media/volume-full.png);
+  background-clip: content-box;
 }
 
-.volumeControl::-moz-range-thumb,
-.scrubber::-moz-range-thumb {
-  height: 13px;
-  width: 13px;
-  border: none;
-  border-radius: 50%;
-  background-color: #ffffff;
-  filter: drop-shadow(0px 0px 5px rgba(0,0,0,0.65));
+.textTrackList {
+  display: -moz-box;
+  -moz-appearance: none;
+  -moz-box-pack: end;
+  -moz-box-align: end;
+  padding: 0;
 }
 
-.volumeControl::-moz-focus-outer,
-.scrubber::-moz-focus-outer {
-  border: 0;
+.textTrackList[hidden] {
+  display: none;
 }
 
-.progressBackgroundBar {
-  display: flex;
-  flex-direction: column;
-  justify-content: center;
-  align-items: center;
+.textTrackList > html|*.textTrackItem {
+  -moz-appearance: none;
+  -moz-box-align: start;
+  text-align: start;
+  overflow: hidden;
+  margin: 0;
+  padding: 2px 10px;
+  -moz-margin-end: 10px;
+  border: none;
+  color: rgba(255,255,255,.5);
+  background-color: rgba(35,31,32,.74);
+  white-space: nowrap;
 }
 
-.progressStack {
-  position: relative;
-  width: 100%;
-  height: 5px;
+.textTrackList > html|*.textTrackItem[on] {
+  color: white;
+  background-color: black;
+}
+
+.textTrackList > html|*.textTrackItem:hover {
+  background-color: rgba(0,0,0,.55);
 }
 
-.scrubberStack {
-  min-width: 48px;
-  flex-basis: 48px;
-  flex-grow: 2;
-  flex-shrink: 0;
-  margin: 0 9px;
+.controlBar[fullscreen-unavailable] {
+  /* This value is duplicated in the videocontrols.xml adjustControlSize function. */
+  padding-inline-end: 8px;
+}
+
+.volumeControl .scale-thumb {
+  min-width: 0;
+  opacity: 0;
 }
 
-.volumeStack {
-  max-width: 60px;
-  min-width: 48px;
-  flex-grow: 1;
-  flex-shrink: 0;
-  margin-right: 6px;
-  margin-left: 4px;
+.durationBox {
+  -moz-box-pack: center;
+}
+
+.durationLabel {
+  margin-left: -22px; /* 1/2 of scrubber thumb width, for overhang. */
+  padding-left: 8px; /* don't bump into the scrubber bar */
+  color: rgba(255,255,255,.75);
+  font: message-box;
+  font-size: 11px;
 }
 
-.bufferBar,
-.progressBar,
-.scrubber,
-.volumeBackground,
-.volumeControl {
-  bottom: 0;
-  left: 0;
-  position: absolute;
-  width: 100%;
-  height: 100%;
-  padding: 0;
-  border: 0;
+%ifdef XP_MACOSX
+.durationLabel {
+  padding-top: 2px; /* center vertically with scrubber bar */
+}
+%else
+.durationLabel {
+  padding-top: 0; /* center vertically with scrubber bar */
+}
+%endif
+
+.positionLabel {
+  display: none;
+}
+
+.backgroundBar {
+  /* margin top/bottom: make bar 8px tall (control height = 28, minus 2 * 10 margin) */
+  /* margin left/right: 1/2 of scrubber thumb width, for overhang. */
+  margin: 10px 22px;
+  background-color: rgba(255,255,255,.5);
   border-radius: 2.5px;
-  margin: 0;
-  background: none;
-  background-color: transparent;
 }
 
 .bufferBar,
-.volumeBackground {
-  background-color: rgba(0,0,0,0.7);
-}
-
-.bufferBar::-moz-progress-bar,
-.progressBar::-moz-progress-bar,
-.volumeBackground::-moz-meter-bar {
-  height: 100%;
-  padding: 0;
-  margin: 0;
-  border: 0;
-  border-radius: 2.5px;
-  background: none;
-}
-
-.scrubber:hover::-moz-range-thumb,
-.volumeControl:hover::-moz-range-thumb {
-  background-color: #48a0f7;
-}
-
-.scrubber:active::-moz-range-thumb,
-.volumeControl:active::-moz-range-thumb {
-  background-color: #2d89e6;
+.progressBar {
+  /* margin top/bottom: make bar 8px tall (control height = 28, minus 2 * 10 margin) */
+  /* margin left/right: 1/2 of scrubber thumb width, for overhang. */
+  margin: 10px 22px;
+  -moz-appearance: none;
+  border: none;
+  background-color: transparent;
+  min-width: 0;
+  min-height: 0;
 }
 
-.scrubber::-moz-range-track,
-.scrubber::-moz-range-progress {
-  background-color: transparent;
-}
-
-.volumeControl::-moz-range-progress,
-.volumeControl::-moz-range-track {
-  height: 5px;
+/* .progress-bar is an element inside the <progressmeter> implementation. */
+.bufferBar .progress-bar {
+  /*
+   * Note that this is drawn on top of the .backgroundBar. So although this
+   * has the same background-color specified, the semitransparent
+   * compositing gives it a different visual appearance.
+   */
+  background-color: rgba(255,255,255,.5);
   border-radius: 2.5px;
+  -moz-appearance: none;
 }
 
-.volumeControl::-moz-range-progress {
-  background-color: #ffffff;
-}
-
-.volumeControl::-moz-range-track {
-  background-color: rgba(0,0,0,0.7);
-}
-
-
-.bufferBar::-moz-progress-bar {
-  background-color: rgba(255,255,255,0.3);
+.progressBar .progress-bar {
+  background-color: white;
   border-radius: 2.5px;
-}
-
-.progressBar::-moz-progress-bar {
-  background-color: #00b6f0;
+  -moz-appearance: none;
 }
 
-.textTrackList {
-  position: absolute;
-  right: 5px;
-  bottom: 45px;
-  max-width: 80%;
-  border: 1px solid #000000;
-  border-radius: 2.5px;
-  padding: 5px 0;
-  vertical-align: middle;
-  font-size: 12px;
-  background-color: #000000;
-  opacity: 0.7;
+/* .scale-slider is an element inside the <scale> implementation. */
+.scrubber .scale-slider,
+.volumeControl .scale-slider {
+  /* Hide the default horizontal bar. */
+  -moz-appearance: none;
+  background: none;
+  margin: 0;
 }
 
-.textTrackList > .textTrackItem {
-  display: block;
-  width: 100%;
-  height: 30px;
-  padding: 2px 10px;
+.scrubber .scale-slider {
+  /* abs(margin-top) + margin-bottom + bar height == timeThumb height */
+  margin-top: -10px;
+  margin-bottom: 10px;
+}
+/* .scale-thumb is an element inside the <scale> implementation. */
+.scrubber .scale-thumb,
+.volumeControl .scale-thumb {
+  /* Override the default thumb appearance with a custom image. */
+  -moz-appearance: none;
+  background: transparent;
   border: none;
-  margin: 0;
-  white-space: nowrap;
-  overflow: hidden;
-  text-align: left;
-  text-overflow: ellipsis;
-  color: #ffffff;
-  background-color: transparent;
-}
-
-.textTrackList > .textTrackItem:hover {
-  background-color: #444444;
 }
 
-.textTrackList > .textTrackItem[on] {
-  color: #00b6f0;
-}
-
-.positionLabel,
-.durationLabel {
-  display: none;
+.timeThumb {
+  background: url(chrome://global/skin/media/scrubberThumb.png) no-repeat center;
+  min-width: 45px;
+  min-height: 28px;
+  -moz-box-pack: center;
 }
 
-.positionDurationBox {
-  min-width: 9ch;
-  text-align: center;
-  padding-inline-start: 1px;
-  padding-inline-end: 9px;
-  white-space: nowrap;
-  font: message-box;
-  font-size: 13px;
-  font-size-adjust: 0.6;
-  color: #ffffff;
+.timeThumb[showhours="true"] {
+  background-image: url(chrome://global/skin/media/scrubberThumbWide.png);
 }
 
-.positionDurationBox[positionOnly] {
-  min-width: 4ch;
+.timeLabel {
+  color: rgba(255,255,255,.75);
+  font: message-box;
+  font-size: 10px;
+  text-shadow: rgba(0,0,0,.3) 0 1px;
+  padding-top: 7px;
 }
 
 %ifdef XP_MACOSX
-.positionDurationBox {
-  font-size-adjust: unset;
+.timeLabel {
+  padding-top: 7px; /* center vertically with scrubber bar */
+}
+%else
+.timeLabel {
+  padding-top: 5px; /* center vertically with scrubber bar */
 }
 %endif
 
-.duration {
-  display: inline-block;
-  white-space: pre;
-  color: #929292;
+.statusOverlay {
+  -moz-box-align: center;
+  -moz-box-pack: center;
+  background-color: rgba(0,0,0,.55);
 }
 
 .statusIcon {
+  margin-bottom: 28px; /* same height as .controlBar, to keep icon centered above it */
   width: 36px;
   height: 36px;
-  margin-bottom: 20px;
 }
 
 .statusIcon[type="throbber"] {
   background: url(chrome://global/skin/media/throbber.png) no-repeat center;
 }
 
 .statusIcon[type="throbber"][stalled] {
   background: url(chrome://global/skin/media/stalled.png) no-repeat center;
 }
 
 .statusIcon[type="error"] {
-  min-width: 70px;
-  min-height: 60px;
   background: url(chrome://global/skin/media/error.png) no-repeat center;
-  background-size: contain;
 }
 
 /* Overlay Play button */
 .clickToPlay {
-  min-width: 48px;
-  min-height: 48px;
-  border-radius: 50%;
-  background-image: url(chrome://global/skin/media/playButton.svg#play);
-  background-repeat: no-repeat;
-  background-position: 54% 50%;
-  background-size: 40% 40%;
-  background-color: #1a1a1a;
-  opacity: 0.8;
-  position: relative;
-  top: 20px;
+  width: 64px;
+  height: 64px;
+  -moz-box-pack: center;
+  -moz-box-align: center;
+  opacity: 0.7;
+  background-image: url(chrome://global/skin/media/clicktoplay-bgtexture.png),
+                    url(chrome://global/skin/media/videoClickToPlayButton.svg);
+  background-repeat: repeat, no-repeat;
+  background-position: center, center;
+  background-size: auto, 64px 64px;
+  background-color: hsla(0,0%,10%,.5);
+}
+.clickToPlay:hover {
+  opacity: 1;
 }
 
-.controlsSpacerStack:hover > .clickToPlay,
-.clickToPlay:hover {
-  opacity: 0.55;
+/* Statistics formatting */
+html|*.statsDiv {
+  position: relative;
+}
+html|td {
+  height: 1em;
+  max-height: 1em;
+  padding: 0 2px;
 }
-
-.controlsSpacerStack:hover > .clickToPlay[fadeout] {
-  opacity: 0;
-}
-
-.controlBar[fullscreen-unavailable] .fullscreenButton {
-  display: none;
+html|table {
+  font-family: Helvetica, Arial, sans-serif;
+  font-size: 11px;
+  color: white;
+  text-shadow:
+    -1px -1px 0 #000,
+    1px -1px 0 #000,
+    -1px 1px 0 #000,
+    1px 1px 0 #000;
+  min-width: 100%;
+  background: rgba(68,68,68,.7);
+  table-layout: fixed;
+  border-collapse: collapse;
+  position: absolute;
 }
 
 /* CSS Transitions */
 .clickToPlay {
-  transition-property: transform, opacity;
+  transition-property: opacity, background-size;
   transition-duration: 400ms, 400ms;
 }
-
-.controlsSpacer[fadeout] {
+.clickToPlay[fadeout] {
+  background-size: auto, 192px 192px;
   opacity: 0;
 }
-
-.clickToPlay[fadeout] {
-  transform: scale(3);
-  opacity: 0;
-}
-
 .clickToPlay[fadeout][immediate] {
   transition-property: opacity, background-size;
   transition-duration: 0s, 0s;
 }
 .controlBar:not([immediate]) {
   transition-property: opacity;
   transition-duration: 200ms;
 }
 .controlBar[fadeout] {
   opacity: 0;
 }
 .volumeStack:not([immediate]) {
   transition-property: opacity, margin-top;
   transition-duration: 200ms, 200ms;
 }
+.volumeStack[fadeout] {
+  opacity: 0;
+  margin-top: 0;
+}
 .statusOverlay:not([immediate]) {
   transition-property: opacity;
   transition-duration: 300ms;
   transition-delay: 750ms;
 }
 .statusOverlay[fadeout] {
   opacity: 0;
 }
 
 /* Error description formatting */
 .errorLabel {
+  font-family: Helvetica, Arial, sans-serif;
+  font-size: 11px;
+  color: #bbb;
+  text-shadow:
+    -1px -1px 0 #000,
+    1px -1px 0 #000,
+    -1px 1px 0 #000,
+    1px 1px 0 #000;
   padding: 0 10px;
   text-align: center;
-  font: message-box;
-  font-size: 14px;
-  color: #ffffff;
 }
 
-.errorLabel {
-  display: none;
+@media (min-resolution: 2dppx) {
+  .playButton {
+    background-image: url(chrome://global/skin/media/pauseButton@2x.png);
+    background-size: 28px 28px;
+  }
+  .playButton[paused] {
+    background-image: url(chrome://global/skin/media/playButton@2x.png);
+    background-size: 28px 28px;
+  }
+  .volumeBackground {
+    background-image: url(chrome://global/skin/media/volume-empty@2x.png);
+    background-size: 32px 16px;
+  }
+  .volumeForeground {
+    background-image: url(chrome://global/skin/media/volume-full@2x.png);
+    background-size: 32px 16px;
+  }
+  .muteButton {
+    background-image: url(chrome://global/skin/media/muteButton@2x.png);
+    background-size: 33px 28px;
+  }
+  .muteButton[muted] {
+    background-image: url(chrome://global/skin/media/unmuteButton@2x.png);
+    background-size: 33px 28px;
+  }
+  .muteButton[noAudio] {
+    background-image: url(chrome://global/skin/media/noAudio@2x.png);
+    background-size: 33px 28px;
+  }
+  .closedCaptionButton {
+    background-image: url(chrome://global/skin/media/closeCaptionButton@2x.png);
+    background-position: 4px;
+    background-size: 28px 28px;
+  }
+  .fullscreenButton {
+    background-image: -moz-image-rect(url("chrome://global/skin/media/fullscreenButton@2x.png"), 0, 32, 32, 0);
+    background-size: 16px 16px;
+  }
+  .fullscreenButton[fullscreened] {
+    background-image: -moz-image-rect(url("chrome://global/skin/media/fullscreenButton@2x.png"), 0, 64, 32, 32);
+    background-size: 16px 16px;
+  }
+  .timeThumb {
+    background-image: url(chrome://global/skin/media/scrubberThumb@2x.png);
+    background-size: 33px 28px;
+  }
+  .timeThumb[showhours="true"] {
+    background-image: url(chrome://global/skin/media/scrubberThumbWide@2x.png);
+    background-size: 45px 28px;
+  }
 }
-
-[error="errorAborted"]         > [anonid="errorAborted"],
-[error="errorNetwork"]         > [anonid="errorNetwork"],
-[error="errorDecode"]          > [anonid="errorDecode"],
-[error="errorSrcNotSupported"] > [anonid="errorSrcNotSupported"],
-[error="errorNoSource"]        > [anonid="errorNoSource"],
-[error="errorGeneric"]         > [anonid="errorGeneric"] {
-  display: inline;
-}
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..589abfbd5816bb3ec179a3fdf6530106356dba8e
GIT binary patch
literal 295
zc%17D@N?(olHy`uVBq!ia0vp^3P3Et!3HGD8EPYelw^r(L`iUdT1k0gQ7VIDN`6wR
zf@f}GdTLN=VoGJ<$y6JlqLZF3jv*DdlK%YvZ-3Z<Y1*-4ZdJD>`Hrv!tU2xE+<j((
z4pXA`iXU841Qtw6UFRX@>U`8sNR(BCZJ~Ndj`*Y+6VFVBb_;2N|4o~gKje1uViXqW
zc4`)2TgUX#U!_h>Ao`MyIKxM6joE@;*%yty4Geh<7%UxxGz}XM`0f&Oarnd3QLfOL
z$zZ51R4-;Cc<Bt|jRWN>WmdCdOoGgo%w+!1m>ST-V{@`pWUJR9*^G-P7<A2fI4pan
ql^!hANIM|h%GSdiE6dCx!SL>yqE+B(ySG43F?hQAxvX<aXaWGv&|&KU
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..ca494e89366563cbb509761eb1f8f3bcae60e2cd
GIT binary patch
literal 268
zc$@(Y0rUQeP)<h;3K|Lk000e1NJLTq002M$001Be1ONa42$Z%D0002fNkl<ZcmeH}
zu?Ye}6hsfrtiTEcE3gGC5Uv6{@C;w3C0N0M71)9m2v%SNnkkCGB+JKa{{-Gnau=NQ
z_%k23ah%~WV#bOcCvFYdI&kLBTdHq3WyywK?=r3qpb^U`17N~}b!n6X(9v_@DWm!T
zYH{(S2>?Zls{^RTUD@KA02*=eK^lNYoCgq&I1xY(e+n=FsDxXNK7eQqA1(lC%-jZ0
zN)g!r;)t98im3Jc9mo1cbmip(Fki`Hwd}Jmr9ZdG2M}(N5kOm{h#JhY1AG7pNkP0H
Soro&{0000<MNUMnLSTaT9Ay0f
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..4398a569b8c76d0b42fd2900abfcdec1747a0483
GIT binary patch
literal 297
zc$@(#0oMMBP)<h;3K|Lk000e1NJLTq001BW000mO1^@s6cL04^0000PbVXQnQ*UN;
zcVTj606}DLVr3vnZDD6+Qe|Oed2z{QJOBUy%Sl8*RCwBA{Qv(y!$1O-&!0cj+s<$x
zHh^MX#!sI<(aIt-B#S`U3M!5g<SbOO%oWL^XsFmpVl<Ky0?0w=3HA~YFfua2&BW$Y
zT;jMKzy`#>pzLWt^9_I&U<*P<BE|4JKoshm-B7WsK&*vD10yXQ07?U|&=hFVGfOZr
z3@`vWKoXXipx`Dw9e^tlasu&pD0?O}jhNFa4PXP`k=W^Ia?wcHkY*u3D)2yZR0K83
v0crqCw4&IY-VVS8qL3ZNIMCHGK!5=N%h^ktibA+A00000NkvXXu0mjf898vG
new file mode 100644
index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..5bf63c7ee25a0a7c2fbfee5db50b95b20093b1e8
GIT binary patch
literal 267
zc%17D@N?(olHy`uVBq!ia0vp^4nVBH!2%>XrflN}QkOhk978G?-%i`e$>b>F!hd$n
z0WKEp4XoM%>zJ%Rym9c}(8LVpt~u~$;mk!6KAUO`ZrL|(pL~b)xy`>b$8%-UEqZ2b
zOgi2f?Yxa|&d$%%UP=2!Zd!PKch73(j3Y*;7-noph?RQEQ1T_F;?xSOhNzf-8B7ir
zAH8D8Dh%JYL#e?nrfve;0>R~sN0j|oE*zfE#KWNVaN1&Sg}B4*+zwL4+Zm?>x!5%r
zD5*CnW!csr-?&dOwsI!JpYTl)y1(CezkIK|iQ!1}6XpwInv2*rzhRJ<^r#mNe6ac^
P(02@;u6{1-oD!M<!C7c!