Flight card
A flight option from a travel agent: carrier, times and airports on a drawn route line with the kit's square marks, stops with their layovers, then price, cabin, bags and one select action. Return trips stack their legs.
On this page
Installation
Usage
import { FlightCard } from "@/components/ui/chatcn/flight-card"
<FlightCard
legs={[
{
carrier: "TAP Air Portugal",
logo: <img src={carrierLogo} alt="" />,
departure: { code: "LIS", city: "Lisbon", time: "07:15" },
arrival: { code: "SFO", city: "San Francisco", time: "14:40" },
duration: 1045,
stops: [{ code: "EWR", city: "Newark", duration: 105 }],
},
]}
price={1184}
currency="EUR"
cabin="Economy"
baggage={{ carryOn: 1, checked: 1 }}
onSelect={() => choose(offer.id)}
/>Every widget takes plain props from a tool result, so map the tool output straight onto it. While the call runs, pass loading for a skeleton that matches the final layout; when it fails, pass error (and onRetry). Install with flight-card and nothing else from the kit is required at runtime.
Times are passed already formatted in each airport's local time, the way fare APIs return them; dayOffset adds the +1. The carrier is always text. Logos are yours to supply through logo: the kit ships no airline marks.
The route line
Solid squares mark departure and arrival, hollow squares mark stops. A stop shorter than shortConnection (60 minutes by default), overnight, or with an airport change turns amber and says why, here and in the details.
Examples
Compact options
States
Props
| Prop | Type | Notes |
|---|---|---|
legs | FlightLeg[] | carrier, logo?, label?, date?, departure, arrival, duration, stops?, segments? |
FlightPlace | { code, time, city?, airport?, terminal?, dayOffset? } | |
FlightStop | { code, duration, city?, overnight?, airportChange? } | Layover in minutes |
segments | FlightSegment[] | Each flight for the Details view |
price, currency, locale, priceNote | Round trip, 1 adult | |
cabin, fareName | string | Economy, Classic |
baggage | { carryOn?, checked? } | Reads 1 checked bag, Carry-on only or No bags included |
seatsLeft | number | Amber note |
badge | string | Cheapest, Fastest |
shortConnection | number | Minutes. Default 60 |
selected, onSelect, selectLabel | Selected adds an accent outline | |
layout | "full" | "compact" | Default full |
loading, error, onRetry, empty | States | |
labels | Partial<FlightCardLabels> | Every string the card shows or announces, durations and the spoken leg included, for translation |
Accessibility
- Each leg is read as one sentence: carrier, departure, arrival with any extra day, duration in words and the stops. The drawn line is hidden from screen readers.
- Select is a toggle with
aria-pressed. Details is a disclosure. - Route lines follow the page direction in RTL; times and codes stay in reading order.
Motion
- Details opens by height and opacity in 200 ms, instantly under reduced motion.
- Selecting swaps the label to a check with the kit's 150 ms blur crossfade.