import { AnimatePresence, motion } from 'framer-motion'
import React, { useEffect, useState } from 'react'
import { ModalStack, useModals } from '../src'
export default {
title: 'Animated',
decorators: [
(Story) => (
),
],
}
export const FramerMotion = () => {
const { openModal } = useModals()
return (
)
}
function AnimatedModals({ stack }) {
// the "displayed" stack which will be a lagged version of stack
// in order to animate the transitions between modals
const [displayedStack, setDisplayedStack] = useState(stack)
// track the "open" state manually so we can dismiss the
// top modal before popping it off the stack
const [isOpen, setOpen] = useState(false)
useEffect(() => {
// we're opening the first modal, so update the stack right away
if (stack.length === 1 && displayedStack.length === 0) {
setOpen(true)
setDisplayedStack(stack)
}
// stack updated, trigger a dismissal of the current modal
else {
setOpen(false)
}
}, [stack])
return (
<>
{stack.length > 0 && (
)}
{displayedStack.map((modal, index) => (
{
// set open state for next modal
if (stack.length > 0) {
setOpen(true)
} else {
setOpen(false)
}
// update displayed stack
// setTimeout is a hack to prevent a warning about updating state
// in an unmounted component (I can't figure out why it happens, or why this fixes it)
setTimeout(() => setDisplayedStack(stack))
modal.props?.onAnimationComplete?.()
}}
{...modal.props}
/>
))}
>
)
}
type AnimatedModalProps = {
open: boolean
title?: string
message?: string
}
function AnimatedModal({
open,
message = `I'm modal #1`,
title = 'Hello',
...props
}: AnimatedModalProps) {
const { stack, openModal, closeModal } = useModals()
const [value, setValue] = useState('')
return (
{open && (