Skip to content

Instantly share code, notes, and snippets.

@dylanjha
Created October 13, 2021 22:58
Show Gist options
  • Save dylanjha/0add32352bf6575a50e618695830392e to your computer and use it in GitHub Desktop.
Save dylanjha/0add32352bf6575a50e618695830392e to your computer and use it in GitHub Desktop.
diff --git a/components/media-chrome.js b/components/media-chrome.js
index d67d7d8..91a52cd 100644
--- a/components/media-chrome.js
+++ b/components/media-chrome.js
@@ -3,7 +3,7 @@ import { useImperativeHandle, forwardRef, useRef, useState, useCallback, useEffe
import { useRouter } from 'next/router';
import '@mux-elements/mux-video';
import 'media-chrome';
-import { controlBarHeight, mobileControlBarOffsetLive, mobileControlBarOffsetVod, desktopControlBarOffsetLive, desktopControlBarOffsetVod } from '../config/style-vars';
+import { controlBarHeight } from '../config/style-vars';
import { HEADER_KEY } from '../client/request';
import PlayButton from './controls/play-button';
import LargePlayButton from './controls/large-play-button';
@@ -12,7 +12,7 @@ import SeekBack from './controls/seek-back';
import SeekForward from './controls/seek-forward';
import FullScreen from './controls/fullscreen-button';
import PipButton from './controls/pip-button';
-import CaptionsButton from './controls/captions-button';
+// import CaptionsButton from './controls/captions-button';
import AirPlayButton from './controls/air-play-button';
/*
@@ -31,7 +31,7 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
const src = `/api/playback/${userId}/${streamId}.m3u8?${HEADER_KEY}=${authToken}&variant=${streamVariant}`;
const isLive = useMemo(() => streamType === 'live', [streamType]);
const [isLoading, setIsLoading] = useState(true);
- const [hasCaptions, setHasCaptions] = useState(false);
+ // const [hasCaptions, setHasCaptions] = useState(false);
const [waitForAutoplayAttempt, setWaitForAutoplayAttempt] = useState(true);
const isAndroid = useMemo(() => (
@@ -52,7 +52,7 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
const captionsOrSubtitlesTrack = Array.prototype.find.call(textTrackList, (t) => t.kind === 'subtitles' || t.kind === 'captions');
if (captionsOrSubtitlesTrack) {
captionsOrSubtitlesTrack.mode = 'showing';
- setHasCaptions(true);
+ // setHasCaptions(true);
}
});
@@ -167,7 +167,7 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
return (
<>
<div className="container">
- <media-controller autohide="2">
+ <media-controller autohide="0">
{(isLoading || waitForAutoplayAttempt) && <media-loading-indicator is-loading />}
<mux-video
ref={muxVideoRef}
@@ -188,19 +188,32 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
>
{storyboardSrc && <track label="thumbnails" default kind="metadata" src={storyboardSrc} />}
</mux-video>
- {
- !waitForAutoplayAttempt
+ { !waitForAutoplayAttempt && (
+ <>
+ <div className="top-controls" slot="top-controls">
+ <media-mute-button />
+ <media-playback-rate-button />
+ <div className="spacer" />
+ {hasPip && <PipButton />}
+ <FullScreen />
+ </div>
+ <div className="overlay" slot="controls-overlay">
+ <SeekBack />
+ <LargePlayButton />
+ <SeekForward />
+ </div>
+ </>
+ )}
+ <div className="mobile-control-bar">
+ {!isLive
&& (
- <div className="large-play">
- <LargePlayButton />
- </div>
- )
- }
- <div className="mobile-time-range">
- {!isLive && <media-time-range />}
- {!isLive && <media-time-display show-duration />}
+ <media-control-bar>
+ <media-time-range />
+ <media-time-display show-duration />
+ </media-control-bar>
+ )}
</div>
- <div className="control-bar-wrapper">
+ <div className="desktop-control-bar">
{
!waitForAutoplayAttempt && (
<media-control-bar>
@@ -213,7 +226,6 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
{!isLive && <media-time-display show-duration class="desktop-time-display" />}
{isLive && <div className="spacer" />}
{!isLive && <media-playback-rate-button />}
- {hasCaptions && <CaptionsButton />}
{hasPip && <PipButton />}
<FullScreen />
{hasAirplay && <AirPlayButton onClick={() => muxVideoRef.current.webkitShowPlaybackTargetPicker()} />}
@@ -227,120 +239,79 @@ const MediaChrome = forwardRef(({ onReady, title, streamType, streamVariant, use
.spacer {
flex-grow: 1;
}
- .control-bar-wrapper {
- margin-bottom: -${streamType === 'live' ? mobileControlBarOffsetLive : mobileControlBarOffsetVod}px;
- height: ${controlBarHeight}px;
- background: #000;
- }
- :global(media-controller) {
- --media-control-background: #000;
- --media-control-hover-background: rgba(0, 0, 0, 0.2);
+ .desktop-control-bar {
+ display: none;
}
- :global(media-time-range) {
- --media-range-bar-color: #FF5968;
+ .mobile-control-bar {
+ margin-bottom: -${controlBarHeight}px;
+ background: #000;
}
:global(media-controller) {
position: absolute;
width: 100%;
height: 100%;
- top: 0;
- left: 0;
- flex-direction: column;
- justify-content: flex-end;
}
- :global(media-loading-indicator) {
- width: 100%;
- height: 100%;
- z-index: 10;
- position: absolute;
- display: flex;
- justify-content: center;
- align-items: center;
+ :global(media-time-range) {
+ --media-range-bar-color: #FF5968;
}
- .large-play {
- width: 100%;
- height: 100%;
+ .top-controls {
display: flex;
- align-items: center;
- justify-content: center;
- }
- .large-play :global(media-play-button) {
- --media-button-icon-width: 160px;
- width: 160px;
- height: 160px;
- background: transparent;
- }
- .large-play :global(media-play-button) {
- display: none;
}
- .large-play :global(media-play-button[media-paused]) {
- display: block;
- }
- :global(media-controller mux-video) {
- width: 100%;
- height: 100%;
- }
- :global(media-control-bar) {
- justify-content: space-between;
- width: 100%;
- }
- :global(media-control-bar > *) {
- height: ${controlBarHeight}px;
- }
- :global(media-control-bar > media-time-range) {
- display: none;
- }
- :global(media-play-button) {
- width: 40px;
+ .overlay {
+ flex-grow: 1;
+ display: flex;
+ flex-flow: row nowrap;
align-items: center;
justify-content: center;
}
- :global(media-play-button[media-paused]) {
- --media-button-icon-width: 20px;
+ .overlay {
+ --media-control-hover-background: transparent;
+ --media-control-background: transparent;
}
- :global(media-play-button) {
- --media-button-icon-width: 11px;
+ .top-controls {
+ --media-control-hover-background: rgba(50,50,70, 0.7);
+ --media-control-background: rgba(50,50,70, 0.7);
}
- .mobile-time-range {
- display: flex;
- align-items: center;
- height: 44px;
- background: #000;
+ .overlay :global(media-play-button) {
+ --media-button-icon-width: 160px;
+ width: 25%;
}
- .mobile-time-range :global(media-time-range) {
- flex-grow: 1;
- z-index: 100;
+ .overlay :global(media-seek-backward-button),
+ .overlay :global(media-seek-forward-button) {
+ --media-button-icon-width: 100px;
+ width: 15%;
}
- .mobile-time-range :global(media-time-display) {
- flex-shrink: 0;
- z-index: 100;
+ .mobile-control-bar :global(media-time-range) {
+ display: inline-block;
}
- :global(.desktop-time-display) {
- display: none;
+ .mobile-control-bar :global(media-control-bar) {
+ width: 100%;
}
- :global(media-volume-range) {
- display: none;
+ :global(media-controller[user-inactive="user-inactive"]:not([media-paused]) :is(.top-controls, .overlay)) {
+ opacity: 0.01;
+ transition: opacity 1s;
}
@media (min-width: 768px) {
- .mobile-time-range {
+ .mobile-control-bar {
display: none;
}
- .control-bar-wrapper {
- margin-bottom: -${streamType === 'live' ? desktopControlBarOffsetLive : desktopControlBarOffsetVod}px;
- }
- :global(media-control-bar > media-time-range) {
- display: inline-block;
+ .top-controls {
+ display: none;
}
- :global(media-control-bar > media-volume-range) {
- display: inline-block;
+ .overlay {
+ display: none;
}
- :global(.desktop-time-display) {
- display: inline-flex;
+ .desktop-control-bar {
+ display: flex;
+ width: 100%;
+ margin-bottom: -${controlBarHeight}px;
+ height: ${controlBarHeight}px;
+ background: #000;
}
- :global(.mobile-time-display) {
- display: none;
+ .desktop-control-bar :global(media-control-bar) {
+ width: 100%;
}
- :global(media-controller[user-inactive="user-inactive"] media-control-bar) {
+ :global(media-controller[user-inactive="user-inactive"]:not([media-paused]) media-control-bar) {
opacity: 0.01;
transition: opacity 1s;
}
diff --git a/components/player-loader.js b/components/player-loader.js
index ab002cc..66f3e1a 100644
--- a/components/player-loader.js
+++ b/components/player-loader.js
@@ -1,7 +1,7 @@
/* eslint-disable react/jsx-props-no-spreading */
import { forwardRef } from 'react';
import dynamic from 'next/dynamic';
-import { mobileControlBarOffsetLive, mobileControlBarOffsetVod, desktopControlBarOffsetLive, desktopControlBarOffsetVod } from '../config/style-vars';
+import { controlBarHeight } from '../config/style-vars';
const MediaChrome = dynamic(() => import('./media-chrome'), { ssr: false });
const Plyr = dynamic(() => import('./plyr'), { ssr: false });
@@ -23,7 +23,7 @@ const PlayerLoader = forwardRef(({ playerToLoad, ...otherProps }, ref) => (
}
.player-border.player-media-chrome {
- padding-bottom: ${(otherProps.streamType === 'live' ? mobileControlBarOffsetLive : mobileControlBarOffsetVod)}px;
+ padding-bottom: ${controlBarHeight}px;
}
.player-border {
@@ -40,7 +40,7 @@ const PlayerLoader = forwardRef(({ playerToLoad, ...otherProps }, ref) => (
@media (min-width: 768px) {
.player-border.player-media-chrome {
- padding-bottom: ${otherProps.streamType === 'live' ? desktopControlBarOffsetLive : desktopControlBarOffsetVod}px;
+ padding-bottom: ${controlBarHeight}px;
}
}
`}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment