diff --git a/package.json b/package.json index f9adcbb6..4cca72a1 100644 --- a/package.json +++ b/package.json @@ -7,7 +7,7 @@ "@analytics/google-tag-manager": "^0.5.3", "@appquality/appquality-design-system": "^1.0.49", "@appquality/craft-blocks": "^0.1.27", - "@appquality/stream-player": "^1.0.4", + "@appquality/stream-player": "^1.0.5", "@craco/craco": "^6.4.3", "@craftjs/core": "^0.2.0-beta.5", "@reduxjs/toolkit": "^1.8.3", diff --git a/src/pages/UxDashboard/UxForm/VideoParts/VideoPart.tsx b/src/pages/UxDashboard/UxForm/VideoParts/VideoPart.tsx index 77596ac6..ce4c886e 100644 --- a/src/pages/UxDashboard/UxForm/VideoParts/VideoPart.tsx +++ b/src/pages/UxDashboard/UxForm/VideoParts/VideoPart.tsx @@ -92,7 +92,11 @@ const VideoPart = ({ form.validateField(field.name); }, }} - value={moment.utc(field.value * 1000).format("HH:mm:ss")} + value={ + !field.value + ? "00:00:00" + : moment.utc(field.value * 1000).format("HH:mm:ss") + } onChange={(value) => { form.setFieldValue( field.name, diff --git a/src/pages/UxDashboard/UxForm/VideoParts/VideoPlayer/index.tsx b/src/pages/UxDashboard/UxForm/VideoParts/VideoPlayer/index.tsx index 6f49cd99..ecc14fac 100644 --- a/src/pages/UxDashboard/UxForm/VideoParts/VideoPlayer/index.tsx +++ b/src/pages/UxDashboard/UxForm/VideoParts/VideoPlayer/index.tsx @@ -1,7 +1,7 @@ import Video from "@appquality/stream-player"; import styled from "styled-components"; import { VideoControls } from "./VideoControls"; -import { useEffect, useRef, useState } from "react"; +import { useCallback, useEffect, useRef, useState } from "react"; const PlayerWrapper = styled.div<{ isFullScreen?: boolean; @@ -15,6 +15,20 @@ const PlayerWrapper = styled.div<{ max-height: 200px; } + ${({ isFullScreen }) => + isFullScreen && + ` + video { + position: absolute; + top: 0; + left: 0; + bottom: 0; + display: block; + margin: 0 auto; + max-height: 100%; + } + `} + ${({ isLoading }) => isLoading && ` @@ -28,35 +42,15 @@ const PlayerWrapper = styled.div<{ } } `} - - ${({ isFullScreen, theme }) => - !isFullScreen && - ` - border-top-left-radius: ${theme.general.borderRadius}; - border-top-right-radius: ${theme.general.borderRadius}; - // from card to list item in desktop - @media (min-width: ${theme.grid.breakpoints.lg}) { - border-top-right-radius: 0; - border-bottom-left-radius: ${theme.general.borderRadius}; - } - `} - - ${({ isFullScreen }) => - isFullScreen && - ` - position: fixed; - top: 0; - left: 0; - width: 100vw; - height: 100vh; - background-color: black; - z-index: 1000; - video { - max-height: 100vh; - } - `} `; +interface ElementWithFullscreen extends HTMLDivElement { + webkitEnterFullscreen?: () => Promise; + webkitRequestFullscreen?: () => Promise; + mozRequestFullScreen?: () => Promise; + msRequestFullscreen?: () => Promise; +} + const VideoPlayer = ({ videoFieldName, title, @@ -68,6 +62,51 @@ const VideoPlayer = ({ const [isLoading, setIsLoading] = useState(true); const playerRef = useRef(null); + const handleFullScreen = useCallback(async () => { + if (playerRef) { + const ref = playerRef.current as ElementWithFullscreen; + if (!isFullScreen || !document.fullscreenElement) { + setFullScreen(true); + if (ref.requestFullscreen) { + await ref.requestFullscreen(); + } else if (ref.webkitRequestFullscreen) { + await ref.webkitRequestFullscreen(); + } else if (ref.mozRequestFullScreen) { + await ref.mozRequestFullScreen(); + } else if (ref.webkitEnterFullscreen) { + // iOS + await ref.webkitEnterFullscreen(); + } else if (ref.msRequestFullscreen) { + await ref.msRequestFullscreen(); + } else { + console.error("Fullscreen API is not supported"); + setFullScreen(false); + } + } else { + if (document.fullscreenElement) { + await document.exitFullscreen(); + } + setFullScreen(false); + } + } + }, [playerRef, isFullScreen]); + + useEffect(() => { + if (playerRef && playerRef.current) { + playerRef.current.addEventListener("fullscreenchange", () => { + setFullScreen(!!document.fullscreenElement); + }); + } + + return () => { + if (playerRef && playerRef.current) { + playerRef.current.removeEventListener("fullscreenchange", () => { + setFullScreen(!!document.fullscreenElement); + }); + } + }; + }, [playerRef]); + useEffect(() => { playerRef.current ?.querySelector("video") @@ -87,7 +126,7 @@ const VideoPlayer = ({ videoFieldName={videoFieldName} title={title} isFullScreen={isFullScreen} - setFullScreen={setFullScreen} + setFullScreen={handleFullScreen} /> )} diff --git a/yarn.lock b/yarn.lock index d3ad474b..bb40a04c 100644 --- a/yarn.lock +++ b/yarn.lock @@ -137,10 +137,10 @@ resolved "https://registry.npmjs.org/@appquality/mobiscroll/-/mobiscroll-5.10.1.tgz" integrity sha512-A9YVu/5aFcmd6WtLEfr//x20mV5w9O3X5nsooYW43HMdfrx1fKcPfarCk9fHyyov1h0S9DdrzR7Dl/sciL7usA== -"@appquality/stream-player@^1.0.4": - version "1.0.4" - resolved "https://registry.yarnpkg.com/@appquality/stream-player/-/stream-player-1.0.4.tgz#d1a87be1e04f25b39a539b9eff2e8aa0b38627df" - integrity sha512-RMhzbf9uDLCWIHwVQf5LSOYbenrM/RNQkCSjtayrRBj4pcVs42gvnIa0TgPflZDEFL/jxTHthu1eL0U2NhKxWg== +"@appquality/stream-player@^1.0.5": + version "1.0.5" + resolved "https://registry.yarnpkg.com/@appquality/stream-player/-/stream-player-1.0.5.tgz#aeb0996f166e671d53aba937df4f2c50867f6bac" + integrity sha512-HhRIyF3fAyHvysRL6jhzc/G85yDpIVOxqEvZrygRneG5Ama+sErPkTjUOW8vdgW9YQElXtdGUI3aLZl9iLBmxQ== dependencies: hls.js "^1.4.8"