fix: clean up dictionaries

This commit is contained in:
Michael Zetterberg
2025-03-11 13:12:06 +01:00
parent 1a8a57599c
commit 91c36ee41c
32 changed files with 372 additions and 182 deletions
@@ -1,6 +1,7 @@
"use client"
import { cx } from "class-variance-authority"
import { useIntl } from "react-intl"
import { ArrowRightIcon } from "@/components/Icons"
@@ -13,13 +14,15 @@ import type { CarouselButtonProps } from "./types"
export function CarouselPrevious({ className, ...props }: CarouselButtonProps) {
const { scrollPrev, canScrollPrev } = useCarousel()
const intl = useIntl()
if (!canScrollPrev()) return null
return (
<button
className={cx(styles.button, styles.buttonPrev, className)}
onClick={scrollPrev}
aria-label="Previous slide"
aria-label={intl.formatMessage({ id: "Previous slide" })}
{...props}
>
<ArrowRightIcon color="burgundy" className={styles.prevIcon} />
@@ -30,13 +33,15 @@ export function CarouselPrevious({ className, ...props }: CarouselButtonProps) {
export function CarouselNext({ className, ...props }: CarouselButtonProps) {
const { scrollNext, canScrollNext } = useCarousel()
const intl = useIntl()
if (!canScrollNext()) return null
return (
<button
className={cx(styles.button, styles.buttonNext, className)}
onClick={scrollNext}
aria-label="Next slide"
aria-label={intl.formatMessage({ id: "Next slide" })}
{...props}
>
<ArrowRightIcon color="burgundy" />
@@ -126,7 +126,7 @@ export default function Map({
style={
{ "--destination-map-height": mapHeight } as React.CSSProperties
}
aria-label={"Mapview"}
aria-label={intl.formatMessage({ id: "Map view" })}
>
<div className={styles.mobileNavigation}>
<Button
@@ -25,8 +25,6 @@ import type {
} from "@/types/components/bookingWidget"
import type { ButtonProps } from "@/components/TempDesignSystem/Button/button"
const removeExtraRoomsTranslationId = "Remove extra rooms"
export default function BookingCode() {
const intl = useIntl()
const checkIsTablet = useMediaQuery(
@@ -50,7 +48,7 @@ export default function BookingCode() {
const addCode = intl.formatMessage({ id: "Add code" })
const ref = useRef<HTMLDivElement | null>(null)
const removeExtraRoomsText = intl.formatMessage({
id: removeExtraRoomsTranslationId,
id: "Remove extra rooms",
})
function updateBookingCodeFormValue(value: string) {
@@ -287,7 +285,7 @@ export function RemoveExtraRooms({ ...props }: ButtonProps) {
intent="secondary"
{...props}
>
{intl.formatMessage({ id: removeExtraRoomsTranslationId })}
{intl.formatMessage({ id: "Remove extra rooms" })}
</Button>
)
}
@@ -23,7 +23,12 @@ export function GuestsRoom({
onRemove: (index: number) => void
}) {
const intl = useIntl()
const roomLabel = intl.formatMessage({ id: "Room" })
const roomLabel = intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: index + 1,
}
)
const childrenInAdultsBed = room.childrenInRoom.filter(
(child) => child.bed === ChildBedMapEnum.IN_ADULTS_BED
@@ -33,7 +38,7 @@ export function GuestsRoom({
<div className={styles.roomContainer}>
<section className={styles.roomDetailsContainer}>
<Subtitle type="two" className={styles.roomHeading}>
{roomLabel} {index + 1}
{roomLabel}
</Subtitle>
<AdultSelector
roomIndex={index}
@@ -26,7 +26,12 @@ export default function Multiroom() {
<section>
<Header>
<Title level="h2" as="h4">
{`${intl.formatMessage({ id: "Room" })} ${roomNr}`}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: roomNr,
}
)}
</Title>
</Header>
@@ -31,7 +31,12 @@ export default function RoomOne({ user }: { user: SafeUser }) {
{isMultiroom ? (
<Header>
<Title level="h2" as="h4">
{`${intl.formatMessage({ id: "Room" })} 1`}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: 1,
}
)}
</Title>
</Header>
) : null}
@@ -149,7 +149,12 @@ export default function SummaryUI({
<div>
{rooms.length > 1 ? (
<Body textTransform="bold">
{intl.formatMessage({ id: "Room" })} {roomNumber}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: roomNumber,
}
)}
</Body>
) : null}
<div className={styles.entry}>
@@ -218,8 +218,12 @@ export default function AddAncillaryFlowModal({
<>
<Divider variant="vertical" color="subtle" />
<Body textTransform="bold" color="uiTextHighContrast">
{selectedAncillary.points}{" "}
{intl.formatMessage({ id: "points" })}
{intl.formatMessage(
{ id: "{value} points" },
{
value: selectedAncillary.points,
}
)}
</Body>
</>
)}
@@ -110,7 +110,10 @@ export default function ConfirmationStep() {
<Divider variant="vertical" color="subtle" />
</div>
<Body textTransform="bold" color="uiTextHighContrast">
{totalPoints} {intl.formatMessage({ id: "points" })}
{intl.formatMessage(
{ id: "{value} points" },
{ value: totalPoints }
)}
</Body>
</div>
)}
@@ -73,7 +73,12 @@ export function AddedAncillaries({
color="baseSurfaceSubtleNormal"
/>
<Body textTransform="bold">
{`${ancillary.points} ${intl.formatMessage({ id: "Points" })}`}
{intl.formatMessage(
{ id: "{value} points" },
{
value: ancillary.points,
}
)}
</Body>
</div>
</div>
@@ -120,7 +125,12 @@ export function AddedAncillaries({
</Body>
<Divider variant="vertical" color="baseSurfaceSubtleNormal" />
<Body textTransform="bold">
{`${ancillary.points} ${intl.formatMessage({ id: "Points" })}`}
{intl.formatMessage(
{ id: "{value} points" },
{
value: ancillary.points,
}
)}
</Body>
</div>
</div>
@@ -68,7 +68,12 @@ export function CancelStayConfirmation({
>
<div className={styles.roomInfo}>
<Caption color="uiTextHighContrast">
{intl.formatMessage({ id: "Room" })} {index + 1}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: index + 1,
}
)}
</Caption>
{roomDetail && (
<>
@@ -56,11 +56,35 @@ export default function LinkedReservation({
const fromDate = dt(booking.checkInDate).locale(lang)
const toDate = dt(booking.checkOutDate).locale(lang)
const adultsMsg = intl.formatMessage(
{ id: "{adults, plural, one {# adult} other {# adults}}" },
{
adults: booking.adults,
}
)
const childrenMsg = intl.formatMessage(
{
id: "{children, plural, one {# child} other {# children}}",
},
{
children: booking.childrenAges.length,
}
)
const adultsOnlyMsg = adultsMsg
const adultsAndChildrenMsg = [adultsMsg, childrenMsg].join(", ")
return (
<article className={styles.linkedReservation}>
<div className={styles.title}>
<Subtitle color="burgundy">
{intl.formatMessage({ id: "Room" }) + " " + (index + 2)}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: index + 2,
}
)}
</Subtitle>
</div>
<div className={styles.details}>
@@ -70,19 +94,8 @@ export default function LinkedReservation({
<div>
<Caption color="uiTextHighContrast">
{booking.childrenAges.length > 0
? intl.formatMessage(
{ id: "{adults} adults, {children} children" },
{
adults: booking.adults,
children: booking.childrenAges.length,
}
)
: intl.formatMessage(
{ id: "{adults} adults" },
{
adults: booking.adults,
}
)}
? adultsAndChildrenMsg
: adultsOnlyMsg}
</Caption>
</div>
</div>
@@ -49,6 +49,7 @@ export function ReferenceCard({ booking, hotel }: ReferenceCardProps) {
(acc, linkedReservation) => acc + linkedReservation.adults,
0
) ?? 0)
const children =
booking.childrenAges.length +
(booking.linkedReservations?.reduce(
@@ -56,6 +57,25 @@ export function ReferenceCard({ booking, hotel }: ReferenceCardProps) {
0
) ?? 0)
const adultsMsg = intl.formatMessage(
{ id: "{adults, plural, one {# adult} other {# adults}}" },
{
adults: adults,
}
)
const childrenMsg = intl.formatMessage(
{
id: "{children, plural, one {# child} other {# children}}",
},
{
children: children,
}
)
const adultsOnlyMsg = adultsMsg
const adultsAndChildrenMsg = [adultsMsg, childrenMsg].join(", ")
return (
<div className={styles.referenceCard}>
<div className={styles.referenceRow}>
@@ -83,20 +103,7 @@ export function ReferenceCard({ booking, hotel }: ReferenceCardProps) {
{intl.formatMessage({ id: "Guests" })}
</Caption>
<Caption type="bold" color="uiTextHighContrast">
{children > 0
? intl.formatMessage(
{ id: "{adults} adults, {children} children" },
{
adults: adults,
children: children,
}
)
: intl.formatMessage(
{ id: "{adults} adults" },
{
adults: adults,
}
)}
{children > 0 ? adultsAndChildrenMsg : adultsOnlyMsg}
</Caption>
</div>
<div className={styles.referenceRow}>
@@ -158,8 +158,12 @@ export default function GuestDetails({
</Body>
{isMemberBooking && (
<Body color="uiTextHighContrast">
{intl.formatMessage({ id: "Member no." })}{" "}
{user.membership!.membershipNumber}
{intl.formatMessage(
{ id: "Member no. {nr}" },
{
nr: user.membership!.membershipNumber,
}
)}
</Body>
)}
<Caption color="uiTextHighContrast">{guestDetails.email}</Caption>
@@ -87,6 +87,44 @@ export function Room({ booking, room, hotel, user }: RoomProps) {
const fromDate = dt(booking.checkInDate).locale(lang)
const mainBedWidthValueMsg = intl.formatMessage(
{ id: "{value} cm" },
{
value: room.bedType.mainBed.widthRange.min,
}
)
const mainBedWidthRangeMsg = intl.formatMessage(
{
id: "{min}{max} cm",
},
{
min: room.bedType.mainBed.widthRange.min,
max: room.bedType.mainBed.widthRange.max,
}
)
const adultsMsg = intl.formatMessage(
{
id: "{adults, plural, one {# adult} other {# adults}}",
},
{
adults: booking.adults,
}
)
const childrenMsg = intl.formatMessage(
{
id: "{children, plural, one {# child} other {# children}}",
},
{
children: booking.childrenAges.length,
}
)
const adultsOnlyMsg = adultsMsg
const adultsAndChildrenMsg = [adultsMsg, childrenMsg].join(", ")
return (
<div>
<article className={styles.room}>
@@ -189,19 +227,8 @@ export function Room({ booking, room, hotel, user }: RoomProps) {
<div className={styles.rowContent}>
<Body color="uiTextHighContrast">
{booking.childrenAges.length > 0
? intl.formatMessage(
{ id: "{adults} adults, {children} children" },
{
adults: booking.adults,
children: booking.childrenAges.length,
}
)
: intl.formatMessage(
{ id: "{adults} adults" },
{
adults: booking.adults,
}
)}
? adultsAndChildrenMsg
: adultsOnlyMsg}
</Body>
</div>
</div>
@@ -232,8 +259,8 @@ export function Room({ booking, room, hotel, user }: RoomProps) {
{room.bedType.mainBed.description}
{room.bedType.mainBed.widthRange.min ===
room.bedType.mainBed.widthRange.max
? ` (${room.bedType.mainBed.widthRange.min} ${intl.formatMessage({ id: "cm" })})`
: ` (${room.bedType.mainBed.widthRange.min} - ${room.bedType.mainBed.widthRange.max} ${intl.formatMessage({ id: "cm" })})`}
? ` (${mainBedWidthValueMsg})`
: ` (${mainBedWidthRangeMsg})`}
</Body>
</div>
</div>
@@ -110,7 +110,12 @@ export default function PriceDetailsTable({
<TableSection>
{rooms.length > 1 && (
<Body textTransform="bold">
{intl.formatMessage({ id: "Room" })} {idx + 1}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: idx + 1,
}
)}
</Body>
)}
<TableSectionHeader title={room.roomType} subtitle={duration} />
@@ -43,7 +43,7 @@ export default function BookingCodeFilter() {
<>
<div className={styles.bookingCodeFilter}>
<Select
aria-label="Booking Code Filter"
aria-label={intl.formatMessage({ id: "Booking Code Filter" })}
className={styles.bookingCodeFilterSelect}
name="bookingCodeFilter"
onSelect={updateFilter}
@@ -209,7 +209,12 @@ export default async function SelectHotel({
<div className={styles.cityInformation}>
<Subtitle>
{isAlternativeFor
? `${intl.formatMessage({ id: "Alternatives for" })} ${isAlternativeFor.name}`
? intl.formatMessage(
{ id: "Alternatives for {value}" },
{
value: isAlternativeFor.name,
}
)
: city.name}
</Subtitle>
<HotelCount />
@@ -138,7 +138,12 @@ export default function Summary({
<div>
{rooms.length > 1 ? (
<Body textTransform="bold">
{intl.formatMessage({ id: "Room" })} {roomNumber}
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{
roomIndex: roomNumber,
}
)}
</Body>
) : null}
<div className={styles.entry}>
@@ -27,18 +27,33 @@ export default function MultiRoomWrapper({
selectedRate,
} = useRoomContext()
const onlyAdultsMsg = intl.formatMessage(
{ id: "{adults} adults" },
const roomMsg = intl.formatMessage(
{ id: "Room {roomIndex}" },
{ roomIndex: roomNr }
)
const adultsMsg = intl.formatMessage(
{ id: "{adults, plural, one {# adult} other {# adults}}" },
{ adults: bookingRoom.adults }
)
const adultsAndChildrenMsg = intl.formatMessage(
{ id: "{adults} adults, {children} children" },
const childrenMsg = intl.formatMessage(
{
id: "{children, plural, one {# child} other {# children}}",
},
{
adults: bookingRoom.adults,
children: bookingRoom.childrenInRoom?.length,
}
)
const onlyAdultsMsg = adultsMsg
const adultsAndChildrenMsg = [adultsMsg, childrenMsg].join(", ")
const guestsMsg = bookingRoom.childrenInRoom?.length
? adultsAndChildrenMsg
: onlyAdultsMsg
const title = [roomMsg, guestsMsg].join(", ")
useEffect(() => {
requestAnimationFrame(() => {
const SCROLL_OFFSET = 100
@@ -67,16 +82,7 @@ export default function MultiRoomWrapper({
<div className={styles.roomContainer} data-multiroom="true">
<div className={styles.header}>
{selectedRate && !isActiveRoom ? null : (
<Subtitle className={styles.subtitle} color="uiTextHighContrast">
{intl.formatMessage(
{ id: "Room {roomIndex}" },
{ roomIndex: roomNr }
)}
,{" "}
{bookingRoom.childrenInRoom?.length
? adultsAndChildrenMsg
: onlyAdultsMsg}
</Subtitle>
<Subtitle color="uiTextHighContrast">{title}</Subtitle>
)}
{selectedRate && isActiveRoom ? (
<Button
@@ -217,10 +217,16 @@ export default function RoomCard({ roomConfiguration }: RoomCardProps) {
<Caption color="uiTextMediumContrast">
{occupancy.max === occupancy.min
? intl.formatMessage(
{ id: "guests.plural" },
{ guests: occupancy.max }
)
: intl.formatMessage({ id: "guests.span" }, occupancy)}
{ id: "{guests, plural, one {# guest} other {# guests}}" },
{ guests: occupancy.max }
)
: intl.formatMessage(
{ id: "{min}-{max} guests" },
{
min: occupancy.min,
max: occupancy.max,
}
)}
</Caption>
)}
<RoomSize roomSize={roomSize} />
@@ -290,7 +296,7 @@ export default function RoomCard({ roomConfiguration }: RoomCardProps) {
title={rateTitle}
rateTitle={
product.public &&
product.public?.rateType !== RateTypeEnum.Regular
product.public?.rateType !== RateTypeEnum.Regular
? rateDefinition?.title
: undefined
}
@@ -70,7 +70,7 @@ export default function RoomTypeFilter() {
: allRoomsAvailableText}
</Caption>
<ToggleButtonGroup
aria-label="Filter"
aria-label={intl.formatMessage({ id: "Filter" })}
className={styles.roomsFilter}
defaultSelectedKeys={selectedPackage ? [selectedPackage] : undefined}
onSelectionChange={handleChange}
@@ -28,7 +28,7 @@ export default function Parking({ parking }: ParkingProps) {
<ul className={styles.list}>
{p.address !== undefined && (
<li>
<FilledHeartIcon color="baseIconLowContrast" />$
<FilledHeartIcon color="baseIconLowContrast" />
{intl.formatMessage(
{ id: "Address: {address}" },
{
@@ -13,6 +13,8 @@ import type { AncillaryCardProps } from "@/types/components/ancillaryCard"
export function AncillaryCard({ ancillary }: AncillaryCardProps) {
const intl = useIntl()
const priceMsg = `${formatPrice(intl, ancillary.price.total, ancillary.price.currency)} ${ancillary.price.text ?? ""}`
return (
<article className={styles.ancillaryCard}>
<div className={styles.imageContainer}>
@@ -34,11 +36,7 @@ export function AncillaryCard({ ancillary }: AncillaryCardProps) {
<Body color="uiTextHighContrast">
{ancillary.price.included
? intl.formatMessage({ id: "Included" })
: `${formatPrice(
intl,
ancillary.price.total,
ancillary.price.currency
)} ${ancillary.price.text ?? ""}`}
: priceMsg}
</Body>
{ancillary.points && (
@@ -47,7 +45,12 @@ export function AncillaryCard({ ancillary }: AncillaryCardProps) {
<Divider variant="vertical" color="subtle" />
</div>
<Body textAlign="right" color="uiTextHighContrast">
{ancillary.points} {intl.formatMessage({ id: "Points" })}
{intl.formatMessage(
{ id: "{value} points" },
{
value: ancillary.points,
}
)}
</Body>
</>
)}