flutter 自定义日历选择(没有用到第三方日历库)

这篇博客详细介绍了如何在Flutter中实现一个自定义的日历选择组件,包括星期一作为一周的第一天、显示当前月份、设置选择范围限制、全选功能、已选天数统计及回显等功能。博主分享了核心代码,并提供了数据处理和UI交互的关键逻辑,同时提到了第三方库的不足,最终选择了手动实现。文章末尾提供了关键代码片段和回显功能的实现方式。

flutter 自定义日历选择

禁止转载、抄袭

功能需求

实现后是长这样的(因为项目要以底部弹窗显示,也可以整个UI自定义)
要代码的私信我(看人品回复)
请添加图片描述
项目需求:

  1. 星期一在第一,星期日在最后
  2. 一开始显示的是当前月份
  3. 有startTime和endTime的限制,所以并不是每个日期都能选择
  4. 选择全部工作日按钮,意思是除了星期六日和第三点的条件都选择
  5. 已选统计选了多少天,下一步把选择的传到下个页面
  6. 没有说需不需要滑动切换月份(我是没做了)
  7. 在第3点外的月份不能点击全选
  8. 新增一个带回显的功能

干就完事了

我看了日历第三方库,有些符合要求,但有些不符合要求(淦),看了原理直接手撕算了。

实际原理就是gradeview(iOS里的collectionView),里面添数据而已,就是处理数据比较麻烦,幸好没叫我做滑动。

说这么多,上核心代码

因为部分是项目的代码,我不可能公开,你需要的话可以私信我,女的请私信你的qq(感觉不可能)

工具类

这些函数的dateTime date都是该月的第一天,其他不管用(主要是自己懒得再重新处理数据)


  ///星期一为第一天
  static int computeFirstDay(
      DateTime date, MaterialLocalizations localizations) {
   
   
    final int weekdayFromMonday = date.weekday;
    final int firstDayOfWeekFromSunday = localizations.firstDayOfWeekIndex + 1;
    final int firstDayOfWeekFromMonday = firstDayOfWeekFromSunday % 7;
    return (weekdayFromMonday - firstDayOfWeekFromMonday) % 7;
  }
  static const List<int> _daysInMonth = <int>[
    31,
    -1,
    31,
    30,
    31,
    30,
    31,
    31,
    30,
    31,
    30,
    31
  ];
  /// 获取这个月的天数
  static int getDayCountInMonth(DateTime date) {
   
   
    int month = date.month;
    int year = date.year;
    if (month == DateTime.february) {
   
   
      final bool isLeapYear =
          (year % 4 == 0) && (year % 100 != 0) || (year % 400 == 0);
      if (isLeapYear) return 29;
      return 28;
    }
    return _daysInMonth[month-1];
  }

这些大概是定位该月gradeView(collectionView)的显示数据位置。

UI方面的代码我不怎么想给,毕竟产品+UI都不一样

调用
List<DateModel> list = [];
  List<DateTime> returnList = [];
  List<TotalDateModel> totalList = [];
  bool isfullChoice = false;
  bool canChooseMoon = true;
@override
  void initState() {
   
   
    super.initState();
    WidgetsBinding.instance!.addPostFrameCallback((timeStamp) {
   
   
      setState(() {
   
   
        list = getDateModel(MaterialLocalizations.of(context));
      });

    });
  }


class DateModel {
   
   
  int day;
  bool isChoosen;
  DateModel({
   
   
    required this.day,
    required this.isChoosen,
  });
}
创建原始数据
///创建数据
  List<DateModel> getDateModel(MaterialLocalizations localizations){
   
   
    //当月的总天数
    final int currentMonthTotalDays = CommonUtils.getMonthDay(widget.date)
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值