The calendar supports swipe gestures on mobile platforms, allowing users to navigate between pages by swiping left or right.
A FCalendarControl
controls navigation, while a FDateSelectionControl
controls the selection behavior (single date, multiple dates, or a range).
FCalendar, FDateSelectionController, and all FCalendarControllers return DateTimes in UTC timezone, truncated
to the nearest day.
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2040),6 ),7 selectionControl: .managedSingle(),8);9CLI
To generate a specific style for customization:
dart run forui style create calendardart run forui style create calendar-headerdart run forui style create calendar-day-pickerdart run forui style create calendar-month-pickerdart run forui style create calendar-year-pickerUsage
FCalendar.grid(...)
1FCalendar.grid(2 style: const .delta(padding: .value(.zero)),3 fixedWeeks: false,4)FCalendar.splitGrid(...)
1FCalendar.splitGrid(2 style: const .delta(padding: .value(.zero)),3 fixedWeeks: false,4)FCalendar.wheel(...)
1FCalendar.wheel(2 style: const .delta(padding: .value(.zero)),3 fixedWeeks: false,4)Examples
Fixed Weeks
By default, the day grid adjusts its height to each month's 4 — 6 weeks. Set fixedWeeks: true to keep the calendar's
height constant.
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 today: DateTime.utc(2026, 2, 15),6 initial: DateTime.utc(2026, 2, 15),7 end: DateTime.utc(2030),8 ),9 selectionControl: .managedSingle(),10 fixedWeeks: true,11);12Modes
Split Grid
1@override2Widget build(BuildContext _) => FCalendar.splitGrid(3 control: FGridSplitCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2040),6 ),7 selectionControl: .managedSingle(),8);9Month-Year Wheel
1@override2Widget build(BuildContext _) => FCalendar.wheel(3 control: FWheelCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2040),6 ),7 selectionControl: .managedSingle(),8);9Selection
Single Date
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2040),6 ),7 selectionControl: .managedSingle(),8);9Multiple Dates
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 today: DateTime.utc(2026, 7, 15),6 end: DateTime.utc(2030),7 ),8 selectionControl: .managedMulti(9 initial: {DateTime.utc(2026, 7, 17), DateTime.utc(2026, 7, 20)},10 ),11);12Range Selection
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 today: DateTime.utc(2026, 7, 15),6 end: DateTime.utc(2030),7 ),8 selectionControl: .managedRange(9 initial: (DateTime.utc(2026, 7, 17), DateTime.utc(2026, 7, 20)),10 ),11);12Display Only
Pass selectionControl: .none() to render a read-only calendar that selects nothing.
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2030),6 ),7 selectionControl: .none(),8);9Unselectable Dates
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 selectable: (date) =>5 !{DateTime.utc(2026, 7, 18), DateTime.utc(2026, 7, 19)}.contains(date),6 start: DateTime.utc(2000),7 today: DateTime.utc(2026, 7, 15),8 end: DateTime.utc(2030),9 ),10 selectionControl: .managedMulti(11 initial: {DateTime.utc(2026, 7, 17), DateTime.utc(2026, 7, 20)},12 ),13);14Custom Footer with Presets
1@override2Widget build(BuildContext _) => FCalendar.grid(3 control: FGridCalendarControl(4 start: DateTime.utc(2000),5 end: DateTime.utc(2030),6 ),7 selectionControl: .managedSingle(),8 footerBuilder: (context, controller, selectionController) => Padding(9 padding: const .only(top: 8),10 child: Wrap(11 spacing: 6,12 runSpacing: 6,13 alignment: .center,14 children: [15 for (final (label, date) in [16 ('Today', controller.today),17 ('In a week', controller.today.add(const Duration(days: 7))),18 ('In a month', controller.today.add(const Duration(days: 30))),19 ])20 FButton(21 variant: .outline,22 size: .sm,23 mainAxisSize: .min,24 onPress: () async {25 selectionController.select(date);26 await controller.animateToDayPicker(date);27 },28 child: Text(label),29 ),30 ],31 ),32 ),33);34Badge
A badge draws attention to specific information, such as labels and counts. Use badges to display status, notifications, or small pieces of information that need to stand out.
Card
A flexible container component that displays content with an optional title, subtitle, and child widget. Cards are commonly used to group related information and actions.