diff --git a/apps/react/src/app/features/online-board/components/online-board-filter.tsx b/apps/react/src/app/features/online-board/components/online-board-filter.tsx index 7fcf92005..0d6ec6283 100644 --- a/apps/react/src/app/features/online-board/components/online-board-filter.tsx +++ b/apps/react/src/app/features/online-board/components/online-board-filter.tsx @@ -15,6 +15,7 @@ interface OnlineBoardFilterProps { flightNumber?: string tripType?: string passengers?: { adults: number, children: number, infants: number } + cabinClass?: 'economy' | 'business' | 'first' } } @@ -29,7 +30,7 @@ export const OnlineBoardFilter: React.FC = ({ initialSea navigate(`/onlineboard/flight/${params}`) } - const handleRouteSearch = (departure: string, arrival: string, date: Date, returnDate?: Date | null, tripType?: string, passengers?: { adults: number, children: number, infants: number }) => { + const handleRouteSearch = (departure: string, arrival: string, date: Date, returnDate?: Date | null, tripType?: string, passengers?: { adults: number, children: number, infants: number }, cabinClass?: 'economy' | 'business' | 'first') => { // Navigate to route search results const params = btoa(JSON.stringify({ departure, @@ -38,6 +39,7 @@ export const OnlineBoardFilter: React.FC = ({ initialSea ...(returnDate && { returnDate: returnDate.toISOString() }), ...(tripType && { tripType }), ...(passengers && { passengers }), + ...(cabinClass && { cabinClass }), })) navigate(`/onlineboard/route/${params}`) } @@ -66,6 +68,7 @@ export const OnlineBoardFilter: React.FC = ({ initialSea initialReturnDate={initialSearchParams?.returnDate} initialTripType={initialSearchParams?.tripType} initialPassengers={initialSearchParams?.passengers} + initialCabinClass={initialSearchParams?.cabinClass} /> diff --git a/apps/react/src/app/features/online-board/components/route-filter.scss b/apps/react/src/app/features/online-board/components/route-filter.scss index 209133ded..60598b7aa 100644 --- a/apps/react/src/app/features/online-board/components/route-filter.scss +++ b/apps/react/src/app/features/online-board/components/route-filter.scss @@ -125,6 +125,69 @@ } } +.route-filter__cabin-class-group { + position: relative; +} + +.route-filter__cabin-class-dropdown { + width: 100%; + justify-content: space-between; + padding: 8px 12px; + background-color: #f5f5f5; + border-radius: 4px; + font-size: 14px; + text-align: left; + + &:hover { + background-color: #ececec; + } +} + +.route-filter__cabin-class-options { + display: flex; + flex-direction: column; + gap: 0; + padding: 0; + background-color: #fafafa; + border: 1px solid #e0e0e0; + border-top: none; + border-radius: 0 0 4px 4px; + margin-top: -4px; +} + +.route-filter__cabin-option { + width: 100%; + justify-content: flex-start; + padding: 8px 12px; + border-radius: 0; + font-size: 14px; + border-bottom: 1px solid #e0e0e0; + background-color: transparent; + + &:last-child { + border-bottom: none; + } + + &:hover { + background-color: #f0f0f0; + } + + &.active { + background-color: #e3f2fd; + font-weight: 600; + color: #0066cc; + } +} + +.route-filter__cabin-class-display { + margin-top: 4px; + padding: 4px 8px; + background-color: #f5f5f5; + border-radius: 4px; + font-size: 12px; + color: #666; +} + .route-filter__actions { display: flex; gap: 8px; diff --git a/apps/react/src/app/features/online-board/components/route-filter.tsx b/apps/react/src/app/features/online-board/components/route-filter.tsx index 83be09078..f1c2d1e7c 100644 --- a/apps/react/src/app/features/online-board/components/route-filter.tsx +++ b/apps/react/src/app/features/online-board/components/route-filter.tsx @@ -13,13 +13,14 @@ export interface PassengerCounts { } export interface RouteFilterProps { - onSearch?: (departure: string, arrival: string, date: Date, returnDate?: Date | null, tripType?: string, passengers?: PassengerCounts) => void + onSearch?: (departure: string, arrival: string, date: Date, returnDate?: Date | null, tripType?: string, passengers?: PassengerCounts, cabinClass?: 'economy' | 'business' | 'first') => void initialDeparture?: string initialArrival?: string initialDate?: Date | string initialReturnDate?: Date | string initialTripType?: string initialPassengers?: PassengerCounts + initialCabinClass?: 'economy' | 'business' | 'first' } // Validation service @@ -77,7 +78,8 @@ export const RouteFilter: React.FC = ({ initialDate, initialReturnDate, initialTripType, - initialPassengers + initialPassengers, + initialCabinClass }) => { const { t } = useTranslation() const validated = validatePassengerCounts(initialPassengers) @@ -102,6 +104,8 @@ export const RouteFilter: React.FC = ({ const [children, setChildren] = useState(validated.children) const [infants, setInfants] = useState(validated.infants) const [showPassengerDropdown, setShowPassengerDropdown] = useState(false) + const [cabinClass, setCabinClass] = useState<'economy' | 'business' | 'first'>(initialCabinClass || 'economy') + const [showCabinDropdown, setShowCabinDropdown] = useState(false) const totalPassengers = adults + children + infants const maxPassengers = 9 @@ -119,10 +123,10 @@ export const RouteFilter: React.FC = ({ const handleSearch = useCallback(() => { if (validateRouteParams(departure, arrival, date) && onSearch) { - // Pass all search parameters including return date for round trips and passenger counts - onSearch(departure!.code, arrival!.code, date!, returnDate, tripType, { adults, children, infants }) + // Pass all search parameters including return date for round trips, passenger counts, and cabin class + onSearch(departure!.code, arrival!.code, date!, returnDate, tripType, { adults, children, infants }, cabinClass) } - }, [departure, arrival, date, returnDate, tripType, adults, children, infants, onSearch]) + }, [departure, arrival, date, returnDate, tripType, adults, children, infants, cabinClass, onSearch]) const handleSwap = () => { const temp = departure @@ -238,6 +242,52 @@ export const RouteFilter: React.FC = ({ +
+
+ )} + +
+ {t(`SHARED.${cabinClass.toUpperCase()}`)} +
+ +
{ flightNumber: searchParams.flightNumber, returnDate: searchParams.returnDate, tripType: searchParams.tripType, + cabinClass: searchParams.cabinClass, } : undefined } diff --git a/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select multi-city trip (failed).png b/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select multi-city trip (failed).png new file mode 100644 index 000000000..7b763ba0b Binary files /dev/null and b/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select multi-city trip (failed).png differ diff --git a/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select round trip (failed).png b/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select round trip (failed).png new file mode 100644 index 000000000..66e7f8762 Binary files /dev/null and b/e2e/cypress/screenshots/search-filter.cy.ts/Online Board - Search & Filter -- Filter - Trip Type -- should select round trip (failed).png differ