feat: Preferences view layout on mobile has been updated, and can be dismissed by swiping from the right

This commit is contained in:
Aman Harwara
2023-05-17 19:42:08 +05:30
parent 7b44224314
commit e5c580deab
18 changed files with 114 additions and 79 deletions

View File

@@ -6,29 +6,32 @@ import { useModalAnimation } from '../Modal/useModalAnimation'
type Props = {
isOpen: boolean
children: ReactNode
animationVariant?: 'horizontal' | 'vertical'
}
const ModalOverlay = forwardRef(({ isOpen, children, ...props }: Props, ref: ForwardedRef<HTMLDivElement>) => {
const [isMounted, setElement] = useModalAnimation(isOpen)
const dialog = useDialogStore({
open: isMounted,
})
const ModalOverlay = forwardRef(
({ isOpen, children, animationVariant, ...props }: Props, ref: ForwardedRef<HTMLDivElement>) => {
const [isMounted, setElement] = useModalAnimation(isOpen, animationVariant)
const dialog = useDialogStore({
open: isMounted,
})
if (!isMounted) {
return null
}
if (!isMounted) {
return null
}
return (
<Dialog
tabIndex={0}
className="fixed top-0 left-0 z-modal h-full w-full"
ref={mergeRefs([setElement, ref])}
store={dialog}
{...props}
>
{children}
</Dialog>
)
})
return (
<Dialog
tabIndex={0}
className="fixed top-0 left-0 z-modal h-full w-full"
ref={mergeRefs([setElement, ref])}
store={dialog}
{...props}
>
{children}
</Dialog>
)
},
)
export default ModalOverlay

View File

@@ -3,49 +3,86 @@ import { useMediaQuery, MutuallyExclusiveMediaQueryBreakpoints } from '@/Hooks/u
export const IosModalAnimationEasing = 'cubic-bezier(.36,.66,.04,1)'
export const useModalAnimation = (isOpen: boolean) => {
const Animations = {
vertical: {
enter: {
keyframes: [
{
transform: 'translateY(100%)',
},
{
transform: 'translateY(0)',
},
],
transformOrigin: 'bottom',
},
exit: {
keyframes: [
{
transform: 'translateY(0)',
},
{
transform: 'translateY(100%)',
},
],
transformOrigin: 'bottom',
},
},
horizontal: {
enter: {
keyframes: [
{
transform: 'translateX(100%)',
},
{
transform: 'translateX(0)',
},
],
transformOrigin: 'right',
},
exit: {
keyframes: [
{
transform: 'translateX(0)',
},
{
transform: 'translateX(100%)',
},
],
transformOrigin: 'right',
},
},
}
export const useModalAnimation = (isOpen: boolean, variant: 'horizontal' | 'vertical' = 'vertical') => {
const isMobileScreen = useMediaQuery(MutuallyExclusiveMediaQueryBreakpoints.sm)
return useLifecycleAnimation(
{
open: isOpen,
enter: {
keyframes: [
{
transform: 'translateY(100%)',
},
{
transform: 'translateY(0)',
},
],
keyframes: Animations[variant].enter.keyframes,
options: {
easing: IosModalAnimationEasing,
duration: 250,
fill: 'forwards',
},
initialStyle: {
transformOrigin: 'bottom',
transformOrigin: Animations[variant].enter.transformOrigin,
},
},
enterCallback: (element) => {
element.scrollTop = 0
},
exit: {
keyframes: [
{
transform: 'translateY(0)',
},
{
transform: 'translateY(100%)',
},
],
keyframes: Animations[variant].exit.keyframes,
options: {
easing: IosModalAnimationEasing,
duration: 250,
fill: 'forwards',
},
initialStyle: {
transformOrigin: 'bottom',
transformOrigin: Animations[variant].exit.transformOrigin,
},
},
},