Flutter Metro Line Card with Station Route Map and Live Train
A transit line card for journey planning apps: an orthogonal route map with station markers, a bend into the return leg, a live train marker sitting between two stops, service status, headline stats and the next departures. Built with Wind utility classes and absolute pixel positioning, no map SDK and no canvas painting.
main.dart
WDiv(
className: 'flex flex-col items-start w-full max-w-sm rounded-3xl bg-white dark:bg-gray-900 p-5',
children: [
WDiv(
className: 'flex flex-row items-center justify-between w-full',
children: [
WDiv(
className: 'flex flex-row items-center',
children: [
WDiv(
className: 'flex flex-row items-center justify-center w-8 h-8 rounded-xl bg-violet-600 dark:bg-violet-500',
child: WText(
'M2',
className: 'text-[11px] font-bold text-white dark:text-white'
),
),
WDiv(
className: 'flex flex-col items-start ml-2',
children: [
WText(
'Violet Line',
className: 'text-sm font-bold text-gray-900 dark:text-white'
),
WText(
'Riverside to Airport T2',
className: 'text-[10px] text-gray-500 dark:text-gray-400'
),
],
),
],
),
WDiv(
className: 'flex flex-row items-center rounded-full bg-emerald-100 dark:bg-emerald-900 px-2 py-1',
children: [
WIcon(
Icons.check_circle,
className: 'text-emerald-600 dark:text-emerald-300 text-xs'
),
WText(
'Good service',
className: 'text-[10px] font-bold text-emerald-700 dark:text-emerald-200 ml-1'
),
],
),
],
),
WDiv(
className: 'relative w-[320px] h-[132px] mt-3 rounded-2xl bg-gray-50 dark:bg-gray-800',
children: [
WDiv(
className: 'absolute left-[15px] top-[31px] w-[286px] h-[6px] rounded-full bg-violet-500 dark:bg-violet-400'
),
WDiv(
className: 'absolute left-[295px] top-[31px] w-[6px] h-[68px] rounded-full bg-violet-500 dark:bg-violet-400'
),
WDiv(
className: 'absolute left-[15px] top-[93px] w-[286px] h-[6px] rounded-full bg-violet-500 dark:bg-violet-400'
),
WDiv(
className: 'absolute left-[12px] top-[28px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[82px] top-[28px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[152px] top-[28px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[222px] top-[28px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[290px] top-[26px] w-[17px] h-[17px] rounded-full bg-white dark:bg-gray-100 border-4 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[222px] top-[90px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[82px] top-[90px] w-[13px] h-[13px] rounded-full bg-white dark:bg-gray-100 border-2 border-violet-600 dark:border-violet-500'
),
WDiv(
className: 'absolute left-[10px] top-[88px] w-[17px] h-[17px] rounded-full bg-violet-600 dark:bg-violet-400 border-4 border-white dark:border-gray-900'
),
WDiv(
className: 'absolute left-[184px] top-[84px] w-[25px] h-[25px] rounded-full bg-violet-200 dark:bg-violet-900'
),
WDiv(
className: 'absolute left-[190px] top-[90px] w-[13px] h-[13px] rounded-full bg-violet-600 dark:bg-violet-300 border-2 border-white dark:border-gray-900'
),
WDiv(
className: 'absolute left-[12px] top-[8px] flex flex-row items-center',
child: WText(
'Riverside',
className: 'text-[10px] font-bold text-gray-700 dark:text-gray-200'
)
),
WDiv(
className: 'absolute left-[232px] top-[8px] flex flex-row items-center',
child: WText(
'Central',
className: 'text-[10px] font-bold text-gray-700 dark:text-gray-200'
)
),
WDiv(
className: 'absolute left-[164px] top-[110px] flex flex-row items-center',
child: WText(
'Train 6021',
className: 'text-[10px] font-bold text-violet-700 dark:text-violet-300'
)
),
WDiv(
className: 'absolute left-[12px] top-[110px] flex flex-row items-center',
child: WText(
'Airport T2',
className: 'text-[10px] font-bold text-gray-700 dark:text-gray-200'
)
),
],
),
WDiv(
className: 'flex flex-row items-center w-full mt-4',
children: [
WDiv(
className: 'flex flex-col items-start w-[104px] rounded-2xl bg-gray-50 dark:bg-gray-800 px-3 py-3',
children: [
WText(
'STATIONS',
className: 'text-[10px] font-bold tracking-wide text-gray-500 dark:text-gray-400'
),
WText(
'9',
className: 'text-lg font-bold text-gray-900 dark:text-white mt-1'
),
],
),
WDiv(
className: 'flex flex-col items-start w-[104px] rounded-2xl bg-gray-50 dark:bg-gray-800 px-3 py-3 ml-2',
children: [
WText(
'END TO END',
className: 'text-[10px] font-bold tracking-wide text-gray-500 dark:text-gray-400'
),
WText(
'26 min',
className: 'text-lg font-bold text-gray-900 dark:text-white mt-1'
),
],
),
WDiv(
className: 'flex flex-col items-start w-[104px] rounded-2xl bg-gray-50 dark:bg-gray-800 px-3 py-3 ml-2',
children: [
WText(
'FREQUENCY',
className: 'text-[10px] font-bold tracking-wide text-gray-500 dark:text-gray-400'
),
WText(
'4 min',
className: 'text-lg font-bold text-gray-900 dark:text-white mt-1'
),
],
),
],
),
WText(
'NEXT DEPARTURES FROM MUSEUM SQUARE',
className: 'text-[10px] font-bold tracking-widest text-gray-500 dark:text-gray-400 mt-3'
),
WDiv(
className: 'flex flex-row items-center justify-between w-full rounded-2xl bg-gray-50 dark:bg-gray-800 px-3 py-3 mt-2',
children: [
WDiv(
className: 'flex flex-col items-start',
children: [
WText(
'Airport T2',
className: 'text-xs font-bold text-gray-900 dark:text-white'
),
WText(
'Platform 1 - arriving',
className: 'text-[10px] text-gray-500 dark:text-gray-400'
),
],
),
WDiv(
className: 'flex flex-row items-center rounded-full bg-emerald-100 dark:bg-emerald-900 px-2 py-1',
children: [
WText(
'Now',
className: 'text-[11px] font-bold text-emerald-700 dark:text-emerald-200'
),
],
),
],
),
WDiv(
className: 'flex flex-row items-center justify-between w-full rounded-2xl bg-gray-50 dark:bg-gray-800 px-3 py-3 mt-2',
children: [
WDiv(
className: 'flex flex-col items-start',
children: [
WText(
'Riverside',
className: 'text-xs font-bold text-gray-900 dark:text-white'
),
WText(
'Platform 2 - 6 cars',
className: 'text-[10px] text-gray-500 dark:text-gray-400'
),
],
),
WDiv(
className: 'flex flex-row items-center rounded-full bg-violet-100 dark:bg-violet-900 px-2 py-1',
children: [
WText(
'4 min',
className: 'text-[11px] font-bold text-violet-700 dark:text-violet-200'
),
],
),
],
),
WDiv(
className: 'flex flex-row items-center w-full rounded-2xl bg-amber-50 dark:bg-amber-950 px-3 py-3 mt-3',
children: [
WIcon(
Icons.warning,
className: 'text-amber-600 dark:text-amber-300 text-base'
),
WText(
'Lift out of service at Central until 6 PM',
className: 'text-xs font-semibold text-amber-800 dark:text-amber-200 ml-2'
),
],
),
WDiv(
className: 'w-full mt-4',
child: WButton(
className: 'flex flex-row items-center justify-center w-full rounded-2xl bg-violet-600 dark:bg-violet-500 px-4 py-3',
child: WDiv(
className: 'flex flex-row items-center',
children: [
WIcon(
Icons.location_on,
className: 'text-white dark:text-white text-base'
),
WText(
'Plan a journey',
className: 'text-sm font-bold text-white dark:text-white ml-2'
),
],
),
),
),
],
)
Stats
- Views
- 13
- Stars
- 0
- Revisions
- 1
- Size
- 9,414 chars
- Created
- Aug 19, 2026