725 lines
14 KiB
CSS
725 lines
14 KiB
CSS
/* 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/. */
|
|
|
|
:root {
|
|
--player-bg-color: #000;
|
|
--player-control-icon-fill: #fff;
|
|
--player-control-item-half-width: clamp(calc(16px / 2), calc(10vmax / 2), calc(32px / 2));
|
|
--player-control-item-height: clamp(16px, 10vmax, 32px);
|
|
--close-btn-fill-color: #000;
|
|
--controls-bottom-distance: 15px;
|
|
--controls-bottom-upper-height: 30px;
|
|
--scrubber-vertical-margin: 7px;
|
|
--resize-margin: 5px;
|
|
|
|
background-color: var(--player-bg-color);
|
|
overflow: hidden;
|
|
}
|
|
|
|
button::-moz-focus-inner {
|
|
border: 0;
|
|
}
|
|
|
|
body {
|
|
margin: 0;
|
|
}
|
|
|
|
body:fullscreen {
|
|
-moz-window-dragging: no-drag;
|
|
}
|
|
|
|
.player-holder {
|
|
display: flex;
|
|
flex-direction: column;
|
|
height: 100vh;
|
|
overflow: hidden;
|
|
}
|
|
|
|
.seethrough-mode {
|
|
background: transparent;
|
|
|
|
.player-holder {
|
|
will-change: opacity, filter;
|
|
transition: opacity 160ms linear, filter 160ms linear;
|
|
|
|
body:hover:not(:fullscreen) & {
|
|
opacity: 0.35;
|
|
filter: blur(8px);
|
|
}
|
|
}
|
|
}
|
|
|
|
browser {
|
|
flex: 1;
|
|
}
|
|
|
|
#controls {
|
|
height: calc(100% - 2 * var(--resize-margin));
|
|
left: 0;
|
|
position: absolute;
|
|
top: 0;
|
|
width: calc(100% - 2 * var(--resize-margin));
|
|
margin: var(--resize-margin);
|
|
-moz-window-dragging: drag;
|
|
}
|
|
|
|
#controls button {
|
|
appearance: none;
|
|
border: 0;
|
|
z-index: 1;
|
|
}
|
|
|
|
#controls button:focus-visible,
|
|
#controls input:focus-visible,
|
|
.switch > input:focus-visible + .slider {
|
|
outline: 3px solid #0060DF;
|
|
box-shadow: 1px 2px 5px #000;
|
|
}
|
|
|
|
/* Styling for background gradient.
|
|
* Opacity changes are handled separately under .control-item.
|
|
*/
|
|
#controls-bottom-gradient {
|
|
background: linear-gradient(0deg, #000000 -13.24%, rgba(0, 0, 0, 0) 90.44%);
|
|
position: absolute;
|
|
height: calc(var(--controls-bottom-distance) + 2 * var(--resize-margin) + var(--player-control-item-height) + var(--controls-bottom-upper-height) + var(--scrubber-vertical-margin));
|
|
bottom: 0;
|
|
width: 100vw;
|
|
margin: 0 calc(-1 * var(--resize-margin)) calc(-1 * var(--resize-margin)) calc(-1 * var(--resize-margin));
|
|
pointer-events: none;
|
|
-moz-window-dragging: drag;
|
|
}
|
|
|
|
#controls-bottom {
|
|
position: absolute;
|
|
bottom: var(--controls-bottom-distance);
|
|
width: 100%;
|
|
}
|
|
|
|
.controls-bottom-lower {
|
|
display: grid;
|
|
grid-template-columns: repeat(3, 1fr);
|
|
margin: 0 24px;
|
|
}
|
|
|
|
.start-controls {
|
|
display: grid;
|
|
justify-self: start;
|
|
}
|
|
|
|
.center-controls {
|
|
display: grid;
|
|
grid-template-columns: repeat(3, 1fr);
|
|
grid-template-areas: "seekbackward playpause seekforward";
|
|
justify-self: center;
|
|
gap: 8px;
|
|
}
|
|
|
|
.end-controls {
|
|
display: grid;
|
|
grid-template-columns: 1fr 2fr 1fr 1fr;
|
|
grid-template-areas: "audio audio-scrubber closedcaption fullscreen";
|
|
justify-self: end;
|
|
gap: 8px;
|
|
}
|
|
|
|
.control-item {
|
|
-moz-window-dragging: no-drag;
|
|
transition: opacity 160ms linear, fill-opacity 160ms linear;
|
|
opacity: 0;
|
|
cursor: pointer;
|
|
}
|
|
|
|
.control-button {
|
|
background-color: transparent;
|
|
border-radius: 4px;
|
|
/**
|
|
* Make the button dimensions a square proportional to one
|
|
* dimension of the window - in this case, the width dimension,
|
|
* since we suspect most videos are wider than they are tall.
|
|
*/
|
|
height: var(--player-control-item-height);
|
|
width: 10vmax;
|
|
max-width: 32px;
|
|
min-width: 16px;
|
|
-moz-context-properties: fill, fill-opacity;
|
|
fill: var(--player-control-icon-fill);
|
|
background-position: center;
|
|
background-size: 60%;
|
|
background-repeat: no-repeat;
|
|
}
|
|
|
|
.control-button:hover:enabled {
|
|
background-color: rgba(255, 255, 255, .25);
|
|
}
|
|
|
|
#controls:is([keying], [showing]) .control-button:disabled,
|
|
/* Only change opacity on hover events for non-fullscreen mode.
|
|
* Fullscreen mode uses the `showing` attribute instead. */
|
|
body:not(:fullscreen) #controls:hover .control-button:disabled {
|
|
/* Set `fill-opacity` to the desired opacity in addition to full `opacity`
|
|
* to allow having the button's tooltip in full opacity even if the button is disabled. */
|
|
fill-opacity: 0.4;
|
|
opacity: 1 !important;
|
|
}
|
|
|
|
.control-item:focus-visible::after,
|
|
.control-item:hover::after {
|
|
content: attr(tooltip);
|
|
display: inline-block;
|
|
width: max-content;
|
|
position: relative;
|
|
padding: .4em .5em;
|
|
background: #000000;
|
|
color: #ffffff;
|
|
border-radius: 4px;
|
|
pointer-events: none;
|
|
}
|
|
|
|
/* Since #controls is set to LTR, button tooltips would normally appear
|
|
* as LTR also for RTL locales. To fix this, set the .control-item's ::after
|
|
* to RTL based on the root directionality.
|
|
* Because of that, don't set logical properties for the next set of rules. */
|
|
:root:dir(rtl) .control-item::after {
|
|
direction: rtl;
|
|
}
|
|
|
|
/* Set the tooltip position for different playback controls */
|
|
|
|
.tooltip-under-controls:focus-visible::after,
|
|
.tooltip-under-controls:hover::after {
|
|
bottom: -3em;
|
|
}
|
|
|
|
#close:focus-visible::after,
|
|
#close:hover::after,
|
|
#unpip[mac="true"]:focus-visible::after,
|
|
#unpip[mac="true"]:hover::after {
|
|
float: right;
|
|
transform: translateX(1em);
|
|
}
|
|
|
|
#unpip:focus-visible::after,
|
|
#unpip:hover::after,
|
|
#close[mac="true"]:focus-visible::after,
|
|
#close[mac="true"]:hover::after {
|
|
float: left;
|
|
transform: translateX(-1em);
|
|
}
|
|
|
|
.tooltip-over-controls:focus-visible::after,
|
|
.tooltip-over-controls:hover::after {
|
|
bottom: 3em;
|
|
}
|
|
|
|
.inline-end-tooltip:focus-visible::after,
|
|
.inline-end-tooltip:hover::after {
|
|
float: right;
|
|
right: -1em;
|
|
}
|
|
|
|
.inline-start-tooltip:focus-visible::after,
|
|
.inline-start-tooltip:hover::after {
|
|
float: left;
|
|
left: -1em;
|
|
}
|
|
|
|
.center-tooltip:focus-visible::after,
|
|
.center-tooltip:hover::after {
|
|
right: 0.8em;
|
|
translate: calc(-50% + var(--player-control-item-half-width));
|
|
}
|
|
|
|
/* Since the unpip button icon is reversed for RTL locales,
|
|
* re-position the tooltip so that the tooltip remains in the original placement */
|
|
:root:dir(rtl) #unpip:focus-visible::after,
|
|
:root:dir(rtl) #unpip:hover::after {
|
|
float: right;
|
|
}
|
|
|
|
:root:dir(rtl) #unpip[mac="true"]:focus-visible::after,
|
|
:root:dir(rtl) #unpip[mac="true"]:hover::after {
|
|
float: left;
|
|
}
|
|
|
|
/* Since the unpip icon is reversed for RTL locales,
|
|
* flip its tooltip back */
|
|
:root:dir(rtl) #unpip:focus-visible::after,
|
|
:root:dir(rtl) #unpip:hover::after {
|
|
scale: -1 1;
|
|
}
|
|
|
|
/* Set opacity for buttons and scrubber when controls are visible on the pip window and are not hovered over.
|
|
* For fullscreen mode, only apply opacity if there is a showing attribute. */
|
|
body:not(:fullscreen) #controls:hover .control-item:not(:hover),
|
|
body:fullscreen #controls[showing]:hover .control-item:not(:hover),
|
|
#controls[donthide] .control-item {
|
|
opacity: 0.8;
|
|
}
|
|
|
|
#controls[keying] .control-item,
|
|
#controls[showing] .control-item,
|
|
.control-item:hover {
|
|
opacity: 1;
|
|
}
|
|
|
|
/* Background gradient is the only control item with a fixed opacity value. */
|
|
#controls[keying] #controls-bottom-gradient,
|
|
#controls[showing] #controls-bottom-gradient,
|
|
#controls-bottom-gradient:hover {
|
|
opacity: 0.8;
|
|
}
|
|
|
|
/* For readability, timestamp should maintain full opacity when visible */
|
|
body:not(:fullscreen) #controls:hover #timestamp,
|
|
body:fullscreen #controls[showing]:hover {
|
|
opacity: 1;
|
|
}
|
|
|
|
#close,
|
|
#unpip {
|
|
background-color: rgba(255, 255, 255, .8);
|
|
position: absolute;
|
|
fill: var(--close-btn-fill-color);
|
|
}
|
|
|
|
#close:is(:hover, :focus-visible),
|
|
#unpip:is(:hover, :focus-visible) {
|
|
background-color: rgba(255, 255, 255, .9);
|
|
}
|
|
|
|
#close {
|
|
background-image: url("chrome://global/skin/icons/close.svg");
|
|
right: 10px;
|
|
top: 10px;
|
|
}
|
|
|
|
#close[mac="true"] {
|
|
right: auto;
|
|
left: 10px;
|
|
}
|
|
|
|
#unpip {
|
|
background-image: url("chrome://global/skin/media/picture-in-picture-closed.svg");
|
|
left: 10px;
|
|
top: 10px;
|
|
}
|
|
|
|
#unpip[mac="true"] {
|
|
right: 10px;
|
|
left: auto;
|
|
}
|
|
|
|
#playpause {
|
|
grid-area: playpause;
|
|
}
|
|
|
|
#audio {
|
|
grid-area: audio;
|
|
}
|
|
|
|
#audio-scrubber {
|
|
grid-area: audio-scrubber;
|
|
align-self: center;
|
|
width: 64px;
|
|
background-color: transparent;
|
|
padding: 6px 2px;
|
|
margin: 0;
|
|
|
|
&::-moz-range-thumb {
|
|
border-radius: 8px;
|
|
background-color: #FFFFFF;
|
|
width: 8px;
|
|
height: 8px;
|
|
padding: 0;
|
|
}
|
|
|
|
&::-moz-range-track {
|
|
background-color: #969696;
|
|
}
|
|
|
|
&::-moz-range-progress {
|
|
background-color: #FFFFFF;
|
|
}
|
|
|
|
&,
|
|
&::-moz-range-track,
|
|
&::-moz-range-progress {
|
|
height: 2px;
|
|
border-radius: 10px;
|
|
}
|
|
}
|
|
|
|
#fullscreen {
|
|
grid-area: fullscreen;
|
|
}
|
|
|
|
#controls.playing #playpause {
|
|
background-image: url("chrome://global/skin/media/pause-fill.svg");
|
|
}
|
|
|
|
#controls:not(.playing) #playpause {
|
|
background-image: url("chrome://global/skin/media/play-fill.svg");
|
|
}
|
|
|
|
#controls.muted #audio {
|
|
background-image: url("chrome://global/skin/media/audio-muted.svg");
|
|
}
|
|
|
|
#controls:not(.muted) #audio {
|
|
background-image: url("chrome://global/skin/media/audio.svg");
|
|
}
|
|
|
|
body:fullscreen #fullscreen {
|
|
background-image: url("chrome://global/skin/media/picture-in-picture-exit-fullscreen-button.svg");
|
|
background-size: auto;
|
|
}
|
|
|
|
body:not(:fullscreen) #fullscreen {
|
|
background-image: url("chrome://global/skin/media/picture-in-picture-enter-fullscreen-button.svg");
|
|
background-size: auto;
|
|
}
|
|
|
|
#seekBackward {
|
|
background-image: url("chrome://global/skin/media/picture-in-picture-seekBackward-button.svg");
|
|
background-size: auto;
|
|
grid-area: seekbackward;
|
|
}
|
|
|
|
#seekForward {
|
|
background-image: url("chrome://global/skin/media/picture-in-picture-seekForward-button.svg");
|
|
background-size: auto;
|
|
grid-area: seekforward;
|
|
}
|
|
|
|
:root:dir(rtl) #unpip {
|
|
transform: scaleX(-1);
|
|
}
|
|
|
|
#closed-caption {
|
|
background-image: url("chrome://global/skin/media/closed-caption-settings-button.svg");
|
|
color: white;
|
|
grid-area: closedcaption;
|
|
}
|
|
|
|
.box {
|
|
-moz-window-dragging: no-drag;
|
|
background-color: #2B2A33;
|
|
text-align: start;
|
|
font-size: 1em;
|
|
width: 186px;
|
|
padding: 0 8px;
|
|
margin: 0;
|
|
border-radius: 8px;
|
|
}
|
|
|
|
:root:dir(rtl) .box {
|
|
direction: rtl;
|
|
}
|
|
|
|
.a11y-only {
|
|
visibility: hidden;
|
|
position: absolute;
|
|
}
|
|
|
|
.hide {
|
|
display: none;
|
|
}
|
|
|
|
.bold {
|
|
font-weight: 590;
|
|
}
|
|
|
|
.box > input[type="radio"] {
|
|
background-color: red;
|
|
fill: currentColor;
|
|
}
|
|
|
|
.box label:not(.switch) {
|
|
color: white;
|
|
font-family: sans-serif;
|
|
}
|
|
|
|
#subtitles-toggle-label {
|
|
width: fit-content;
|
|
padding: 8px;
|
|
}
|
|
|
|
.panel {
|
|
position: absolute;
|
|
bottom: 40px;
|
|
user-select: none;
|
|
right: 24px;
|
|
}
|
|
|
|
.panel-fieldset {
|
|
border: none;
|
|
margin-top: 8px;
|
|
padding-inline-start: 0;
|
|
}
|
|
|
|
.panel-legend {
|
|
font-family: sans-serif;
|
|
color: white;
|
|
margin-top: 8px;
|
|
padding-inline-start: 0;
|
|
}
|
|
|
|
.arrow {
|
|
border: 10px solid transparent;
|
|
border-top-color: #2B2A33;
|
|
width: 0;
|
|
height: 0;
|
|
inset-inline-start: 136px;
|
|
position: relative;
|
|
}
|
|
|
|
.grey-line {
|
|
width: 100%;
|
|
height: 1px;
|
|
background: #8F8F9D;
|
|
}
|
|
|
|
.font-size-selection {
|
|
margin-inline-start: 8px;
|
|
padding-inline-start: 8px;
|
|
}
|
|
|
|
.font-size-selection-radio {
|
|
display: flex;
|
|
width: fit-content;
|
|
cursor: pointer;
|
|
padding-block: 8px;
|
|
}
|
|
|
|
.font-size-selection-radio label {
|
|
cursor: pointer;
|
|
}
|
|
|
|
.font-size-selection-radio > input[type="radio"] {
|
|
appearance: none;
|
|
width: 16px;
|
|
height: 16px;
|
|
border: 1px solid #8f8f9d;
|
|
border-radius: 50%;
|
|
margin: 0;
|
|
margin-inline-end: 6px;
|
|
}
|
|
|
|
.font-size-selection-radio > input[type="radio"]:checked {
|
|
border: 4px solid #00ddff;
|
|
}
|
|
|
|
.subtitle-grid {
|
|
display: grid;
|
|
grid-template-rows: auto;
|
|
grid-template-columns: auto 46px;
|
|
padding: 8px;
|
|
}
|
|
|
|
.switch {
|
|
position: relative;
|
|
display: inline-block;
|
|
width: 32px;
|
|
height: 16px;
|
|
grid-column: 2;
|
|
margin: 8px;
|
|
cursor: pointer;
|
|
}
|
|
|
|
.switch input {
|
|
opacity: 0;
|
|
width: 0;
|
|
height: 0;
|
|
}
|
|
|
|
.slider {
|
|
position: absolute;
|
|
inset: 0;
|
|
transition: transform 250ms;
|
|
border-radius: 13px;
|
|
background-color: #55545f;
|
|
}
|
|
|
|
.slider::before {
|
|
position: absolute;
|
|
content: '';
|
|
height: 12px;
|
|
width: 12px;
|
|
inset-inline-start: 2px;
|
|
bottom: 2px;
|
|
background-color: #2B2A33;
|
|
transition: transform 250ms;
|
|
border-radius: 50%;
|
|
}
|
|
|
|
input:checked + .slider {
|
|
background-color: #00ddff;
|
|
}
|
|
|
|
input:checked + .slider::before {
|
|
transform: translateX(16px);
|
|
}
|
|
|
|
:root:dir(rtl) input:checked + .slider::before {
|
|
transform: translateX(-16px);
|
|
}
|
|
|
|
.font-size-overlay {
|
|
opacity: 0.4;
|
|
pointer-events: none;
|
|
}
|
|
|
|
.controls-bottom-upper {
|
|
width: calc(100% - 38px);
|
|
height: var(--controls-bottom-upper-height);
|
|
margin: 0 19px;
|
|
display: grid;
|
|
}
|
|
|
|
.scrubber-no-drag {
|
|
-moz-window-dragging: no-drag;
|
|
height: 16px;
|
|
margin: var(--scrubber-vertical-margin) 0;
|
|
display: grid;
|
|
justify-items: center;
|
|
align-items: center;
|
|
width: 100%;
|
|
}
|
|
|
|
#scrubber {
|
|
width: 100%;
|
|
background-color: transparent;
|
|
padding: 6px 2px;
|
|
|
|
&::-moz-range-thumb {
|
|
border-radius: 14px;
|
|
background-color: #BFBFC9;
|
|
width: 8px;
|
|
height: 8px;
|
|
border: 3px solid #FFFFFF;
|
|
padding: 0;
|
|
}
|
|
|
|
&::-moz-range-track {
|
|
background-color: #969696;
|
|
}
|
|
|
|
&::-moz-range-progress {
|
|
background-color: #FFFFFF;
|
|
}
|
|
|
|
&,
|
|
&::-moz-range-track,
|
|
&::-moz-range-progress {
|
|
height: 4px;
|
|
border-radius: 10px;
|
|
}
|
|
}
|
|
|
|
#timestamp {
|
|
align-self: center;
|
|
color: #FFFFFF;
|
|
cursor: default;
|
|
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", "Ubuntu", "Helvetica Neue", sans-serif;
|
|
font-size: 0.9em;
|
|
user-select: none;
|
|
width: 16ch;
|
|
grid-area: timestamp;
|
|
}
|
|
|
|
#timestamp::after {
|
|
background: unset;
|
|
content: unset;
|
|
}
|
|
|
|
@media (width <= 630px) {
|
|
#audio-scrubber {
|
|
display: none;
|
|
}
|
|
|
|
.end-controls {
|
|
grid-template-columns: repeat(3, 1fr);
|
|
grid-template-areas: "audio closedcaption fullscreen";
|
|
}
|
|
}
|
|
|
|
@media (width <= 475px) {
|
|
#closed-caption {
|
|
display: none;
|
|
}
|
|
|
|
.end-controls {
|
|
grid-template-columns: repeat(2, 1fr);
|
|
grid-template-areas: "audio fullscreen";
|
|
}
|
|
}
|
|
|
|
@media (height <= 325px) and (width > 630px) {
|
|
#closed-caption {
|
|
display: none;
|
|
}
|
|
|
|
.end-controls {
|
|
grid-template-columns: 1fr 2fr 1fr;
|
|
grid-template-areas: "audio audio-scrubber fullscreen";
|
|
}
|
|
}
|
|
|
|
@media (height <= 325px) and (width <= 630px) {
|
|
#closed-caption,
|
|
#audio-scrubber {
|
|
display: none;
|
|
}
|
|
|
|
.end-controls {
|
|
grid-template-columns: repeat(2, 1fr);
|
|
grid-template-areas: "audio fullscreen";
|
|
}
|
|
}
|
|
|
|
@media (width <= 440px) {
|
|
#timestamp {
|
|
display: none;
|
|
}
|
|
}
|
|
|
|
@media (width <= 350px) {
|
|
#fullscreen {
|
|
display: none;
|
|
}
|
|
|
|
.end-controls {
|
|
grid-template-columns: repeat(1, 1fr);
|
|
grid-template-areas: "audio";
|
|
}
|
|
}
|
|
|
|
@media (height <= 200px) {
|
|
.scrubber-no-drag {
|
|
display: none;
|
|
}
|
|
}
|
|
|
|
@media (width <= 300px) {
|
|
.scrubber-no-drag,
|
|
#seekForward,
|
|
#seekBackward,
|
|
.start-controls {
|
|
display: none;
|
|
}
|
|
|
|
.controls-bottom-lower {
|
|
grid-template-columns: repeat(2, 1fr);
|
|
}
|
|
|
|
.center-controls {
|
|
grid-template-columns: repeat(1, 1fr);
|
|
grid-template-areas: "playpause";
|
|
}
|
|
|
|
.end-controls {
|
|
justify-self: center;
|
|
}
|
|
}
|