From 5e433266ee552761477901d6678e43d7d8d42394 Mon Sep 17 00:00:00 2001 From: Jelle van Snik Date: Tue, 7 Feb 2023 18:19:31 +0100 Subject: [PATCH] popout transitions --- src/components/Transition.tsx | 74 ++++++++----------- .../popouts/PopoutProviderAction.tsx | 30 ++++---- 2 files changed, 45 insertions(+), 59 deletions(-) diff --git a/src/components/Transition.tsx b/src/components/Transition.tsx index 85443461..c594038f 100644 --- a/src/components/Transition.tsx +++ b/src/components/Transition.tsx @@ -1,12 +1,14 @@ -import { ReactNode, useRef } from "react"; -import { CSSTransition } from "react-transition-group"; -import { CSSTransitionClassNames } from "react-transition-group/CSSTransition"; +import { ReactNode } from "react"; +import { + Transition as HeadlessTransition, + TransitionClasses, +} from "@headlessui/react"; -type TransitionAnimations = "slide-down" | "slide-up" | "fade" | "fade-inverse"; +type TransitionAnimations = "slide-down" | "slide-up" | "fade"; interface Props { show: boolean; - durationClass?: string; + durationClass?: "duration-200" | string; // default is specified so tailwind doesnt remove the class in prod builds animation: TransitionAnimations; className?: string; children?: ReactNode; @@ -15,44 +17,37 @@ interface Props { function getClasses( animation: TransitionAnimations, duration: number -): CSSTransitionClassNames { +): TransitionClasses { if (animation === "slide-down") { return { - exit: `transition-[transform,opacity] translate-y-0 duration-${duration} opacity-100`, - exitActive: "!-translate-y-4 !opacity-0", - exitDone: "hidden", - enter: `transition-[transform,opacity] -translate-y-4 duration-${duration} opacity-0`, - enterActive: "!translate-y-0 !opacity-100", + leave: `transition-[transform,opacity] duration-${duration}`, + leaveFrom: "opacity-100 translate-y-0", + leaveTo: "-translate-y-4 opacity-0", + enter: `transition-[transform,opacity] duration-${duration}`, + enterFrom: "opacity-0 -translate-y-4", + enterTo: "translate-y-0 opacity-100", }; } if (animation === "slide-up") { return { - exit: `transition-[transform,opacity] translate-y-0 duration-${duration} opacity-100`, - exitActive: "!translate-y-4 !opacity-0", - exitDone: "hidden", - enter: `transition-[transform,opacity] translate-y-4 duration-${duration} opacity-0`, - enterActive: "!translate-y-0 !opacity-100", + leave: `transition-[transform,opacity] duration-${duration}`, + leaveFrom: "opacity-100 translate-y-0", + leaveTo: "translate-y-4 opacity-0", + enter: `transition-[transform,opacity] duration-${duration}`, + enterFrom: "opacity-0 translate-y-4", + enterTo: "translate-y-0 opacity-100", }; } if (animation === "fade") { return { - exit: `transition-[transform,opacity] duration-${duration} opacity-100`, - exitActive: "!opacity-0", - exitDone: "hidden", - enter: `transition-[transform,opacity] duration-${duration} opacity-0`, - enterActive: "!opacity-100", - }; - } - - if (animation === "fade-inverse") { - return { - enter: `transition-[transform,opacity] duration-${duration} opacity-100`, - enterActive: "!opacity-0", - exit: `transition-[transform,opacity] duration-${duration} opacity-0`, - exitActive: "!opacity-100", - enterDone: "hidden", + leave: `transition-[transform,opacity] duration-${duration}`, + leaveFrom: "opacity-100", + leaveTo: "opacity-0", + enter: `transition-[transform,opacity] duration-${duration}`, + enterFrom: "opacity-0", + enterTo: "opacity-100", }; } @@ -60,25 +55,16 @@ function getClasses( } export function Transition(props: Props) { - const ref = useRef(null); const duration = props.durationClass ? parseInt(props.durationClass.split("-")[1], 10) : 200; const classes = getClasses(props.animation, duration); return ( - -
+
+ {props.children} -
- + +
); } diff --git a/src/video/components/popouts/PopoutProviderAction.tsx b/src/video/components/popouts/PopoutProviderAction.tsx index b602fe71..c8bb9345 100644 --- a/src/video/components/popouts/PopoutProviderAction.tsx +++ b/src/video/components/popouts/PopoutProviderAction.tsx @@ -1,3 +1,4 @@ +import { Transition } from "@/components/Transition"; import { EpisodeSelectionPopout } from "@/video/components/popouts/EpisodeSelectionPopout"; import { useVideoPlayerDescriptor } from "@/video/state/hooks"; import { useControls } from "@/video/state/logic/controls"; @@ -6,7 +7,7 @@ import { useCallback, useEffect, useMemo, useState } from "react"; import "./Popouts.css"; -function ShowPopout(props: { popoutId: string }) { +function ShowPopout(props: { popoutId: string | null }) { // only updates popout id when a new one is set, so transitions look good const [popoutId, setPopoutId] = useState(props.popoutId); useEffect(() => { @@ -20,7 +21,6 @@ function ShowPopout(props: { popoutId: string }) { // TODO use new design for popouts // TODO improve anti offscreen math -// TODO in and out transition // TODO attach router history to popout state, so you can use back button to remove popout export function PopoutProviderAction() { const descriptor = useVideoPlayerDescriptor(); @@ -51,20 +51,20 @@ export function PopoutProviderAction() { : "30px"; }, [videoInterface]); - if (!videoInterface.popout) return null; - return ( -
-
-
- + +
+
+
+ +
-
+
); }