Merged in feat/sw-3238-move-modal-to-design-system (pull request #2628)
feat(SW-3238): Move modal to design system * Move Modal to design-system * Remove temp modal from booking-flow Approved-by: Joakim Jäderberg
This commit is contained in:
@@ -18,12 +18,11 @@ import { useIntl } from "react-intl"
|
|||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
import Image from "@scandic-hotels/design-system/Image"
|
import Image from "@scandic-hotels/design-system/Image"
|
||||||
import { Input } from "@scandic-hotels/design-system/Input"
|
import { Input } from "@scandic-hotels/design-system/Input"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { SAS_TRANSFER_POINT_KEY } from "@scandic-hotels/trpc/constants/partnerSAS"
|
import { SAS_TRANSFER_POINT_KEY } from "@scandic-hotels/trpc/constants/partnerSAS"
|
||||||
|
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
|
|
||||||
import styles from "./transferPoints.module.css"
|
import styles from "./transferPoints.module.css"
|
||||||
|
|
||||||
import type { Lang } from "@scandic-hotels/common/constants/language"
|
import type { Lang } from "@scandic-hotels/common/constants/language"
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
|||||||
import { Button } from "@scandic-hotels/design-system/Button"
|
import { Button } from "@scandic-hotels/design-system/Button"
|
||||||
import { Divider } from "@scandic-hotels/design-system/Divider"
|
import { Divider } from "@scandic-hotels/design-system/Divider"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { ChildBedTypeEnum } from "@scandic-hotels/trpc/enums/childBedTypeEnum"
|
import { ChildBedTypeEnum } from "@scandic-hotels/trpc/enums/childBedTypeEnum"
|
||||||
|
|
||||||
@@ -14,7 +15,6 @@ import { CancellationRuleEnum } from "@/constants/booking"
|
|||||||
import { useBookingConfirmationStore } from "@/stores/booking-confirmation"
|
import { useBookingConfirmationStore } from "@/stores/booking-confirmation"
|
||||||
|
|
||||||
import { getFeatureDescription } from "@/components/HotelReservation/utils/getRoomFeatureDescription"
|
import { getFeatureDescription } from "@/components/HotelReservation/utils/getRoomFeatureDescription"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
|
|
||||||
import Breakfast from "./Breakfast"
|
import Breakfast from "./Breakfast"
|
||||||
import RoomSkeletonLoader from "./RoomSkeletonLoader"
|
import RoomSkeletonLoader from "./RoomSkeletonLoader"
|
||||||
|
|||||||
@@ -8,11 +8,11 @@ import { CurrencyEnum } from "@scandic-hotels/common/constants/currency"
|
|||||||
import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
||||||
import Body from "@scandic-hotels/design-system/Body"
|
import Body from "@scandic-hotels/design-system/Body"
|
||||||
import MagicWandIcon from "@scandic-hotels/design-system/Icons/MagicWandIcon"
|
import MagicWandIcon from "@scandic-hotels/design-system/Icons/MagicWandIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
||||||
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
||||||
import Title from "@scandic-hotels/design-system/Title"
|
import Title from "@scandic-hotels/design-system/Title"
|
||||||
|
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import { useRoomContext } from "@/contexts/Details/Room"
|
import { useRoomContext } from "@/contexts/Details/Room"
|
||||||
|
|
||||||
import styles from "./modal.module.css"
|
import styles from "./modal.module.css"
|
||||||
|
|||||||
@@ -5,11 +5,11 @@ import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
|||||||
import { Button } from "@scandic-hotels/design-system/Button"
|
import { Button } from "@scandic-hotels/design-system/Button"
|
||||||
import { Divider } from "@scandic-hotels/design-system/Divider"
|
import { Divider } from "@scandic-hotels/design-system/Divider"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { ChildBedMapEnum } from "@scandic-hotels/trpc/enums/childBedMapEnum"
|
import { ChildBedMapEnum } from "@scandic-hotels/trpc/enums/childBedMapEnum"
|
||||||
|
|
||||||
import { getFeatureDescription } from "@/components/HotelReservation/utils/getRoomFeatureDescription"
|
import { getFeatureDescription } from "@/components/HotelReservation/utils/getRoomFeatureDescription"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
|
|
||||||
import { getMemberPrice, getPublicPrice } from "../utils"
|
import { getMemberPrice, getPublicPrice } from "../utils"
|
||||||
import Breakfast from "./Breakfast"
|
import Breakfast from "./Breakfast"
|
||||||
|
|||||||
@@ -11,6 +11,7 @@ import { guaranteeCallback } from "@scandic-hotels/common/constants/routes/hotel
|
|||||||
import { dt } from "@scandic-hotels/common/dt"
|
import { dt } from "@scandic-hotels/common/dt"
|
||||||
import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
||||||
import { Divider } from "@scandic-hotels/design-system/Divider"
|
import { Divider } from "@scandic-hotels/design-system/Divider"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { trpc } from "@scandic-hotels/trpc/client"
|
import { trpc } from "@scandic-hotels/trpc/client"
|
||||||
import { BreakfastPackageEnum } from "@scandic-hotels/trpc/enums/breakfast"
|
import { BreakfastPackageEnum } from "@scandic-hotels/trpc/enums/breakfast"
|
||||||
@@ -30,7 +31,6 @@ import {
|
|||||||
setAncillarySessionData,
|
setAncillarySessionData,
|
||||||
} from "@/components/HotelReservation/MyStay/utils/ancillaries"
|
} from "@/components/HotelReservation/MyStay/utils/ancillaries"
|
||||||
import LoadingSpinner from "@/components/LoadingSpinner"
|
import LoadingSpinner from "@/components/LoadingSpinner"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import { toast } from "@/components/TempDesignSystem/Toasts"
|
import { toast } from "@/components/TempDesignSystem/Toasts"
|
||||||
import { useGuaranteeBooking } from "@/hooks/booking/useGuaranteeBooking"
|
import { useGuaranteeBooking } from "@/hooks/booking/useGuaranteeBooking"
|
||||||
import useLang from "@/hooks/useLang"
|
import useLang from "@/hooks/useLang"
|
||||||
|
|||||||
@@ -8,6 +8,8 @@ import { useIntl } from "react-intl"
|
|||||||
|
|
||||||
import { profileEdit } from "@scandic-hotels/common/constants/routes/myPages"
|
import { profileEdit } from "@scandic-hotels/common/constants/routes/myPages"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
|
import { ModalContentWithActions } from "@scandic-hotels/design-system/Modal/ModalContentWithActions"
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { trpc } from "@scandic-hotels/trpc/client"
|
import { trpc } from "@scandic-hotels/trpc/client"
|
||||||
@@ -15,8 +17,6 @@ import { trpc } from "@scandic-hotels/trpc/client"
|
|||||||
import { isWebview } from "@/constants/routes/webviews"
|
import { isWebview } from "@/constants/routes/webviews"
|
||||||
|
|
||||||
import MembershipLevelIcon from "@/components/Levels/Icon"
|
import MembershipLevelIcon from "@/components/Levels/Icon"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import { ModalContentWithActions } from "@/components/Modal/ModalContentWithActions"
|
|
||||||
import { toast } from "@/components/TempDesignSystem/Toasts"
|
import { toast } from "@/components/TempDesignSystem/Toasts"
|
||||||
import useLang from "@/hooks/useLang"
|
import useLang from "@/hooks/useLang"
|
||||||
|
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import { IconButton } from "@scandic-hotels/design-system/IconButton"
|
|||||||
import IconChip from "@scandic-hotels/design-system/IconChip"
|
import IconChip from "@scandic-hotels/design-system/IconChip"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
import Image from "@scandic-hotels/design-system/Image"
|
import Image from "@scandic-hotels/design-system/Image"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { RateEnum } from "@scandic-hotels/trpc/enums/rate"
|
import { RateEnum } from "@scandic-hotels/trpc/enums/rate"
|
||||||
import { RoomPackageCodeEnum } from "@scandic-hotels/trpc/enums/roomFilter"
|
import { RoomPackageCodeEnum } from "@scandic-hotels/trpc/enums/roomFilter"
|
||||||
@@ -16,7 +17,6 @@ import { RoomPackageCodeEnum } from "@scandic-hotels/trpc/enums/roomFilter"
|
|||||||
import { CancellationRuleEnum } from "@/constants/booking"
|
import { CancellationRuleEnum } from "@/constants/booking"
|
||||||
|
|
||||||
import { IconForFeatureCode } from "@/components/HotelReservation/utils"
|
import { IconForFeatureCode } from "@/components/HotelReservation/utils"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import useRateTitles from "@/hooks/booking/useRateTitles"
|
import useRateTitles from "@/hooks/booking/useRateTitles"
|
||||||
import useLang from "@/hooks/useLang"
|
import useLang from "@/hooks/useLang"
|
||||||
|
|
||||||
|
|||||||
@@ -2,13 +2,13 @@ import { useIntl } from "react-intl"
|
|||||||
|
|
||||||
import { IconButton } from "@scandic-hotels/design-system/IconButton"
|
import { IconButton } from "@scandic-hotels/design-system/IconButton"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { RateEnum } from "@scandic-hotels/trpc/enums/rate"
|
import { RateEnum } from "@scandic-hotels/trpc/enums/rate"
|
||||||
|
|
||||||
import { CancellationRuleEnum } from "@/constants/booking"
|
import { CancellationRuleEnum } from "@/constants/booking"
|
||||||
import { useMyStayStore } from "@/stores/my-stay"
|
import { useMyStayStore } from "@/stores/my-stay"
|
||||||
|
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import useRateTitles from "@/hooks/booking/useRateTitles"
|
import useRateTitles from "@/hooks/booking/useRateTitles"
|
||||||
|
|
||||||
import Row from "../Row"
|
import Row from "../Row"
|
||||||
|
|||||||
@@ -3,8 +3,7 @@ import { useIntl } from "react-intl"
|
|||||||
|
|
||||||
import { Button } from "@scandic-hotels/design-system/Button"
|
import { Button } from "@scandic-hotels/design-system/Button"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
|
|
||||||
import PriceDetailsTable, {
|
import PriceDetailsTable, {
|
||||||
type PriceDetailsTableProps,
|
type PriceDetailsTableProps,
|
||||||
|
|||||||
@@ -5,11 +5,10 @@ import { formatPrice } from "@scandic-hotels/common/utils/numberFormatting"
|
|||||||
import { Button } from "@scandic-hotels/design-system/Button"
|
import { Button } from "@scandic-hotels/design-system/Button"
|
||||||
import { Divider } from "@scandic-hotels/design-system/Divider"
|
import { Divider } from "@scandic-hotels/design-system/Divider"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { ChildBedMapEnum } from "@scandic-hotels/trpc/enums/childBedMapEnum"
|
import { ChildBedMapEnum } from "@scandic-hotels/trpc/enums/childBedMapEnum"
|
||||||
|
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
|
|
||||||
import { isBookingCodeRate } from "../../utils"
|
import { isBookingCodeRate } from "../../utils"
|
||||||
import { getMemberPrice } from "../utils"
|
import { getMemberPrice } from "../utils"
|
||||||
|
|
||||||
|
|||||||
@@ -1,36 +0,0 @@
|
|||||||
import type { Dispatch, JSX, SetStateAction } from "react"
|
|
||||||
|
|
||||||
export enum AnimationStateEnum {
|
|
||||||
unmounted = "unmounted",
|
|
||||||
hidden = "hidden",
|
|
||||||
visible = "visible",
|
|
||||||
}
|
|
||||||
|
|
||||||
export type AnimationState = keyof typeof AnimationStateEnum
|
|
||||||
|
|
||||||
export type ModalProps = {
|
|
||||||
onAnimationComplete?: () => void
|
|
||||||
title?: string
|
|
||||||
subtitle?: string
|
|
||||||
withActions?: boolean
|
|
||||||
hideHeader?: boolean
|
|
||||||
className?: string
|
|
||||||
} & (
|
|
||||||
| {
|
|
||||||
trigger: JSX.Element
|
|
||||||
isOpen?: never
|
|
||||||
onToggle?: never
|
|
||||||
onOpenChange?: (open: boolean) => void
|
|
||||||
}
|
|
||||||
| {
|
|
||||||
trigger?: never
|
|
||||||
isOpen: boolean
|
|
||||||
onToggle: (open: boolean) => void
|
|
||||||
onOpenChange?: never
|
|
||||||
}
|
|
||||||
)
|
|
||||||
|
|
||||||
export type InnerModalProps = Omit<ModalProps, "trigger"> & {
|
|
||||||
animation: AnimationState
|
|
||||||
setAnimation: Dispatch<SetStateAction<AnimationState>>
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
export const fade = {
|
|
||||||
hidden: {
|
|
||||||
opacity: 0,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
visible: {
|
|
||||||
opacity: 1,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
export const slideInOut = {
|
|
||||||
hidden: {
|
|
||||||
opacity: 0,
|
|
||||||
y: 32,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
visible: {
|
|
||||||
opacity: 1,
|
|
||||||
y: 0,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
}
|
|
||||||
@@ -4,9 +4,9 @@ import { useIntl } from "react-intl"
|
|||||||
|
|
||||||
import ButtonLink from "@scandic-hotels/design-system/ButtonLink"
|
import ButtonLink from "@scandic-hotels/design-system/ButtonLink"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
|
|
||||||
import Modal from "@/components/Modal"
|
|
||||||
import useWakeLock from "@/hooks/useWakeLock"
|
import useWakeLock from "@/hooks/useWakeLock"
|
||||||
|
|
||||||
import DigitalTeamMemberCardContent from "./Content"
|
import DigitalTeamMemberCardContent from "./Content"
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import Body from "@scandic-hotels/design-system/Body"
|
|||||||
import Caption from "@scandic-hotels/design-system/Caption"
|
import Caption from "@scandic-hotels/design-system/Caption"
|
||||||
import Checkbox from "@scandic-hotels/design-system/Form/Checkbox"
|
import Checkbox from "@scandic-hotels/design-system/Form/Checkbox"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import {
|
import {
|
||||||
type ButtonProps,
|
type ButtonProps,
|
||||||
OldDSButton as Button,
|
OldDSButton as Button,
|
||||||
@@ -18,7 +19,6 @@ import { SEARCH_TYPE_REDEMPTION } from "@scandic-hotels/trpc/constants/booking"
|
|||||||
|
|
||||||
import BookingFlowInput from "../../../../BookingFlowInput"
|
import BookingFlowInput from "../../../../BookingFlowInput"
|
||||||
import { getErrorMessage } from "../../../../BookingFlowInput/errors"
|
import { getErrorMessage } from "../../../../BookingFlowInput/errors"
|
||||||
import Modal from "../../../../TEMP/Modal"
|
|
||||||
import { Input as BookingWidgetInput } from "../Input"
|
import { Input as BookingWidgetInput } from "../Input"
|
||||||
import { isMultiRoomError } from "../utils"
|
import { isMultiRoomError } from "../utils"
|
||||||
|
|
||||||
|
|||||||
@@ -8,12 +8,12 @@ import { useMediaQuery } from "usehooks-ts"
|
|||||||
import Caption from "@scandic-hotels/design-system/Caption"
|
import Caption from "@scandic-hotels/design-system/Caption"
|
||||||
import Checkbox from "@scandic-hotels/design-system/Form/Checkbox"
|
import Checkbox from "@scandic-hotels/design-system/Form/Checkbox"
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
||||||
|
import Modal from "@scandic-hotels/design-system/Modal"
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
||||||
import { Typography } from "@scandic-hotels/design-system/Typography"
|
import { Typography } from "@scandic-hotels/design-system/Typography"
|
||||||
import { SEARCH_TYPE_REDEMPTION } from "@scandic-hotels/trpc/constants/booking"
|
import { SEARCH_TYPE_REDEMPTION } from "@scandic-hotels/trpc/constants/booking"
|
||||||
|
|
||||||
import { getErrorMessage } from "../../../../BookingFlowInput/errors"
|
import { getErrorMessage } from "../../../../BookingFlowInput/errors"
|
||||||
import Modal from "../../../../TEMP/Modal"
|
|
||||||
import { RemoveExtraRooms } from "../BookingCode"
|
import { RemoveExtraRooms } from "../BookingCode"
|
||||||
import { isMultiRoomError } from "../utils"
|
import { isMultiRoomError } from "../utils"
|
||||||
|
|
||||||
|
|||||||
@@ -1,69 +0,0 @@
|
|||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
|
||||||
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
|
||||||
|
|
||||||
import styles from "./modalContent.module.css"
|
|
||||||
|
|
||||||
import type { ReactNode } from "react"
|
|
||||||
|
|
||||||
interface ModalContentProps {
|
|
||||||
title?: string
|
|
||||||
content: ReactNode
|
|
||||||
primaryAction: {
|
|
||||||
label: string
|
|
||||||
onClick: () => void
|
|
||||||
intent?: "primary" | "secondary" | "text"
|
|
||||||
isLoading?: boolean
|
|
||||||
disabled?: boolean
|
|
||||||
} | null
|
|
||||||
secondaryAction: {
|
|
||||||
label: string
|
|
||||||
onClick: () => void
|
|
||||||
intent?: "primary" | "secondary" | "text"
|
|
||||||
} | null
|
|
||||||
onClose?: () => void
|
|
||||||
}
|
|
||||||
|
|
||||||
export function ModalContentWithActions({
|
|
||||||
title,
|
|
||||||
content,
|
|
||||||
primaryAction,
|
|
||||||
secondaryAction,
|
|
||||||
onClose,
|
|
||||||
}: ModalContentProps) {
|
|
||||||
return (
|
|
||||||
<>
|
|
||||||
{title && (
|
|
||||||
<header className={styles.header}>
|
|
||||||
<Subtitle>{title}</Subtitle>
|
|
||||||
<button onClick={onClose} type="button" className={styles.close}>
|
|
||||||
<MaterialIcon icon="close" color="Icon/Interactive/Placeholder" />
|
|
||||||
</button>
|
|
||||||
</header>
|
|
||||||
)}
|
|
||||||
<div className={styles.content}>{content}</div>
|
|
||||||
<footer className={styles.footer}>
|
|
||||||
{secondaryAction && (
|
|
||||||
<Button
|
|
||||||
theme="base"
|
|
||||||
intent={secondaryAction.intent ?? "text"}
|
|
||||||
color="burgundy"
|
|
||||||
onClick={secondaryAction.onClick}
|
|
||||||
>
|
|
||||||
{secondaryAction.label}
|
|
||||||
</Button>
|
|
||||||
)}
|
|
||||||
{primaryAction && (
|
|
||||||
<Button
|
|
||||||
theme="base"
|
|
||||||
intent={primaryAction.intent ?? "secondary"}
|
|
||||||
onClick={primaryAction.onClick}
|
|
||||||
disabled={primaryAction.isLoading || primaryAction.disabled}
|
|
||||||
>
|
|
||||||
{primaryAction.label}
|
|
||||||
</Button>
|
|
||||||
)}
|
|
||||||
</footer>
|
|
||||||
</>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,45 +0,0 @@
|
|||||||
.content {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
gap: var(--Spacing-x3);
|
|
||||||
padding: var(--Spacing-x1) var(--Spacing-x3) var(--Spacing-x4);
|
|
||||||
max-height: 70vh;
|
|
||||||
overflow-y: auto;
|
|
||||||
width: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.header {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-between;
|
|
||||||
width: 100%;
|
|
||||||
padding: var(--Spacing-x3) var(--Spacing-x3) var(--Spacing-x1)
|
|
||||||
var(--Spacing-x3);
|
|
||||||
}
|
|
||||||
|
|
||||||
.footer {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-between;
|
|
||||||
width: 100%;
|
|
||||||
border-top: 1px solid var(--Base-Border-Subtle);
|
|
||||||
padding: var(--Spacing-x3);
|
|
||||||
}
|
|
||||||
|
|
||||||
.close {
|
|
||||||
background: none;
|
|
||||||
border: none;
|
|
||||||
cursor: pointer;
|
|
||||||
position: absolute;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
padding: 0;
|
|
||||||
justify-content: center;
|
|
||||||
top: 20px;
|
|
||||||
right: 20px;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media screen and (min-width: 768px) {
|
|
||||||
.content {
|
|
||||||
width: 640px;
|
|
||||||
max-width: 100%;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,215 +0,0 @@
|
|||||||
"use client"
|
|
||||||
|
|
||||||
// TODO this is duplicated from scandic-web
|
|
||||||
|
|
||||||
import { cx } from "class-variance-authority"
|
|
||||||
import { AnimatePresence, motion } from "motion/react"
|
|
||||||
import { type PropsWithChildren, useEffect, useState } from "react"
|
|
||||||
import {
|
|
||||||
Dialog,
|
|
||||||
DialogTrigger,
|
|
||||||
Modal as AriaModal,
|
|
||||||
ModalOverlay,
|
|
||||||
} from "react-aria-components"
|
|
||||||
import { useIntl } from "react-intl"
|
|
||||||
|
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
|
||||||
import Preamble from "@scandic-hotels/design-system/Preamble"
|
|
||||||
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
|
||||||
|
|
||||||
import {
|
|
||||||
type AnimationState,
|
|
||||||
AnimationStateEnum,
|
|
||||||
type InnerModalProps,
|
|
||||||
type ModalProps,
|
|
||||||
} from "./modal"
|
|
||||||
import { fade, slideInOut } from "./motionVariants"
|
|
||||||
import { modalContentVariants } from "./variants"
|
|
||||||
|
|
||||||
import styles from "./modal.module.css"
|
|
||||||
|
|
||||||
const MotionOverlay = motion.create(ModalOverlay)
|
|
||||||
const MotionModal = motion.create(AriaModal)
|
|
||||||
|
|
||||||
function InnerModal({
|
|
||||||
animation,
|
|
||||||
onAnimationComplete = () => undefined,
|
|
||||||
setAnimation,
|
|
||||||
onToggle,
|
|
||||||
isOpen,
|
|
||||||
children,
|
|
||||||
title,
|
|
||||||
subtitle,
|
|
||||||
withActions,
|
|
||||||
hideHeader,
|
|
||||||
className,
|
|
||||||
}: PropsWithChildren<InnerModalProps>) {
|
|
||||||
const intl = useIntl()
|
|
||||||
|
|
||||||
const contentClassNames = modalContentVariants({
|
|
||||||
withActions: withActions,
|
|
||||||
})
|
|
||||||
|
|
||||||
function modalStateHandler(newAnimationState: AnimationState) {
|
|
||||||
setAnimation((currentAnimationState) =>
|
|
||||||
newAnimationState === AnimationStateEnum.hidden &&
|
|
||||||
currentAnimationState === AnimationStateEnum.hidden
|
|
||||||
? AnimationStateEnum.unmounted
|
|
||||||
: currentAnimationState
|
|
||||||
)
|
|
||||||
if (newAnimationState === AnimationStateEnum.visible) {
|
|
||||||
onAnimationComplete()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function onOpenChange(state: boolean) {
|
|
||||||
onToggle!(state)
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<MotionOverlay
|
|
||||||
animate={animation}
|
|
||||||
className={styles.overlay}
|
|
||||||
initial="hidden"
|
|
||||||
isDismissable
|
|
||||||
// TODO: Enabling this causes the modal to never unmount.
|
|
||||||
// Seems to be an issue with react-aria-components, see https://github.com/adobe/react-spectrum/issues/7563.
|
|
||||||
// Exit animations can probably be fixed by rewriting to a solution similar to
|
|
||||||
// https://react-spectrum.adobe.com/react-aria/examples/framer-modal-sheet.html.
|
|
||||||
// isExiting={animation === AnimationStateEnum.hidden}
|
|
||||||
onAnimationComplete={modalStateHandler}
|
|
||||||
variants={fade}
|
|
||||||
isOpen={isOpen}
|
|
||||||
onOpenChange={onOpenChange}
|
|
||||||
>
|
|
||||||
<MotionModal
|
|
||||||
className={cx(styles.modal, className)}
|
|
||||||
variants={slideInOut}
|
|
||||||
animate={animation}
|
|
||||||
initial="hidden"
|
|
||||||
>
|
|
||||||
<Dialog
|
|
||||||
className={styles.dialog}
|
|
||||||
aria-label={intl.formatMessage({
|
|
||||||
defaultMessage: "Dialog",
|
|
||||||
})}
|
|
||||||
>
|
|
||||||
{({ close }) => (
|
|
||||||
<>
|
|
||||||
{!hideHeader && (
|
|
||||||
<header
|
|
||||||
className={`${styles.header} ${!subtitle ? styles.verticalCenter : ""}`}
|
|
||||||
>
|
|
||||||
<div>
|
|
||||||
{title && (
|
|
||||||
<Subtitle type="one" color="uiTextHighContrast">
|
|
||||||
{title}
|
|
||||||
</Subtitle>
|
|
||||||
)}
|
|
||||||
{subtitle && (
|
|
||||||
<Preamble asChild>
|
|
||||||
<span>{subtitle}</span>
|
|
||||||
</Preamble>
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<button
|
|
||||||
onClick={close}
|
|
||||||
type="button"
|
|
||||||
className={styles.close}
|
|
||||||
>
|
|
||||||
<MaterialIcon icon="close" color="Icon/Feedback/Neutral" />
|
|
||||||
</button>
|
|
||||||
</header>
|
|
||||||
)}
|
|
||||||
|
|
||||||
<div className={contentClassNames}>{children}</div>
|
|
||||||
</>
|
|
||||||
)}
|
|
||||||
</Dialog>
|
|
||||||
</MotionModal>
|
|
||||||
</MotionOverlay>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
export default function Modal({
|
|
||||||
onAnimationComplete = () => undefined,
|
|
||||||
trigger,
|
|
||||||
isOpen,
|
|
||||||
onToggle,
|
|
||||||
onOpenChange,
|
|
||||||
title,
|
|
||||||
subtitle,
|
|
||||||
children,
|
|
||||||
withActions = false,
|
|
||||||
hideHeader = false,
|
|
||||||
className = "",
|
|
||||||
}: PropsWithChildren<ModalProps>) {
|
|
||||||
const [animation, setAnimation] = useState<AnimationState>(
|
|
||||||
AnimationStateEnum.visible
|
|
||||||
)
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
if (typeof isOpen === "boolean") {
|
|
||||||
setAnimation(
|
|
||||||
isOpen ? AnimationStateEnum.visible : AnimationStateEnum.hidden
|
|
||||||
)
|
|
||||||
}
|
|
||||||
if (isOpen === undefined) {
|
|
||||||
setAnimation(AnimationStateEnum.unmounted)
|
|
||||||
}
|
|
||||||
}, [isOpen])
|
|
||||||
|
|
||||||
const shouldRender = isOpen || animation !== AnimationStateEnum.unmounted
|
|
||||||
|
|
||||||
if (!trigger) {
|
|
||||||
return (
|
|
||||||
<AnimatePresence>
|
|
||||||
{shouldRender && (
|
|
||||||
<InnerModal
|
|
||||||
onAnimationComplete={onAnimationComplete}
|
|
||||||
animation={animation}
|
|
||||||
setAnimation={setAnimation}
|
|
||||||
onToggle={onToggle}
|
|
||||||
isOpen={isOpen}
|
|
||||||
title={title}
|
|
||||||
subtitle={subtitle}
|
|
||||||
withActions={withActions}
|
|
||||||
hideHeader={hideHeader}
|
|
||||||
className={className}
|
|
||||||
>
|
|
||||||
{children}
|
|
||||||
</InnerModal>
|
|
||||||
)}
|
|
||||||
</AnimatePresence>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<DialogTrigger
|
|
||||||
onOpenChange={(isOpen) => {
|
|
||||||
setAnimation(
|
|
||||||
isOpen ? AnimationStateEnum.visible : AnimationStateEnum.hidden
|
|
||||||
)
|
|
||||||
onOpenChange?.(isOpen)
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
{trigger}
|
|
||||||
<AnimatePresence>
|
|
||||||
{shouldRender && (
|
|
||||||
<InnerModal
|
|
||||||
onAnimationComplete={onAnimationComplete}
|
|
||||||
animation={animation}
|
|
||||||
setAnimation={setAnimation}
|
|
||||||
title={title}
|
|
||||||
subtitle={subtitle}
|
|
||||||
withActions={withActions}
|
|
||||||
className={className}
|
|
||||||
>
|
|
||||||
{children}
|
|
||||||
</InnerModal>
|
|
||||||
)}
|
|
||||||
</AnimatePresence>
|
|
||||||
</DialogTrigger>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
@@ -1,95 +0,0 @@
|
|||||||
.overlay {
|
|
||||||
background: rgba(0, 0, 0, 0.5);
|
|
||||||
height: var(--visual-viewport-height);
|
|
||||||
position: fixed;
|
|
||||||
top: 0;
|
|
||||||
left: 0;
|
|
||||||
width: 100vw;
|
|
||||||
z-index: var(--default-modal-overlay-z-index);
|
|
||||||
}
|
|
||||||
|
|
||||||
.modal {
|
|
||||||
background-color: var(--Base-Surface-Primary-light-Normal);
|
|
||||||
border-radius: var(--Corner-radius-md) var(--Corner-radius-md) 0 0;
|
|
||||||
box-shadow: var(--modal-box-shadow);
|
|
||||||
width: 100%;
|
|
||||||
position: absolute;
|
|
||||||
left: 0;
|
|
||||||
bottom: 0;
|
|
||||||
z-index: var(--default-modal-z-index);
|
|
||||||
}
|
|
||||||
|
|
||||||
.dialog {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
|
|
||||||
/* For removing focus outline when modal opens first time */
|
|
||||||
outline: 0 none;
|
|
||||||
|
|
||||||
max-height: 100dvh;
|
|
||||||
}
|
|
||||||
|
|
||||||
.header {
|
|
||||||
--button-dimension: 32px;
|
|
||||||
|
|
||||||
box-sizing: content-box;
|
|
||||||
display: flex;
|
|
||||||
align-items: flex-start;
|
|
||||||
min-height: var(--button-dimension);
|
|
||||||
position: relative;
|
|
||||||
padding: var(--Spacing-x3) var(--Spacing-x3) 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.content {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: center;
|
|
||||||
gap: var(--Spacing-x2);
|
|
||||||
overflow: auto;
|
|
||||||
}
|
|
||||||
|
|
||||||
.contentWithActions {
|
|
||||||
padding: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.contentWithoutActions {
|
|
||||||
padding: 0 var(--Spacing-x3) var(--Spacing-x4);
|
|
||||||
}
|
|
||||||
|
|
||||||
.close {
|
|
||||||
background: none;
|
|
||||||
border: none;
|
|
||||||
cursor: pointer;
|
|
||||||
position: absolute;
|
|
||||||
right: var(--Spacing-x2);
|
|
||||||
width: var(--button-dimension);
|
|
||||||
height: var(--button-dimension);
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
padding: 0;
|
|
||||||
justify-content: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.verticalCenter {
|
|
||||||
align-items: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
@media screen and (min-width: 768px) {
|
|
||||||
.overlay {
|
|
||||||
display: flex;
|
|
||||||
justify-content: center;
|
|
||||||
align-items: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
.modal {
|
|
||||||
left: auto;
|
|
||||||
bottom: auto;
|
|
||||||
width: auto;
|
|
||||||
border-radius: var(--Corner-radius-md);
|
|
||||||
max-width: var(--max-width-page);
|
|
||||||
}
|
|
||||||
|
|
||||||
.dialog {
|
|
||||||
max-height: 90dvh;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,23 +0,0 @@
|
|||||||
export const fade = {
|
|
||||||
hidden: {
|
|
||||||
opacity: 0,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
visible: {
|
|
||||||
opacity: 1,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
export const slideInOut = {
|
|
||||||
hidden: {
|
|
||||||
opacity: 0,
|
|
||||||
y: 32,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
visible: {
|
|
||||||
opacity: 1,
|
|
||||||
y: 0,
|
|
||||||
transition: { duration: 0.4, ease: "easeInOut" },
|
|
||||||
},
|
|
||||||
}
|
|
||||||
@@ -1,17 +0,0 @@
|
|||||||
import { cva } from "class-variance-authority"
|
|
||||||
|
|
||||||
import styles from "./modal.module.css"
|
|
||||||
|
|
||||||
const config = {
|
|
||||||
variants: {
|
|
||||||
withActions: {
|
|
||||||
true: styles.contentWithActions,
|
|
||||||
false: styles.contentWithoutActions,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
defaultVariants: {
|
|
||||||
withActions: false,
|
|
||||||
},
|
|
||||||
} as const
|
|
||||||
|
|
||||||
export const modalContentVariants = cva(styles.content, config)
|
|
||||||
@@ -1,10 +1,10 @@
|
|||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from '../../Icons/MaterialIcon'
|
||||||
import { OldDSButton as Button } from "@scandic-hotels/design-system/OldDSButton"
|
import { OldDSButton as Button } from '../../OldDSButton'
|
||||||
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
import Subtitle from '../../Subtitle'
|
||||||
|
|
||||||
import styles from "./modalContent.module.css"
|
import styles from './modalContent.module.css'
|
||||||
|
|
||||||
import type { ReactNode } from "react"
|
import type { ReactNode } from 'react'
|
||||||
|
|
||||||
interface ModalContentProps {
|
interface ModalContentProps {
|
||||||
title?: string
|
title?: string
|
||||||
@@ -12,14 +12,14 @@ interface ModalContentProps {
|
|||||||
primaryAction: {
|
primaryAction: {
|
||||||
label: string
|
label: string
|
||||||
onClick: () => void
|
onClick: () => void
|
||||||
intent?: "primary" | "secondary" | "text"
|
intent?: 'primary' | 'secondary' | 'text'
|
||||||
isLoading?: boolean
|
isLoading?: boolean
|
||||||
disabled?: boolean
|
disabled?: boolean
|
||||||
} | null
|
} | null
|
||||||
secondaryAction: {
|
secondaryAction: {
|
||||||
label: string
|
label: string
|
||||||
onClick: () => void
|
onClick: () => void
|
||||||
intent?: "primary" | "secondary" | "text"
|
intent?: 'primary' | 'secondary' | 'text'
|
||||||
} | null
|
} | null
|
||||||
onClose?: () => void
|
onClose?: () => void
|
||||||
}
|
}
|
||||||
@@ -46,7 +46,7 @@ export function ModalContentWithActions({
|
|||||||
{secondaryAction && (
|
{secondaryAction && (
|
||||||
<Button
|
<Button
|
||||||
theme="base"
|
theme="base"
|
||||||
intent={secondaryAction.intent ?? "text"}
|
intent={secondaryAction.intent ?? 'text'}
|
||||||
color="burgundy"
|
color="burgundy"
|
||||||
onClick={secondaryAction.onClick}
|
onClick={secondaryAction.onClick}
|
||||||
>
|
>
|
||||||
@@ -56,7 +56,7 @@ export function ModalContentWithActions({
|
|||||||
{primaryAction && (
|
{primaryAction && (
|
||||||
<Button
|
<Button
|
||||||
theme="base"
|
theme="base"
|
||||||
intent={primaryAction.intent ?? "secondary"}
|
intent={primaryAction.intent ?? 'secondary'}
|
||||||
onClick={primaryAction.onClick}
|
onClick={primaryAction.onClick}
|
||||||
disabled={primaryAction.isLoading || primaryAction.disabled}
|
disabled={primaryAction.isLoading || primaryAction.disabled}
|
||||||
>
|
>
|
||||||
@@ -1,30 +1,30 @@
|
|||||||
"use client"
|
'use client'
|
||||||
|
|
||||||
import { cx } from "class-variance-authority"
|
import { cx } from 'class-variance-authority'
|
||||||
import { AnimatePresence, motion } from "motion/react"
|
import { AnimatePresence, motion } from 'motion/react'
|
||||||
import { type PropsWithChildren, useEffect, useState } from "react"
|
import { type PropsWithChildren, useEffect, useState } from 'react'
|
||||||
import {
|
import {
|
||||||
Dialog,
|
Dialog,
|
||||||
DialogTrigger,
|
DialogTrigger,
|
||||||
Modal as AriaModal,
|
Modal as AriaModal,
|
||||||
ModalOverlay,
|
ModalOverlay,
|
||||||
} from "react-aria-components"
|
} from 'react-aria-components'
|
||||||
import { useIntl } from "react-intl"
|
import { useIntl } from 'react-intl'
|
||||||
|
|
||||||
import { MaterialIcon } from "@scandic-hotels/design-system/Icons/MaterialIcon"
|
import { MaterialIcon } from '../Icons/MaterialIcon'
|
||||||
import Preamble from "@scandic-hotels/design-system/Preamble"
|
import Preamble from '../Preamble'
|
||||||
import Subtitle from "@scandic-hotels/design-system/Subtitle"
|
import Subtitle from '../Subtitle'
|
||||||
|
|
||||||
import {
|
import {
|
||||||
type AnimationState,
|
type AnimationState,
|
||||||
AnimationStateEnum,
|
AnimationStateEnum,
|
||||||
type InnerModalProps,
|
type InnerModalProps,
|
||||||
type ModalProps,
|
type ModalProps,
|
||||||
} from "./modal"
|
} from './modal'
|
||||||
import { fade, slideInOut } from "./motionVariants"
|
import { fade, slideInOut } from './motionVariants'
|
||||||
import { modalContentVariants } from "./variants"
|
import { modalContentVariants } from './variants'
|
||||||
|
|
||||||
import styles from "./modal.module.css"
|
import styles from './modal.module.css'
|
||||||
|
|
||||||
const MotionOverlay = motion.create(ModalOverlay)
|
const MotionOverlay = motion.create(ModalOverlay)
|
||||||
const MotionModal = motion.create(AriaModal)
|
const MotionModal = motion.create(AriaModal)
|
||||||
@@ -89,14 +89,14 @@ function InnerModal({
|
|||||||
<Dialog
|
<Dialog
|
||||||
className={styles.dialog}
|
className={styles.dialog}
|
||||||
aria-label={intl.formatMessage({
|
aria-label={intl.formatMessage({
|
||||||
defaultMessage: "Dialog",
|
defaultMessage: 'Dialog',
|
||||||
})}
|
})}
|
||||||
>
|
>
|
||||||
{({ close }) => (
|
{({ close }) => (
|
||||||
<>
|
<>
|
||||||
{!hideHeader && (
|
{!hideHeader && (
|
||||||
<header
|
<header
|
||||||
className={`${styles.header} ${!subtitle ? styles.verticalCenter : ""}`}
|
className={`${styles.header} ${!subtitle ? styles.verticalCenter : ''}`}
|
||||||
>
|
>
|
||||||
<div>
|
<div>
|
||||||
{title && (
|
{title && (
|
||||||
@@ -141,14 +141,14 @@ export default function Modal({
|
|||||||
children,
|
children,
|
||||||
withActions = false,
|
withActions = false,
|
||||||
hideHeader = false,
|
hideHeader = false,
|
||||||
className = "",
|
className = '',
|
||||||
}: PropsWithChildren<ModalProps>) {
|
}: PropsWithChildren<ModalProps>) {
|
||||||
const [animation, setAnimation] = useState<AnimationState>(
|
const [animation, setAnimation] = useState<AnimationState>(
|
||||||
AnimationStateEnum.visible
|
AnimationStateEnum.visible
|
||||||
)
|
)
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (typeof isOpen === "boolean") {
|
if (typeof isOpen === 'boolean') {
|
||||||
setAnimation(
|
setAnimation(
|
||||||
isOpen ? AnimationStateEnum.visible : AnimationStateEnum.hidden
|
isOpen ? AnimationStateEnum.visible : AnimationStateEnum.hidden
|
||||||
)
|
)
|
||||||
@@ -1,9 +1,9 @@
|
|||||||
import type { Dispatch, JSX, SetStateAction } from "react"
|
import type { Dispatch, JSX, SetStateAction } from 'react'
|
||||||
|
|
||||||
export enum AnimationStateEnum {
|
export enum AnimationStateEnum {
|
||||||
unmounted = "unmounted",
|
unmounted = 'unmounted',
|
||||||
hidden = "hidden",
|
hidden = 'hidden',
|
||||||
visible = "visible",
|
visible = 'visible',
|
||||||
}
|
}
|
||||||
|
|
||||||
export type AnimationState = keyof typeof AnimationStateEnum
|
export type AnimationState = keyof typeof AnimationStateEnum
|
||||||
@@ -30,7 +30,7 @@ export type ModalProps = {
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
export type InnerModalProps = Omit<ModalProps, "trigger"> & {
|
export type InnerModalProps = Omit<ModalProps, 'trigger'> & {
|
||||||
animation: AnimationState
|
animation: AnimationState
|
||||||
setAnimation: Dispatch<SetStateAction<AnimationState>>
|
setAnimation: Dispatch<SetStateAction<AnimationState>>
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,23 @@
|
|||||||
|
export const fade = {
|
||||||
|
hidden: {
|
||||||
|
opacity: 0,
|
||||||
|
transition: { duration: 0.4, ease: 'easeInOut' },
|
||||||
|
},
|
||||||
|
visible: {
|
||||||
|
opacity: 1,
|
||||||
|
transition: { duration: 0.4, ease: 'easeInOut' },
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
export const slideInOut = {
|
||||||
|
hidden: {
|
||||||
|
opacity: 0,
|
||||||
|
y: 32,
|
||||||
|
transition: { duration: 0.4, ease: 'easeInOut' },
|
||||||
|
},
|
||||||
|
visible: {
|
||||||
|
opacity: 1,
|
||||||
|
y: 0,
|
||||||
|
transition: { duration: 0.4, ease: 'easeInOut' },
|
||||||
|
},
|
||||||
|
}
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
import { cva } from "class-variance-authority"
|
import { cva } from 'class-variance-authority'
|
||||||
|
|
||||||
import styles from "./modal.module.css"
|
import styles from './modal.module.css'
|
||||||
|
|
||||||
const config = {
|
const config = {
|
||||||
variants: {
|
variants: {
|
||||||
@@ -33,6 +33,8 @@
|
|||||||
"./Label": "./lib/components/Label/index.tsx",
|
"./Label": "./lib/components/Label/index.tsx",
|
||||||
"./Lightbox": "./lib/components/Lightbox/index.tsx",
|
"./Lightbox": "./lib/components/Lightbox/index.tsx",
|
||||||
"./Link": "./lib/components/Link/index.tsx",
|
"./Link": "./lib/components/Link/index.tsx",
|
||||||
|
"./Modal": "./lib/components/Modal/index.tsx",
|
||||||
|
"./Modal/ModalContentWithActions": "./lib/components/Modal/ModalContentWithActions/index.tsx",
|
||||||
"./OldDSButton": "./lib/components/OldDSButton/index.tsx",
|
"./OldDSButton": "./lib/components/OldDSButton/index.tsx",
|
||||||
"./OpeningHours": "./lib/components/OpeningHours/index.tsx",
|
"./OpeningHours": "./lib/components/OpeningHours/index.tsx",
|
||||||
"./Select": "./lib/components/Select/index.tsx",
|
"./Select": "./lib/components/Select/index.tsx",
|
||||||
|
|||||||
Reference in New Issue
Block a user