From 71e4fc790a337de7bab1885ce6deb0c67322829e Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 09:17:24 +0800 Subject: [PATCH 01/21] Update calendar.dart Change header widget --- lib/src/calendar.dart | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index 672e63d..f16422d 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -24,6 +24,11 @@ typedef List CalendarEventBuilder(DateTime start, DateTime end); /// typedef Widget CalendarWidgetBuilder(BuildContext context, CalendarEvent index); +/// +/// Widget for customizing a specific title to display the desired content +/// +typedef Widget CalendarHeaderBuilder(BuildContext context, CalendarWidgetState? state); + /// /// The widget to show the calendar with a header that displays the /// current month, drop down and then the events in a sliverlist. @@ -131,7 +136,7 @@ class CalendarWidget extends StatefulWidget { final bool tapToCloseHeader; /// The header to display. - final Widget? header; + final CalendarHeaderBuilder? header; @override State createState() { @@ -273,8 +278,8 @@ class CalendarWidgetState extends State { mainAxisAlignment: MainAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start, children: [ - widget.header ?? - CalendarHeader( + widget.header != null ? widget.header!(context, this) + : CalendarHeader( this, widget.bannerHeader, widget.location, From c7e35b7f821d99c518b35aef7f1ecddad6f9efe0 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 16:05:35 +0800 Subject: [PATCH 02/21] Update sliverscrollviewcalendar.dart --- lib/src/sliverscrollviewcalendar.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/src/sliverscrollviewcalendar.dart b/lib/src/sliverscrollviewcalendar.dart index eb6e3f1..abcb6ec 100644 --- a/lib/src/sliverscrollviewcalendar.dart +++ b/lib/src/sliverscrollviewcalendar.dart @@ -152,7 +152,7 @@ class SliverScrollViewCalendarElement extends StatelessElement parentData = currentChild.parentData as SliverMultiBoxAdaptorParentData?; debugPrint('finding index ${parentData!.index} $currentChild'); - } while (parentData.index != scrollToIndex); + } while (parentData!.index != scrollToIndex); if (parentData.index == scrollToIndex) { // Yay! Scroll there and end. calendarWidget.controller!.animateTo(parentData.layoutOffset!, From bc693df8bef5ced5b4b60473cd67ad45fa2704cf Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 16:06:28 +0800 Subject: [PATCH 03/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 114 +++++++++++++++++++++--------------- 1 file changed, 68 insertions(+), 46 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index cc54476..5f87742 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -104,8 +104,8 @@ class _CalendarHeaderState extends State AnimationController(duration: _kExpand, vsync: this); late CurvedAnimation _easeInAnimation; late Animation _iconTurns; - bool myExpandedState = false; late int _monthIndex; + bool myExpandedState = false; int? _beginningMonthIndex; int? _endingMonthIndex; @@ -128,17 +128,16 @@ class _CalendarHeaderState extends State int ms = (widget.state.currentTopDisplayIndex + 1) * Duration.millisecondsPerDay; DateTime currentTopTemp = DateTime.fromMillisecondsSinceEpoch(ms); - _monthIndex = monthIndexFromTime(currentTopTemp); }); }); _headerExpandedSubscription = widget.state.headerExpandedChangeStream!.listen((bool change) { if (myExpandedState != change) { - setState(() { + // setState(() { myExpandedState = change; _doAnimation(); - }); + // }); } }); } @@ -147,11 +146,12 @@ class _CalendarHeaderState extends State if (myExpandedState) { _controller.forward(); } else { - _controller.reverse().then((void value) { - setState(() { - // Rebuild without widget.children. - }); - }); + _controller.reverse(); + // _controller.reverse().then((void value) { + // setState(() { + // // Rebuild without widget.children. + // }); + // }); } } @@ -164,14 +164,14 @@ class _CalendarHeaderState extends State } void _handleOpen() { - setState(() { + // setState(() { // Jump the page controller to the right spot. myExpandedState = !widget.state.headerExpanded; widget.state.headerExpanded = myExpandedState; _doAnimation(); PageStorage.of(context) ?.writeState(context, widget.state..headerExpanded); - }); + // }); } Widget _buildChildren(BuildContext context, Widget? child) { @@ -208,13 +208,13 @@ class _CalendarHeaderState extends State }); }, child: _CalendarMonthDisplay( - widget.state, - widget._location, - monthToShow(_monthIndex), - widget.weekBeginsWithDay, - widget.dayIndicator, - widget.eventIndicator, - ), + sharedState: widget.state, + location: widget._location, + displayDate: monthToShow(_monthIndex), + weekBeginsWithDay: widget.weekBeginsWithDay, + dayIndicator: widget.dayIndicator, + eventIndicator: widget.eventIndicator), + ), ), ), @@ -227,7 +227,7 @@ class _CalendarHeaderState extends State @override Widget build(BuildContext context) { return Material( - elevation: 4.0, + elevation: 0.0, color: widget.color ?? Colors.white, child: AnimatedBuilder( animation: _controller, @@ -287,6 +287,10 @@ class _CalendarHeaderState extends State ), ); } + + void refresh() { + Future.delayed(const Duration(milliseconds: 600), () => setState(() {})); + } } /// @@ -314,26 +318,40 @@ class _CalendarEventIndicator extends CustomPainter { /// The animated container to show for the month with all the days and the /// day headers. /// -class _CalendarMonthDisplay extends StatelessWidget { - _CalendarMonthDisplay(this.sharedState, this.location, this.displayDate, - this.weekBeginsWithDay, this.dayIndicator, this.eventIndicator); - +class _CalendarMonthDisplay extends StatefulWidget { final CalendarWidgetState sharedState; final Location location; - final DateTime displayDate; final int weekBeginsWithDay; final HeaderDayIndicator? dayIndicator; final EventIndicator? eventIndicator; + final DateTime displayDate; + final Duration week = Duration(days: 7); + + _CalendarMonthDisplay( + {Key? key, + required this.sharedState, + required this.location, + required this.weekBeginsWithDay, + this.dayIndicator, + this.eventIndicator, + required this.displayDate}) + : super(key: key); + + @override + _CalendarMonthDisplayState createState() => _CalendarMonthDisplayState(); +} - static final Duration week = Duration(days: 7); +class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { + DateTime selectedDay = clock.now(); Widget _eventIndicator(Widget button, int eventIndex) { - if (sharedState.events.containsKey(eventIndex)) { - if (eventIndicator != null) { - return eventIndicator!(button, sharedState.events[eventIndex]); + if (widget.sharedState.events.containsKey(eventIndex)) { + if (widget.eventIndicator != null) { + return widget.eventIndicator!( + button, widget.sharedState.events[eventIndex]); } List eventIndicators = []; - for (CalendarEvent event in sharedState.events[eventIndex]!) { + for (CalendarEvent event in widget.sharedState.events[eventIndex]!) { eventIndicators.add( SizedBox( height: 4.0, @@ -368,8 +386,8 @@ class _CalendarMonthDisplay extends StatelessWidget { ), ); } else { - if (eventIndicator != null) { - return eventIndicator!(button, []); + if (widget.eventIndicator != null) { + return widget.eventIndicator!(button, []); } return SizedBox( width: 40.0, @@ -382,30 +400,34 @@ class _CalendarMonthDisplay extends StatelessWidget { Widget _buildButton(ThemeData theme, DateTime day, DateTime nowTime) { Widget button; // Only show days in the current month. - if (day.month != displayDate.month) { + if (day.month != widget.displayDate.month) { button = SizedBox(width: 1.0); } else { - if (dayIndicator != null) { - button = dayIndicator!(theme, day, nowTime); + if (widget.dayIndicator != null) { + button = widget.dayIndicator!(theme, day, nowTime); } else { button = Center( child: TextButton( style: TextButton.styleFrom( - primary: day.isAtSameMomentAs(nowTime) + primary: Colors.black54, + backgroundColor: day.isAtSameMomentAs(nowTime) ? theme.accentColor - : day.isAtSameMomentAs(displayDate) + : day.isAtSameMomentAs(selectedDay) ? Colors.grey.shade200 - : Colors.white, + : null, shape: CircleBorder(), padding: EdgeInsets.zero, ), child: Text(day.day.toString()), - onPressed: () => sharedState.scrollToDay(day), + onPressed: () => setState(() { + selectedDay = day; + widget.sharedState.scrollToDay(day); + }), ), ); } } - int eventIndex = CalendarEvent.indexFromMilliseconds(day, location); + int eventIndex = CalendarEvent.indexFromMilliseconds(day, widget.location); return _eventIndicator(button, eventIndex); } @@ -413,18 +435,18 @@ class _CalendarMonthDisplay extends StatelessWidget { Widget build(BuildContext context) { DateTime nowTmp = clock.now(); DateTime nowTime = DateTime(nowTmp.year, nowTmp.month, nowTmp.day); - DateTime topFirst = displayDate; + DateTime topFirst = widget.displayDate; topFirst = - topFirst.subtract(Duration(days: topFirst.weekday - weekBeginsWithDay)); - DateTime topSecond = topFirst.add(week); + topFirst.subtract(Duration(days: topFirst.weekday - widget.weekBeginsWithDay)); + DateTime topSecond = topFirst.add(widget.week); if (topSecond.day == 1) { // Opps, out by a week. topFirst = topSecond; - topSecond = topFirst.add(week); + topSecond = topFirst.add(widget.week); } - DateTime topThird = topSecond.add(week); - DateTime topFourth = topThird.add(week); - DateTime topFifth = topFourth.add(week); + DateTime topThird = topSecond.add(widget.week); + DateTime topFourth = topThird.add(widget.week); + DateTime topFifth = topFourth.add(widget.week); List dayHeaders = []; List firstDays = []; List secondDays = []; From cbb1fe4308accec717a20f74ab51a3a15b8a1fbf Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 16:08:02 +0800 Subject: [PATCH 04/21] Update calendar.dart --- lib/src/calendar.dart | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index f16422d..83ef634 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -24,11 +24,6 @@ typedef List CalendarEventBuilder(DateTime start, DateTime end); /// typedef Widget CalendarWidgetBuilder(BuildContext context, CalendarEvent index); -/// -/// Widget for customizing a specific title to display the desired content -/// -typedef Widget CalendarHeaderBuilder(BuildContext context, CalendarWidgetState? state); - /// /// The widget to show the calendar with a header that displays the /// current month, drop down and then the events in a sliverlist. @@ -70,7 +65,8 @@ class CalendarWidget extends StatefulWidget { this.headerMonthStyle, this.headerExpandIconColor, this.tapToCloseHeader = true, - this.header, + this.leading, + this.trailing, }) : beginningRangeDate = beginningRangeDate ?? TZDateTime(location ?? local, 2010), endingRangeDate = endingRangeDate ?? @@ -135,8 +131,11 @@ class CalendarWidget extends StatefulWidget { /// If you can close the header with a tap. final bool tapToCloseHeader; - /// The header to display. - final CalendarHeaderBuilder? header; + /// The leading to display. + final Widget? leading; + + /// The trailing to display. + final Widget? trailing; @override State createState() { @@ -278,8 +277,10 @@ class CalendarWidgetState extends State { mainAxisAlignment: MainAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start, children: [ - widget.header != null ? widget.header!(context, this) - : CalendarHeader( + ListTile( + contentPadding:EdgeInsets.all(0), + leading: widget.leading ?? null, + title: CalendarHeader( this, widget.bannerHeader, widget.location, @@ -291,6 +292,8 @@ class CalendarWidgetState extends State { null, widget.beginningRangeDate, widget.endingRangeDate), + trailing: widget.trailing ?? null + ), Expanded( child: Padding( padding: EdgeInsets.only(top: 5.0), From 3652e4b2f29bc5e6e21e017302f851c5a1041c61 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 16:56:30 +0800 Subject: [PATCH 05/21] Update calendarheader.dart Add leading and trailing widgets on header bar. --- lib/src/calendarheader.dart | 64 +++++++++++++++++++++---------------- 1 file changed, 37 insertions(+), 27 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 5f87742..43a9393 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -62,7 +62,10 @@ class CalendarHeader extends StatefulWidget { this.dayIndicator, this.eventIndicator, this.beginningRangeDate, - this.endingRangeDate) + this.endingRangeDate, + this.leading, + this.trailing + ) : _location = location; final Location _location; @@ -76,6 +79,8 @@ class CalendarHeader extends StatefulWidget { final HeaderDayIndicator? dayIndicator; final TZDateTime beginningRangeDate; final TZDateTime endingRangeDate; + final Widget? leading; + final Widget? trailing; @override State createState() { @@ -256,33 +261,38 @@ class _CalendarHeaderState extends State ) : null, ), - child: GestureDetector( - onTap: _handleOpen, - child: Row( - mainAxisSize: MainAxisSize.max, - children: [ - Text( - (myExpandedState - ? MaterialLocalizations.of(context) - .formatMonthYear(monthToShow(_monthIndex)) - : MaterialLocalizations.of(context) - .formatMonthYear(currentTop)) + - ' ', - style: widget.headerStyle ?? - Theme.of(context) - .textTheme - .headline6! - .copyWith(fontSize: 25.0), - ), - RotationTransition( - turns: _iconTurns, - child: Icon( - Icons.expand_more, - color: widget.expandIconColor ?? Colors.black, - size: 25.0, + child: ListTile( + contentPadding: const EdgeInsets.all(0), + leading: widget.leading ?? null, + trailing: widget.trailing ?? null, + title: GestureDetector( + onTap: _handleOpen, + child: Row( + mainAxisSize: MainAxisSize.max, + children: [ + Text( + (myExpandedState + ? MaterialLocalizations.of(context) + .formatMonthYear(monthToShow(_monthIndex)) + : MaterialLocalizations.of(context) + .formatMonthYear(currentTop)) + + ' ', + style: widget.headerStyle ?? + Theme.of(context) + .textTheme + .headline6! + .copyWith(fontSize: 25.0), ), - ), - ], + RotationTransition( + turns: _iconTurns, + child: Icon( + Icons.expand_more, + color: widget.expandIconColor ?? Colors.black, + size: 25.0, + ), + ), + ], + ), ), ), ); From 3d5b2e6d4aa7467490025bc9a3625fbbb28ae373 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 16:59:28 +0800 Subject: [PATCH 06/21] Update calendar.dart Remove custom header widget, then add the leading and trailing widgets. --- lib/src/calendar.dart | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index 83ef634..e0975ea 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -277,10 +277,7 @@ class CalendarWidgetState extends State { mainAxisAlignment: MainAxisAlignment.start, crossAxisAlignment: CrossAxisAlignment.start, children: [ - ListTile( - contentPadding:EdgeInsets.all(0), - leading: widget.leading ?? null, - title: CalendarHeader( + CalendarHeader( this, widget.bannerHeader, widget.location, @@ -291,9 +288,9 @@ class CalendarWidgetState extends State { null, null, widget.beginningRangeDate, - widget.endingRangeDate), - trailing: widget.trailing ?? null - ), + widget.endingRangeDate, + widget.leading, + widget.trailing), Expanded( child: Padding( padding: EdgeInsets.only(top: 5.0), From b766c8843a0c68912868ee68b82bfa12f9ef7643 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 20:28:44 +0800 Subject: [PATCH 07/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 80 ++++++++++++++++++++----------------- 1 file changed, 43 insertions(+), 37 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 43a9393..cb7dbdd 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -39,6 +39,11 @@ typedef HeaderDayIndicator = Widget Function( typedef EventIndicator = Widget Function( Widget button, List? events); +/// +/// Widget for customizing a specific title to display the desired content +/// +typedef Widget CalendarHeaderBuilder(BuildContext context, CalendarWidgetState? state); + /// /// Displays the header for the calendar. This handles the title with the /// month/year and a drop down item as well as opening to show the whole month. @@ -63,7 +68,6 @@ class CalendarHeader extends StatefulWidget { this.eventIndicator, this.beginningRangeDate, this.endingRangeDate, - this.leading, this.trailing ) : _location = location; @@ -79,8 +83,7 @@ class CalendarHeader extends StatefulWidget { final HeaderDayIndicator? dayIndicator; final TZDateTime beginningRangeDate; final TZDateTime endingRangeDate; - final Widget? leading; - final Widget? trailing; + final CalendarHeaderBuilder? trailing; @override State createState() { @@ -263,44 +266,47 @@ class _CalendarHeaderState extends State ), child: ListTile( contentPadding: const EdgeInsets.all(0), - leading: widget.leading ?? null, - trailing: widget.trailing ?? null, - title: GestureDetector( - onTap: _handleOpen, - child: Row( - mainAxisSize: MainAxisSize.max, - children: [ - Text( - (myExpandedState - ? MaterialLocalizations.of(context) - .formatMonthYear(monthToShow(_monthIndex)) - : MaterialLocalizations.of(context) - .formatMonthYear(currentTop)) + - ' ', - style: widget.headerStyle ?? - Theme.of(context) - .textTheme - .headline6! - .copyWith(fontSize: 25.0), - ), - RotationTransition( - turns: _iconTurns, - child: Icon( - Icons.expand_more, - color: widget.expandIconColor ?? Colors.black, - size: 25.0, - ), - ), - ], - ), + leading: widget.state.widget.leading ?? null, + title: Row( + mainAxisSize: MainAxisSize.max, + mainAxisAlignment: MainAxisAlignment.spaceBetween, + children: [ + GestureDetector( + onTap: _handleOpen, + child: Row( + mainAxisSize: MainAxisSize.max, + children: [ + Text( + (myExpandedState + ? MaterialLocalizations.of(context) + .formatMonthYear(monthToShow(_monthIndex)) + : MaterialLocalizations.of(context) + .formatMonthYear(currentTop)) + + ' ', + style: widget.headerStyle ?? + Theme.of(context) + .textTheme + .headline6! + .copyWith(fontSize: 25.0), + ), + RotationTransition( + turns: _iconTurns, + child: Icon( + Icons.expand_more, + color: widget.expandIconColor ?? Colors.black, + size: 25.0, + ), + ), + ] + ) + ), + widget.trailing != null ? + widget.trailing!(context, widget.state) : Container() + ] ), ), ); } - - void refresh() { - Future.delayed(const Duration(milliseconds: 600), () => setState(() {})); - } } /// From 1f3a3f82eeeb397303bb893c2a0a3603bb347e57 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 20:37:41 +0800 Subject: [PATCH 08/21] Update calendar.dart --- lib/src/calendar.dart | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index e0975ea..a05a5e4 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -24,6 +24,11 @@ typedef List CalendarEventBuilder(DateTime start, DateTime end); /// typedef Widget CalendarWidgetBuilder(BuildContext context, CalendarEvent index); +/// +/// Widget for customizing a specific title to display the desired content +/// +// typedef Widget CalendarHeaderBuilder(BuildContext context, CalendarWidgetState? state); + /// /// The widget to show the calendar with a header that displays the /// current month, drop down and then the events in a sliverlist. @@ -135,7 +140,7 @@ class CalendarWidget extends StatefulWidget { final Widget? leading; /// The trailing to display. - final Widget? trailing; + final CalendarHeaderBuilder? trailing; @override State createState() { From 7ba895f4f9798551c69684542269c512df9b975e Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 20:38:28 +0800 Subject: [PATCH 09/21] Update calendar.dart --- lib/src/calendar.dart | 5 ----- 1 file changed, 5 deletions(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index a05a5e4..ab9e6be 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -24,11 +24,6 @@ typedef List CalendarEventBuilder(DateTime start, DateTime end); /// typedef Widget CalendarWidgetBuilder(BuildContext context, CalendarEvent index); -/// -/// Widget for customizing a specific title to display the desired content -/// -// typedef Widget CalendarHeaderBuilder(BuildContext context, CalendarWidgetState? state); - /// /// The widget to show the calendar with a header that displays the /// current month, drop down and then the events in a sliverlist. From c65a997cd7cf93aced3113368b186110d512662b Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 20:38:56 +0800 Subject: [PATCH 10/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index cb7dbdd..9cbd556 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -68,6 +68,7 @@ class CalendarHeader extends StatefulWidget { this.eventIndicator, this.beginningRangeDate, this.endingRangeDate, + this.leading, this.trailing ) : _location = location; @@ -83,6 +84,7 @@ class CalendarHeader extends StatefulWidget { final HeaderDayIndicator? dayIndicator; final TZDateTime beginningRangeDate; final TZDateTime endingRangeDate; + final Widget? leading; final CalendarHeaderBuilder? trailing; @override @@ -266,7 +268,7 @@ class _CalendarHeaderState extends State ), child: ListTile( contentPadding: const EdgeInsets.all(0), - leading: widget.state.widget.leading ?? null, + leading: widget.leading ?? null, title: Row( mainAxisSize: MainAxisSize.max, mainAxisAlignment: MainAxisAlignment.spaceBetween, From 13af619804f1d834bbc76327bcae5c1bfb9b1a2f Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Sun, 28 Mar 2021 20:43:23 +0800 Subject: [PATCH 11/21] Update main.dart --- example/lib/main.dart | 161 +++++++++++++++++++++++------------------- 1 file changed, 89 insertions(+), 72 deletions(-) diff --git a/example/lib/main.dart b/example/lib/main.dart index 02d5076..fb5b5cb 100644 --- a/example/lib/main.dart +++ b/example/lib/main.dart @@ -1,37 +1,23 @@ -import 'dart:async'; import 'dart:math'; -import 'dart:typed_data'; - import 'package:flutter/material.dart'; -import 'package:flutter/services.dart' show rootBundle; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_native_timezone/flutter_native_timezone.dart'; import 'package:sliver_calendar/sliver_calendar.dart'; -import 'package:timezone/timezone.dart'; +import 'package:timezone/timezone.dart' as tz; +import 'package:timezone/data/latest.dart' as tz; void main() async { - // Comment this line to enable debug printing... - debugPrint = (String message, {int wrapWidth}) {}; - - ByteData loadedData; - - await Future.wait(>[ - rootBundle.load('assets/timezone/2018c.tzf').then((ByteData data) { - loadedData = data; - print('loaded data'); - }) - ]); - initializeDatabase(loadedData.buffer.asUint8List()); - runApp(new MyApp()); + tz.initializeTimeZones(); + runApp(MyApp()); } class MyApp extends StatelessWidget { // This widget is the root of your application. @override Widget build(BuildContext context) { - return new MaterialApp( + return MaterialApp( title: 'Flutter Calendar', - theme: new ThemeData( + theme: ThemeData( primarySwatch: Colors.blue, ), debugShowCheckedModeBanner: false, @@ -40,10 +26,9 @@ class MyApp extends StatelessWidget { GlobalMaterialLocalizations.delegate ], supportedLocales: const [ - const Locale('en', ''), - const Locale('fr', ''), + Locale('en', ''), ], - home: new MyHomePage(title: 'Flutter Calendar demo'), + home: MyHomePage(title: 'Flutter Calendar demo'), ); } } @@ -53,35 +38,53 @@ class MyHomePage extends StatefulWidget { final String title; @override - _MyHomePageState createState() => new _MyHomePageState(); + _MyHomePageState createState() => _MyHomePageState(); } class _MyHomePageState extends State { List events = []; - Location loc; - Random random = new Random(); + Random random = Random(); + tz.Location loc; - Widget buildItem(BuildContext context, CalendarEvent e) { - return new Card( - child: new ListTile( - title: new Text("Event ${e.index}"), - subtitle: new Text("Yay for events"), - leading: const Icon(Icons.gamepad), + Widget trailingWidget(BuildContext ctx, CalendarWidgetState state) { + return IconButton( + icon: Icon(Icons.today_outlined), + onPressed: () { + state.scrollToDay(DateTime.now()); + }); + } + + Widget buildItem(BuildContext ctx, CalendarEvent e) { + return Card( + shape: Border(left: BorderSide(color: Colors.blue, width: 3)), + child: Material( + type: MaterialType.transparency, + child: InkWell( + child: ListTile( + title: Text("Event:${e.index}"), + subtitle: Text("have fun..."), + leading: const Icon(Icons.grass), + ), + onTap: () { + print([e.index, e.instant.month, e.instant.day]); + // s.s + }, + ), ), ); } List getEvents(DateTime start, DateTime end) { - if (loc != null && events.length == 0) { - TZDateTime nowTime = - new TZDateTime.now(loc).subtract(new Duration(days: 5)); + if (loc != null && events.isEmpty) { + tz.TZDateTime nowTime = + tz.TZDateTime.now(loc).subtract(Duration(days: 5)); for (int i = 0; i < 20; i++) { - TZDateTime start = - nowTime.add(new Duration(days: i + random.nextInt(10))); - events.add(new CalendarEvent( + tz.TZDateTime start = + nowTime.add(Duration(days: i + random.nextInt(10))); + events.add(CalendarEvent( index: i, instant: start, - instantEnd: start.add(new Duration(minutes: 30)))); + instantEnd: start.add(Duration(minutes: 30)))); } } return events; @@ -89,40 +92,54 @@ class _MyHomePageState extends State { @override Widget build(BuildContext context) { - return new Scaffold( - appBar: new AppBar( - title: new Text(widget.title), + return Scaffold( + body: SafeArea( + child: Column( + children: [ + FutureBuilder( + future: FlutterNativeTimezone.getLocalTimezone(), + builder: (BuildContext context, AsyncSnapshot tzone) { + if (tzone.hasData) { + loc = tz.getLocation(tzone.data); + tz.TZDateTime nowTime = tz.TZDateTime.now(loc); + return Expanded( + child: CalendarWidget( + initialDate: nowTime, + location: loc, + buildItem: buildItem, + getEvents: getEvents, + headerColor: Colors.lightBlue, + tapToCloseHeader: false, + leading: IconButton( + icon: Icon(Icons.menu), + onPressed: () { + print("Clicked menu"); + }), + trailing: trailingWidget, + headerMonthStyle: + TextStyle(color: Colors.black87, fontSize: 18.0), + monthHeader: + AssetImage("assets/images/calendarbanner.jpg"), + weekBeginsWithDay: + 0, // Sunday = 0, Monday = 1, Tuesday = 2, ..., Saturday = 6 + ), + ); + } else { + return Center( + child: Text("Getting the timezone..."), + ); + } + }, + ), + ], + ), ), - body: new Column( - children: [ - new FutureBuilder( - future: FlutterNativeTimezone.getLocalTimezone(), - builder: (BuildContext context, AsyncSnapshot tz) { - if (tz.hasData) { - loc = getLocation(tz.data); - TZDateTime nowTime = new TZDateTime.now(loc); - return new Expanded( - child: new CalendarWidget( - initialDate: nowTime, - location: loc, - buildItem: buildItem, - getEvents: getEvents, - bannerHeader: - new AssetImage("assets/images/calendarheader.png"), - monthHeader: - new AssetImage("assets/images/calendarbanner.jpg"), - weekBeginsWithDay: - 1, // Sunday = 0, Monday = 1, Tuesday = 2, ..., Saturday = 6 - ), - ); - } else { - return new Center( - child: new Text("Getting the timezone..."), - ); - } - }, - ), - ], + floatingActionButton: FloatingActionButton( + mini: true, + child: Icon(Icons.add), + onPressed: () { + print("hahaha"); + }, ), ); } From a24e1031f3b79fcf4d7f4429398c8dc2381683d6 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Tue, 30 Mar 2021 13:37:05 +0800 Subject: [PATCH 12/21] Update calendar.dart --- lib/src/calendar.dart | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/lib/src/calendar.dart b/lib/src/calendar.dart index ab9e6be..b469d45 100644 --- a/lib/src/calendar.dart +++ b/lib/src/calendar.dart @@ -53,7 +53,7 @@ class CalendarWidget extends StatefulWidget { required this.getEvents, TZDateTime? beginningRangeDate, TZDateTime? endingRangeDate, - this.bannerHeader, + this.dayIndicator, this.monthHeader, Key? key, this.view = CalendarViewType.Schedule, @@ -116,8 +116,8 @@ class CalendarWidget extends StatefulWidget { /// the header to use at the top of each momth. final ImageProvider? monthHeader; - /// the header to use at the top of the banner. - final ImageProvider? bannerHeader; + /// Indicators for custom dates + final HeaderDayIndicator? dayIndicator; /// The color of the header. final Color? headerColor; @@ -279,13 +279,12 @@ class CalendarWidgetState extends State { children: [ CalendarHeader( this, - widget.bannerHeader, widget.location, widget.headerColor, widget.headerMonthStyle, widget.headerExpandIconColor, widget.weekBeginsWithDay, - null, + widget.dayIndicator, null, widget.beginningRangeDate, widget.endingRangeDate, From ab162e9ea90b9937867657dad03c2b6fb7733e03 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Tue, 30 Mar 2021 13:38:57 +0800 Subject: [PATCH 13/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 25 +++++-------------------- 1 file changed, 5 insertions(+), 20 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 9cbd556..f8e91ea 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -28,7 +28,7 @@ final Duration _kExpand = Duration(milliseconds: 200); /// ); /// typedef HeaderDayIndicator = Widget Function( - ThemeData theme, DateTime day, DateTime nowTime); + BuildContext context, DateTime day, CalendarWidgetState? state); /// /// Generates the small boxes on the calendar to indicate that there are events @@ -58,7 +58,6 @@ class CalendarHeader extends StatefulWidget { /// CalendarHeader( this.state, - this.bannerHeader, Location location, this.color, this.headerStyle, @@ -70,12 +69,10 @@ class CalendarHeader extends StatefulWidget { this.endingRangeDate, this.leading, this.trailing - ) - : _location = location; + ) : _location = location; final Location _location; final CalendarWidgetState state; - final ImageProvider? bannerHeader; final Color? color; final TextStyle? headerStyle; final Color? expandIconColor; @@ -157,11 +154,6 @@ class _CalendarHeaderState extends State _controller.forward(); } else { _controller.reverse(); - // _controller.reverse().then((void value) { - // setState(() { - // // Rebuild without widget.children. - // }); - // }); } } @@ -255,16 +247,9 @@ class _CalendarHeaderState extends State DateTime(currentTopTemp.year, currentTopTemp.month, currentTopTemp.day); return Container( - padding: EdgeInsets.only(top: 10.0, left: 5.0, bottom: 10.0), + padding: EdgeInsets.only(left: 5.0), decoration: BoxDecoration( - color: widget.color ?? Colors.white, - image: widget.bannerHeader != null - ? DecorationImage( - image: widget.bannerHeader!, - fit: BoxFit.fitHeight, - alignment: Alignment(1.0, 1.0), - ) - : null, + color: widget.color ?? Colors.white ), child: ListTile( contentPadding: const EdgeInsets.all(0), @@ -422,7 +407,7 @@ class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { button = SizedBox(width: 1.0); } else { if (widget.dayIndicator != null) { - button = widget.dayIndicator!(theme, day, nowTime); + button = widget.dayIndicator!(context, day, widget.sharedState); } else { button = Center( child: TextButton( From 140b4757d3f30319766f99436bc7e1ad19d1a7b6 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Tue, 30 Mar 2021 13:40:20 +0800 Subject: [PATCH 14/21] Update sliverscrollviewcalendar.dart --- lib/src/sliverscrollviewcalendar.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/src/sliverscrollviewcalendar.dart b/lib/src/sliverscrollviewcalendar.dart index abcb6ec..cb93ae7 100644 --- a/lib/src/sliverscrollviewcalendar.dart +++ b/lib/src/sliverscrollviewcalendar.dart @@ -151,7 +151,7 @@ class SliverScrollViewCalendarElement extends StatelessElement currentChild = _state.renderSliverList.childAfter(currentChild)!; parentData = currentChild.parentData as SliverMultiBoxAdaptorParentData?; - debugPrint('finding index ${parentData!.index} $currentChild'); + // debugPrint('finding index ${parentData!.index} $currentChild'); } while (parentData!.index != scrollToIndex); if (parentData.index == scrollToIndex) { // Yay! Scroll there and end. From eca3ff89914ed2960fd3b6e5bf33f387c28ba6a5 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Tue, 30 Mar 2021 13:44:33 +0800 Subject: [PATCH 15/21] Update main.dart --- example/lib/main.dart | 42 ++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 40 insertions(+), 2 deletions(-) diff --git a/example/lib/main.dart b/example/lib/main.dart index fb5b5cb..15fcecc 100644 --- a/example/lib/main.dart +++ b/example/lib/main.dart @@ -1,4 +1,5 @@ import 'dart:math'; +import 'package:intl/intl.dart'; import 'package:flutter/material.dart'; import 'package:flutter_localizations/flutter_localizations.dart'; import 'package:flutter_native_timezone/flutter_native_timezone.dart'; @@ -44,16 +45,52 @@ class MyHomePage extends StatefulWidget { class _MyHomePageState extends State { List events = []; Random random = Random(); + DateTime _now = DateTime.now(); + DateTime selectedDate; + DateTime nowDate; tz.Location loc; + @override + void initState() { + super.initState(); + selectedDate = _now; + nowDate = DateTime(_now.year, _now.month, _now.day); + } + Widget trailingWidget(BuildContext ctx, CalendarWidgetState state) { return IconButton( icon: Icon(Icons.today_outlined), onPressed: () { - state.scrollToDay(DateTime.now()); + state.scrollToDay(nowDate); }); } + Widget dayIndicatorWidget(BuildContext c, DateTime d, CalendarWidgetState s) { + return GestureDetector( + child: Container( + alignment: Alignment.center, + decoration: BoxDecoration( + color: d.isAtSameMomentAs(nowDate) + ? Colors.lime + : d.isAtSameMomentAs(selectedDate) + ? Colors.grey.shade200 + : null, + shape: BoxShape.circle), + child: Text( + d.day.toString(), + style: TextStyle(color: Colors.black54), + ), + ), + onDoubleTap: () { + print("Double click"); + }, + onTap: () => setState(() { + selectedDate = d; + s.scrollToDay(d); + }), + ); + } + Widget buildItem(BuildContext ctx, CalendarEvent e) { return Card( shape: Border(left: BorderSide(color: Colors.blue, width: 3)), @@ -108,14 +145,15 @@ class _MyHomePageState extends State { location: loc, buildItem: buildItem, getEvents: getEvents, - headerColor: Colors.lightBlue, tapToCloseHeader: false, + dayIndicator: dayIndicatorWidget, leading: IconButton( icon: Icon(Icons.menu), onPressed: () { print("Clicked menu"); }), trailing: trailingWidget, + headerColor: Colors.lightBlue, headerMonthStyle: TextStyle(color: Colors.black87, fontSize: 18.0), monthHeader: From bd0dd9dc7f3f88021f612654b90bf19bd009bb33 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Wed, 31 Mar 2021 21:13:24 +0800 Subject: [PATCH 16/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 27 ++++++++++++++++----------- 1 file changed, 16 insertions(+), 11 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index f8e91ea..fc4b365 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -113,6 +113,7 @@ class _CalendarHeaderState extends State late Animation _iconTurns; late int _monthIndex; bool myExpandedState = false; + bool _monthState = false; int? _beginningMonthIndex; int? _endingMonthIndex; @@ -131,12 +132,14 @@ class _CalendarHeaderState extends State _endingMonthIndex = monthIndexFromTime(widget.endingRangeDate); _indexChangeSubscription = widget.state.indexChangeStream.listen((int newTop) { - setState(() { - int ms = (widget.state.currentTopDisplayIndex + 1) * - Duration.millisecondsPerDay; - DateTime currentTopTemp = DateTime.fromMillisecondsSinceEpoch(ms); - _monthIndex = monthIndexFromTime(currentTopTemp); - }); + if (!_monthState) { + setState(() { + int ms = (widget.state.currentTopDisplayIndex + 1) * + Duration.millisecondsPerDay; + DateTime currentTopTemp = DateTime.fromMillisecondsSinceEpoch(ms); + _monthIndex = monthIndexFromTime(currentTopTemp); + }); + } }); _headerExpandedSubscription = widget.state.headerExpandedChangeStream!.listen((bool change) { @@ -201,14 +204,16 @@ class _CalendarHeaderState extends State DismissDirection.horizontal: 0.2 }, direction: direction, - onDismissed: (DismissDirection direction) { - setState(() { + onDismissed: (DismissDirection direction) => setState(() { _monthIndex += direction == DismissDirection.endToStart ? 1 : -1; // Update the current scroll pos too. + _monthState = true; widget.state.scrollToDay(monthToShow(_monthIndex)); - }); - }, + Future.delayed(const Duration(milliseconds: 1500), () { + _monthState = false; + }); + }), child: _CalendarMonthDisplay( sharedState: widget.state, location: widget._location, @@ -225,7 +230,7 @@ class _CalendarHeaderState extends State ), ); } - + @override Widget build(BuildContext context) { return Material( From 40edf7dbf6b21b036e4cb2120fcb42d50641349d Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Thu, 1 Apr 2021 15:17:04 +0800 Subject: [PATCH 17/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index fc4b365..4546bdb 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -265,6 +265,7 @@ class _CalendarHeaderState extends State children: [ GestureDetector( onTap: _handleOpen, + onDoubleTap: null, child: Row( mainAxisSize: MainAxisSize.max, children: [ From 88e904c384b59f01807a374ed57add2de34a5f7a Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Thu, 1 Apr 2021 17:07:18 +0800 Subject: [PATCH 18/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 4546bdb..8581f88 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -134,10 +134,7 @@ class _CalendarHeaderState extends State widget.state.indexChangeStream.listen((int newTop) { if (!_monthState) { setState(() { - int ms = (widget.state.currentTopDisplayIndex + 1) * - Duration.millisecondsPerDay; - DateTime currentTopTemp = DateTime.fromMillisecondsSinceEpoch(ms); - _monthIndex = monthIndexFromTime(currentTopTemp); + _monthIndex = monthIndexFromTime(getTopDisplayDate()); }); } }); @@ -152,6 +149,12 @@ class _CalendarHeaderState extends State }); } + DateTime getTopDisplayDate() { + int ms = (widget.state.currentTopDisplayIndex + 1) * + Duration.millisecondsPerDay; + return DateTime.fromMillisecondsSinceEpoch(ms); + } + void _doAnimation() { if (myExpandedState) { _controller.forward(); @@ -245,9 +248,7 @@ class _CalendarHeaderState extends State } Widget _buildCurrentHeader(BuildContext context) { - int ms = - (widget.state.currentTopDisplayIndex + 1) * Duration.millisecondsPerDay; - DateTime currentTopTemp = DateTime.fromMillisecondsSinceEpoch(ms); + DateTime currentTopTemp = getTopDisplayDate(); DateTime currentTop = DateTime(currentTopTemp.year, currentTopTemp.month, currentTopTemp.day); From c1c3ed96b2124a2871f925c53d1449019b9c8e98 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Fri, 9 Apr 2021 09:52:40 +0800 Subject: [PATCH 19/21] Update calendarheader.dart Add a sixth row to the calendar header. --- lib/src/calendarheader.dart | 24 +++++++++++++++++++++++- 1 file changed, 23 insertions(+), 1 deletion(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 8581f88..80d4a0e 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -199,7 +199,7 @@ class _CalendarHeaderState extends State child: Align( heightFactor: _easeInAnimation.value, child: Container( - constraints: BoxConstraints(minHeight: 230.0, maxHeight: 230.0), + constraints: BoxConstraints(minHeight: 230.0, maxHeight: 270.0), child: Dismissible( key: ValueKey(_monthIndex), resizeDuration: null, @@ -457,12 +457,21 @@ class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { DateTime topThird = topSecond.add(widget.week); DateTime topFourth = topThird.add(widget.week); DateTime topFifth = topFourth.add(widget.week); + // Check if the sixth row is displayed or not. + int lastday = DateTime(topFifth.year, topFifth.month + 1, 0).day; + DateTime topSixth = topFifth; + bool isShowSixthRow = false; + if ((topFifth.day + 7) <= lastday) { + isShowSixthRow = true; + topSixth = topFifth.add(widget.week); + } List dayHeaders = []; List firstDays = []; List secondDays = []; List thirdDays = []; List fourthDays = []; List fifthDays = []; + List sixthDays = []; ThemeData theme = Theme.of(context); for (int i = 0; i < 7; i++) { @@ -493,6 +502,12 @@ class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { // Fifth row. fifthDays.add(_buildButton(theme, topFifth, nowTime)); + + // Join the sixth row if exist. + if (isShowSixthRow) { + sixthDays.add(_buildButton(theme, topSixth, nowTime)); + topSixth = topSixth.add(oneDay); + } topFirst = topFirst.add(oneDay); topSecond = topSecond.add(oneDay); @@ -542,6 +557,13 @@ class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: fifthDays, ), + sixthDays.length > 0 ? + Row( + crossAxisAlignment: CrossAxisAlignment.start, + mainAxisSize: MainAxisSize.max, + mainAxisAlignment: MainAxisAlignment.spaceEvenly, + children: sixthDays, + ) : Container(), SizedBox(height: 10.0), ], ); From 7a6f644e8209128c225d05b5e888259840e367d2 Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Fri, 9 Apr 2021 11:06:43 +0800 Subject: [PATCH 20/21] Update calendarheader.dart --- lib/src/calendarheader.dart | 28 +++++++++++++++------------- 1 file changed, 15 insertions(+), 13 deletions(-) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 80d4a0e..877b827 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -362,20 +362,22 @@ class _CalendarMonthDisplayState extends State<_CalendarMonthDisplay> { } List eventIndicators = []; for (CalendarEvent event in widget.sharedState.events[eventIndex]!) { - eventIndicators.add( - SizedBox( - height: 4.0, - width: 4.0, - child: CustomPaint( - painter: _CalendarEventIndicator(2.0, event), + if (widget.displayDate.month == event.instant.month) { + eventIndicators.add( + SizedBox( + height: 4.0, + width: 4.0, + child: CustomPaint( + painter: _CalendarEventIndicator(2.0, event), + ), ), - ), - ); - eventIndicators.add( - SizedBox( - width: 2.0, - ), - ); + ); + eventIndicators.add( + SizedBox( + width: 2.0, + ), + ); + } } return SizedBox( width: 40.0, From e3a8a1fc5c3c63bd46f1d2059d7457a8428e338a Mon Sep 17 00:00:00 2001 From: jiazeh <45085050+jiazeh@users.noreply.github.com> Date: Fri, 23 Apr 2021 14:28:17 +0800 Subject: [PATCH 21/21] Update calendarheader.dart Add divider style on calendar bottom. --- lib/src/calendarheader.dart | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/lib/src/calendarheader.dart b/lib/src/calendarheader.dart index 877b827..50f9683 100644 --- a/lib/src/calendarheader.dart +++ b/lib/src/calendarheader.dart @@ -200,6 +200,10 @@ class _CalendarHeaderState extends State heightFactor: _easeInAnimation.value, child: Container( constraints: BoxConstraints(minHeight: 230.0, maxHeight: 270.0), + decoration: BoxDecoration( + border: Border(bottom: BorderSide( + color: Colors.grey.shade400, width: 1.5)) + ), child: Dismissible( key: ValueKey(_monthIndex), resizeDuration: null,