From 7c5205e7cf2b6e94c2e47ef5ba6684be82e97e00 Mon Sep 17 00:00:00 2001 From: Simon Emanuelsson Date: Wed, 9 Oct 2024 12:44:00 +0200 Subject: [PATCH] feat: add summary card --- .../hotelreservation/[step]/layout.module.css | 8 +- .../hotelreservation/[step]/layout.tsx | 4 +- .../Forms/BookingWidget/FormContent/index.tsx | 1 - .../Forms/BookingWidget/form.module.css | 9 +- .../EnterDetails/Summary/index.tsx | 165 ++++++++++++++++++ .../EnterDetails/Summary/summary.module.css | 38 ++++ .../hotelSelectionHeader.module.css | 9 +- .../SelectRate/Summary/index.tsx | 6 - .../SelectRate/Summary/summary.module.css | 2 - components/Icons/icon.module.css | 5 + components/Icons/variants.ts | 1 + .../TempDesignSystem/Link/link.module.css | 4 + components/TempDesignSystem/Link/variants.ts | 1 + i18n/dictionaries/da.json | 3 + i18n/dictionaries/de.json | 2 + i18n/dictionaries/en.json | 2 + i18n/dictionaries/fi.json | 3 + i18n/dictionaries/no.json | 2 + i18n/dictionaries/sv.json | 2 + 19 files changed, 249 insertions(+), 18 deletions(-) create mode 100644 components/HotelReservation/EnterDetails/Summary/index.tsx create mode 100644 components/HotelReservation/EnterDetails/Summary/summary.module.css delete mode 100644 components/HotelReservation/SelectRate/Summary/index.tsx delete mode 100644 components/HotelReservation/SelectRate/Summary/summary.module.css diff --git a/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.module.css b/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.module.css index f40fca31d..4f337ccb2 100644 --- a/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.module.css +++ b/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.module.css @@ -9,8 +9,12 @@ grid-template-columns: 1fr 340px; grid-template-rows: auto 1fr; margin: var(--Spacing-x5) auto 0; - max-width: var(--max-width-navigation); - padding: var(--Spacing-x6) var(--Spacing-x2) 0; + padding-top: var(--Spacing-x6); + /* simulates padding on viewport smaller than --max-width-navigation */ + width: min( + calc(100dvw - (var(--Spacing-x2) * 2)), + var(--max-width-navigation) + ); } .summary { diff --git a/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.tsx b/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.tsx index c234123a4..8ced3a7ce 100644 --- a/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.tsx +++ b/app/[lang]/(live)/(public)/hotelreservation/[step]/layout.tsx @@ -3,8 +3,9 @@ import { redirect } from "next/navigation" import { serverClient } from "@/lib/trpc/server" import SelectedRoom from "@/components/HotelReservation/EnterDetails/SelectedRoom" +import Summary from "@/components/HotelReservation/EnterDetails/Summary" import HotelSelectionHeader from "@/components/HotelReservation/HotelSelectionHeader" -import Summary from "@/components/HotelReservation/SelectRate/Summary" +import { setLang } from "@/i18n/serverContext" import styles from "./layout.module.css" @@ -14,6 +15,7 @@ export default async function StepLayout({ children, params, }: React.PropsWithChildren>) { + setLang(params.lang) const hotel = await serverClient().hotel.hotelData.get({ hotelId: "811", language: params.lang, diff --git a/components/Forms/BookingWidget/FormContent/index.tsx b/components/Forms/BookingWidget/FormContent/index.tsx index 8f3e8cbc4..c7f990c38 100644 --- a/components/Forms/BookingWidget/FormContent/index.tsx +++ b/components/Forms/BookingWidget/FormContent/index.tsx @@ -7,7 +7,6 @@ import { dt } from "@/lib/dt" import DatePicker from "@/components/DatePicker" import { SearchIcon } from "@/components/Icons" import Button from "@/components/TempDesignSystem/Button" -import Body from "@/components/TempDesignSystem/Text/Body" import Caption from "@/components/TempDesignSystem/Text/Caption" import Input from "./Input" diff --git a/components/Forms/BookingWidget/form.module.css b/components/Forms/BookingWidget/form.module.css index 8514dffd7..22ef6be86 100644 --- a/components/Forms/BookingWidget/form.module.css +++ b/components/Forms/BookingWidget/form.module.css @@ -2,8 +2,10 @@ align-items: center; display: grid; margin: 0 auto; - max-width: var(--max-width-navigation); - width: 100%; + width: min( + calc(100dvw - (var(--Spacing-x2) * 2)), + var(--max-width-navigation) + ); } .form { @@ -32,7 +34,8 @@ padding: var(--Spacing-x-one-and-half) var(--Spacing-x2) var(--Spacing-x-one-and-half) var(--Spacing-x1); } + .full { - padding: var(--Spacing-x1) var(--Spacing-x5); + padding: var(--Spacing-x1) 0; } } diff --git a/components/HotelReservation/EnterDetails/Summary/index.tsx b/components/HotelReservation/EnterDetails/Summary/index.tsx new file mode 100644 index 000000000..8efc418a1 --- /dev/null +++ b/components/HotelReservation/EnterDetails/Summary/index.tsx @@ -0,0 +1,165 @@ +import { dt } from "@/lib/dt" + +import { ArrowRightIcon, ChevronRightSmallIcon } from "@/components/Icons" +import Divider from "@/components/TempDesignSystem/Divider" +import Link from "@/components/TempDesignSystem/Link" +import Body from "@/components/TempDesignSystem/Text/Body" +import Caption from "@/components/TempDesignSystem/Text/Caption" +import { getIntl } from "@/i18n" +import { getLang } from "@/i18n/serverContext" + +import styles from "./summary.module.css" + +// TEMP +const rooms = [ + { + adults: 1, + type: "Cozy cabin", + }, +] + +export default async function Summary() { + const intl = await getIntl() + const lang = getLang() + + const fromDate = dt().locale(lang).format("ddd, D MMM") + const toDate = dt().add(1, "day").locale(lang).format("ddd, D MMM") + const diff = dt(toDate).diff(fromDate, "days") + + const totalAdults = rooms.reduce((total, room) => total + room.adults, 0) + + const adults = intl.formatMessage( + { id: "booking.adults" }, + { totalAdults: totalAdults } + ) + const nights = intl.formatMessage( + { id: "booking.nights" }, + { totalNights: diff } + ) + + const addOns = [ + { + price: intl.formatMessage({ id: "Included" }), + title: intl.formatMessage({ id: "King bed" }), + }, + { + price: intl.formatMessage({ id: "Included" }), + title: intl.formatMessage({ id: "Breakfast buffet" }), + }, + ] + + const mappedRooms = Array.from( + rooms + .reduce((acc, room) => { + const currentRoom = acc.get(room.type) + acc.set(room.type, { + total: currentRoom ? currentRoom.total + 1 : 1, + type: room.type, + }) + return acc + }, new Map()) + .values() + ) + + return ( +
+
+ + {mappedRooms.map( + (room, idx) => + `${room.total} x ${room.type}${mappedRooms.length > 1 && idx + 1 !== mappedRooms.length ? ", " : ""}` + )} + + + {fromDate} + + {toDate} + + + {intl.formatMessage({ id: "See room details" })} + + +
+ +
+
+ + {`${nights}, ${adults}`} + + + {intl.formatMessage( + { id: "{amount} {currency}" }, + { amount: "4536", currency: "SEK" } + )} + +
+ {addOns.map((addOn) => ( +
+ {addOn.title} + {addOn.price} +
+ ))} +
+ +
+
+
+ + {intl.formatMessage({ id: "Total incl VAT" })} + + + {intl.formatMessage( + { id: "{amount} {currency}" }, + { amount: "4686", currency: "SEK" } + )} + +
+
+ + {intl.formatMessage({ id: "Approx." })} + + + {intl.formatMessage( + { id: "{amount} {currency}" }, + { amount: "455", currency: "EUR" } + )} + +
+
+
+
+ + {intl.formatMessage({ id: "Member price" })} + + + {intl.formatMessage( + { id: "{amount} {currency}" }, + { amount: "4219", currency: "SEK" } + )} + +
+
+ + {intl.formatMessage({ id: "Approx." })} + + + {intl.formatMessage( + { id: "{amount} {currency}" }, + { amount: "412", currency: "EUR" } + )} + +
+
+
+
+ ) +} diff --git a/components/HotelReservation/EnterDetails/Summary/summary.module.css b/components/HotelReservation/EnterDetails/Summary/summary.module.css new file mode 100644 index 000000000..16ca412c5 --- /dev/null +++ b/components/HotelReservation/EnterDetails/Summary/summary.module.css @@ -0,0 +1,38 @@ +.summary { + background-color: var(--Main-Grey-White); + border: 1px solid var(--Primary-Light-On-Surface-Divider-subtle); + border-radius: var(--Corner-radius-Large); + display: flex; + flex-direction: column; + gap: var(--Spacing-x2); + padding: var(--Spacing-x2); +} + +.date { + align-items: center; + display: flex; + gap: var(--Spacing-x1); + justify-content: flex-start; +} + +.link { + margin-top: var(--Spacing-x1); +} + +.addOns { + display: flex; + flex-direction: column; + gap: var(--Spacing-x1); +} + +.entry { + display: flex; + gap: var(--Spacing-x-half); + justify-content: space-between; +} + +.total { + display: flex; + flex-direction: column; + gap: var(--Spacing-x2); +} diff --git a/components/HotelReservation/HotelSelectionHeader/hotelSelectionHeader.module.css b/components/HotelReservation/HotelSelectionHeader/hotelSelectionHeader.module.css index 268bfe4fe..9eefdfb33 100644 --- a/components/HotelReservation/HotelSelectionHeader/hotelSelectionHeader.module.css +++ b/components/HotelReservation/HotelSelectionHeader/hotelSelectionHeader.module.css @@ -36,15 +36,18 @@ @media (min-width: 768px) { .hotelSelectionHeader { - padding: var(--Spacing-x4) var(--Spacing-x5); + padding: var(--Spacing-x4) 0; } .hotelSelectionHeaderWrapper { flex-direction: row; gap: var(--Spacing-x6); - max-width: var(--max-width-navigation); margin: 0 auto; - width: 100%; + /* simulates padding on viewport smaller than --max-width-navigation */ + width: min( + calc(100dvw - (var(--Spacing-x2) * 2)), + var(--max-width-navigation) + ); } .titleContainer > h1 { diff --git a/components/HotelReservation/SelectRate/Summary/index.tsx b/components/HotelReservation/SelectRate/Summary/index.tsx deleted file mode 100644 index 1cff67248..000000000 --- a/components/HotelReservation/SelectRate/Summary/index.tsx +++ /dev/null @@ -1,6 +0,0 @@ -"use client" -import styles from "./summary.module.css" - -export default function Summary() { - return
Summary TBI
-} diff --git a/components/HotelReservation/SelectRate/Summary/summary.module.css b/components/HotelReservation/SelectRate/Summary/summary.module.css deleted file mode 100644 index ec81ef8e9..000000000 --- a/components/HotelReservation/SelectRate/Summary/summary.module.css +++ /dev/null @@ -1,2 +0,0 @@ -.wrapper { -} diff --git a/components/Icons/icon.module.css b/components/Icons/icon.module.css index bb86becdb..ec5a15fd4 100644 --- a/components/Icons/icon.module.css +++ b/components/Icons/icon.module.css @@ -71,3 +71,8 @@ .baseButtonTertiaryOnFillNormal * { fill: var(--Base-Button-Tertiary-On-Fill-Normal); } + +.baseButtonTextOnFillNormal, +.baseButtonTextOnFillNormal * { + fill: var(--Base-Button-Text-On-Fill-Normal); +} diff --git a/components/Icons/variants.ts b/components/Icons/variants.ts index 911d183da..d319c466e 100644 --- a/components/Icons/variants.ts +++ b/components/Icons/variants.ts @@ -6,6 +6,7 @@ const config = { variants: { color: { baseButtonTertiaryOnFillNormal: styles.baseButtonTertiaryOnFillNormal, + baseButtonTextOnFillNormal: styles.baseButtonTextOnFillNormal, baseIconLowContrast: styles.baseIconLowContrast, black: styles.black, blue: styles.blue, diff --git a/components/TempDesignSystem/Link/link.module.css b/components/TempDesignSystem/Link/link.module.css index a22274051..a29e20309 100644 --- a/components/TempDesignSystem/Link/link.module.css +++ b/components/TempDesignSystem/Link/link.module.css @@ -107,6 +107,10 @@ font-weight: 600; } +.baseButtonTextOnFillNormal { + color: var(--Base-Button-Text-On-Fill-Normal); +} + .black { color: #000; } diff --git a/components/TempDesignSystem/Link/variants.ts b/components/TempDesignSystem/Link/variants.ts index 273eea928..267da008f 100644 --- a/components/TempDesignSystem/Link/variants.ts +++ b/components/TempDesignSystem/Link/variants.ts @@ -8,6 +8,7 @@ export const linkVariants = cva(styles.link, { true: styles.active, }, color: { + baseButtonTextOnFillNormal: styles.baseButtonTextOnFillNormal, black: styles.black, burgundy: styles.burgundy, none: "", diff --git a/i18n/dictionaries/da.json b/i18n/dictionaries/da.json index 164b86117..1ed4d220a 100644 --- a/i18n/dictionaries/da.json +++ b/i18n/dictionaries/da.json @@ -17,6 +17,7 @@ "An error occurred when adding a credit card, please try again later.": "Der opstod en fejl under tilføjelse af et kreditkort. Prøv venligst igen senere.", "An error occurred when trying to update profile.": "Der opstod en fejl under forsøg på at opdatere profilen.", "Any changes you've made will be lost.": "Alle ændringer, du har foretaget, går tabt.", + "Approx.": "Ca.", "Are you sure you want to remove the card ending with {lastFourDigits} from your member profile?": "Er du sikker på, at du vil fjerne kortet, der slutter me {lastFourDigits} fra din medlemsprofil?", "Arrival date": "Ankomstdato", "Approx.": "Ca.", @@ -128,6 +129,7 @@ "How do you want to sleep?": "Hvordan vil du sove?", "How it works": "Hvordan det virker", "Image gallery": "Billedgalleri", + "Included": "Inkluderet", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "Det er ikke muligt at administrere dine kommunikationspræferencer lige nu, prøv venligst igen senere eller kontakt support, hvis problemet fortsætter.", "Join at no cost": "Tilmeld dig uden omkostninger", "Join Scandic Friends": "Tilmeld dig Scandic Friends", @@ -283,6 +285,7 @@ "Things nearby HOTEL_NAME": "Ting i nærheden af {hotelName}", "to": "til", "Total Points": "Samlet antal point", + "Total incl VAT": "Inkl. moms", "Tourist": "Turist", "Transaction date": "Overførselsdato", "Transactions": "Transaktioner", diff --git a/i18n/dictionaries/de.json b/i18n/dictionaries/de.json index cef8605eb..0ddcc5d70 100644 --- a/i18n/dictionaries/de.json +++ b/i18n/dictionaries/de.json @@ -128,6 +128,7 @@ "How do you want to sleep?": "Wie möchtest du schlafen?", "How it works": "Wie es funktioniert", "Image gallery": "Bildergalerie", + "Included": "Iinklusive", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "Es ist derzeit nicht möglich, Ihre Kommunikationseinstellungen zu verwalten. Bitte versuchen Sie es später erneut oder wenden Sie sich an den Support, wenn das Problem weiterhin besteht.", "Join at no cost": "Kostenlos beitreten", "Join Scandic Friends": "Treten Sie Scandic Friends bei", @@ -283,6 +284,7 @@ "Things nearby HOTEL_NAME": "Dinge in der Nähe von {hotelName}", "to": "zu", "Total Points": "Gesamtpunktzahl", + "Total incl VAT": "Gesamt inkl. MwSt.", "Tourist": "Tourist", "Transaction date": "Transaktionsdatum", "Transactions": "Transaktionen", diff --git a/i18n/dictionaries/en.json b/i18n/dictionaries/en.json index 9248144e1..5841856c5 100644 --- a/i18n/dictionaries/en.json +++ b/i18n/dictionaries/en.json @@ -128,6 +128,7 @@ "How do you want to sleep?": "How do you want to sleep?", "How it works": "How it works", "Image gallery": "Image gallery", + "Included": "Included", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.", "Join at no cost": "Join at no cost", "Join Scandic Friends": "Join Scandic Friends", @@ -282,6 +283,7 @@ "Things nearby HOTEL_NAME": "Things nearby {hotelName}", "to": "to", "Total Points": "Total Points", + "Total incl VAT": "Total incl VAT", "Tourist": "Tourist", "Transaction date": "Transaction date", "Transactions": "Transactions", diff --git a/i18n/dictionaries/fi.json b/i18n/dictionaries/fi.json index 66cad603e..036f7ff7e 100644 --- a/i18n/dictionaries/fi.json +++ b/i18n/dictionaries/fi.json @@ -17,6 +17,7 @@ "An error occurred when adding a credit card, please try again later.": "Luottokorttia lisättäessä tapahtui virhe. Yritä myöhemmin uudelleen.", "An error occurred when trying to update profile.": "Profiilia päivitettäessä tapahtui virhe.", "Any changes you've made will be lost.": "Kaikki tekemäsi muutokset menetetään.", + "Approx.": "N.", "Are you sure you want to remove the card ending with {lastFourDigits} from your member profile?": "Haluatko varmasti poistaa kortin, joka päättyy numeroon {lastFourDigits} jäsenprofiilistasi?", "Arrival date": "Saapumispäivä", "Approx.": "Noin", @@ -128,6 +129,7 @@ "How do you want to sleep?": "Kuinka haluat nukkua?", "How it works": "Kuinka se toimii", "Image gallery": "Kuvagalleria", + "Included": "Sisälly hintaan", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "Viestintäasetuksiasi ei voi hallita juuri nyt. Yritä myöhemmin uudelleen tai ota yhteyttä tukeen, jos ongelma jatkuu.", "Join at no cost": "Liity maksutta", "Join Scandic Friends": "Liity jäseneksi", @@ -284,6 +286,7 @@ "Things nearby HOTEL_NAME": "Lähellä olevia asioita {hotelName}", "to": "to", "Total Points": "Kokonaispisteet", + "Total incl VAT": "Yhteensä sis. alv", "Tourist": "Turisti", "Transaction date": "Tapahtuman päivämäärä", "Transactions": "Tapahtumat", diff --git a/i18n/dictionaries/no.json b/i18n/dictionaries/no.json index 1e0276d87..c3da52178 100644 --- a/i18n/dictionaries/no.json +++ b/i18n/dictionaries/no.json @@ -126,6 +126,7 @@ "How do you want to sleep?": "Hvordan vil du sove?", "How it works": "Hvordan det fungerer", "Image gallery": "Bildegalleri", + "Included": "Inkludert", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "Det er ikke mulig å administrere kommunikasjonspreferansene dine akkurat nå, prøv igjen senere eller kontakt support hvis problemet vedvarer.", "Join at no cost": "Bli med uten kostnad", "Join Scandic Friends": "Bli med i Scandic Friends", @@ -280,6 +281,7 @@ "Things nearby HOTEL_NAME": "Ting i nærheten av {hotelName}", "to": "til", "Total Points": "Totale poeng", + "Total incl VAT": "Sum inkl mva", "Tourist": "Turist", "Transaction date": "Transaksjonsdato", "Transactions": "Transaksjoner", diff --git a/i18n/dictionaries/sv.json b/i18n/dictionaries/sv.json index 45b7d3ca2..57b4fb047 100644 --- a/i18n/dictionaries/sv.json +++ b/i18n/dictionaries/sv.json @@ -127,6 +127,7 @@ "How do you want to sleep?": "Hur vill du sova?", "How it works": "Hur det fungerar", "Image gallery": "Bildgalleri", + "Included": "Inkluderad", "It is not posible to manage your communication preferences right now, please try again later or contact support if the problem persists.": "Det gick inte att hantera dina kommunikationsinställningar just nu, försök igen senare eller kontakta supporten om problemet kvarstår.", "Join at no cost": "Gå med utan kostnad", "Join Scandic Friends": "Gå med i Scandic Friends", @@ -281,6 +282,7 @@ "Things nearby HOTEL_NAME": "Saker i närheten av {hotelName}", "to": "till", "Total Points": "Poäng totalt", + "Total incl VAT": "Totalt inkl moms", "Tourist": "Turist", "Transaction date": "Transaktionsdatum", "Transactions": "Transaktioner",