Flutter日历轮播插件calendar_carousel的使用

Flutter日历轮播插件calendar_carousel的使用

插件简介

calendar_carousel 是一个轻量且高度可定制的日历视图插件,适用于您的 Flutter 应用。它提供了丰富的 API 和灵活的自定义选项。


特性

  • 广泛但易于使用的 API
  • 自定义构建器以实现真正的 UI 控制
  • 支持多语言
  • 垂直自动调整大小
  • 高度动画效果
  • 月份切换处理
  • 展开/折叠月视图

示例代码

初始化日期格式

该日历依赖于 intl 库,因此需要先初始化日期格式化:

import 'package:intl/intl.dart';

void main() {
  initializeDateFormatting("zh", null).then((_) {
    runApp(MyApp());
  });
}

定义 CalendarController

如果您需要操作日历,可以定义一个 CalendarController

// 是否显示单行周视图
CalendarController _calendarController = CalendarController(isMinimal: false);
var dateFormat = DateFormat.yMMM("zh");

CalendarCarousel(
  firstDayOfWeek: 0,
  controller: _calendarController,
  dateFormat: dateFormat,
  year: 2019,
  month: 5,
  day: 20,
  headerWidgetBuilder: (controller, dateFormat, dateTime) {
    // 自定义头部
    return CalendarDefaultHeader(
      calendarController: controller,
      dateTime: dateTime,
      dateFormat: dateFormat,
    );
  },
  weekdayWidgetBuilder: (weekday) {
    // 自定义星期头
    return CalendarDefaultWeekday(
      weekday: weekday,
      dateFormat: dateFormat,
      textStyle: TextStyle(
        fontSize: 16,
        color: Colors.red
      )
    );
  },  
  dayWidgetBuilder: (date, isLastMonthDay, isNextMonthDay) {
    // 自定义日期单元格
    var today = DateTime.now();
    var isToday = today.year == date.year && today.month == date.month && today.day == date.day;
    return Padding(
      padding: EdgeInsets.all(3),
      child: FlatButton(
        padding: EdgeInsets.all(0),
        shape: CircleBorder(side: BorderSide(width: 1, color: Colors.black12)),
        color: isToday ? Colors.blueAccent : Colors.green,
        textColor: (isLastMonthDay || isNextMonthDay) ? Colors.black : Colors.white,
        onPressed: (isLastMonthDay || isNextMonthDay) ? null : () {
          print("$date");
        },
        child: Text(
          isToday ? "今天" : "${date.day}",
          style: TextStyle(fontSize: 16)
        ),
      ),
    );
  },
)

日历操作

// 动画到今天
_calendarController.goToToday(duration: const Duration(milliseconds: 450));

// 跳转到特定日期(无动画)
_calendarController.goToDate(dateTime: DateTime(2015, 9, 20), duration: null);

// 跳转到特定月份(无动画)
_calendarController.goToDate(dateTime: DateTime(2015, 9, 1), duration: null);

// 动画到指定月份
_calendarController.goToDate(
  dateTime: DateTime(2018, 9, 1),
  duration: const Duration(milliseconds: 450),
  curve: Curves.bounceIn
);

// 获取当前月份
var date = _calendarController.currentDate;
print("${date.year}-${date.month}");

// 展开日历
_calendarController.changeIsMinimal(false, null);

// 折叠日历
_calendarController.changeIsMinimal(true, null);

// 折叠日历到特定日期
_calendarController.changeIsMinimal(true, DateTime(2019, 5, 4));

监听月份变化

_calendarController.addListener(() {
  print("月份改变 ${_calendarController.currentDate}");
});

完整示例代码

import 'package:intl/intl.dart' show DateFormat;
import 'package:intl/date_symbol_data_local.dart';
import 'package:flutter/material.dart';
import 'package:calendar_carousel/calendar_carousel.dart';
import 'package:calendar_carousel/calendar_default_widget.dart';

const _kDateFormatLanguageCode = "zh";

void main() {
  initializeDateFormatting(_kDateFormatLanguageCode, null).then((_) {
    runApp(MyApp());
  });
}

class MyApp extends StatefulWidget {
  [@override](/user/override)
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {

  CalendarController _calendarController = CalendarController(isMinimal: false);

  [@override](/user/override)
  void initState() {
    super.initState();

    _calendarController.addListener(() {
      print(_calendarController.currentDate);
    });
  }

  [@override](/user/override)
  Widget build(BuildContext context) {
    var dateFormat = DateFormat.yMMM(_kDateFormatLanguageCode);
    const initYear = 2019;
    const initMonth = 3;
    const initDay = 23;

    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: const Text('calendarcarousel 示例'),
        ),
        body: ListView(
          children: <Widget>[
            CalendarCarousel(
              firstDayOfWeek: 0,
              childAspectRatio: 1.5,
              controller: _calendarController,
              dateFormat: dateFormat,
              year: initYear,
              month: initMonth,
              day: initDay,
              headerWidgetBuilder: (controller, dateFormat, dateTime) {
                return CalendarDefaultHeader(
                  calendarController: controller, 
                  dateTime: dateTime,
                  dateFormat: dateFormat,
                );
              },
              weekdayWidgetBuilder: (weekday) {
                return CalendarDefaultWeekday(
                  weekday: weekday, 
                  dateFormat: dateFormat,
                  textStyle: TextStyle(
                    fontSize: 16,
                    color: Colors.red
                  )
                );
              },
              dayWidgetBuilder: (date, isLastMonthDay, isNextMontyDay) {
                var today = DateTime.now();
                var isToday = today.year == date.year && today.month == date.month && today.day == date.day;
                return Padding(
                  padding: EdgeInsets.all(3),
                  child: FlatButton(
                    padding: EdgeInsets.all(0),
                    shape: CircleBorder(side: BorderSide(width: 1, color: Colors.black12)),
                    color: isToday ? Colors.blueAccent : Colors.green,
                    textColor: (isLastMonthDay || isNextMontyDay) ? Colors.black : Colors.white,
                    onPressed: (isLastMonthDay || isNextMontyDay) ? null : () {
                      print("$date");
                    },
                    child: Text(
                      isToday ? "今天" : "${date.day}", 
                      textAlign: TextAlign.center,
                      style: TextStyle(fontSize: 16)),
                  ),
                );
              },
            ),
            Container(
              height: 80,
              color: Colors.redAccent,
              child: Center(
                child: Text("其他组件", style: TextStyle(fontSize: 20, color: Colors.white)),
              ),
            ),
            RaisedButton(
              onPressed: () {
                _calendarController.goToToday(duration: const Duration(milliseconds: 250));
              },
              child: Text("动画到今天"),
            ),
            RaisedButton(
              onPressed: () {
                _calendarController.goToDate(dateTime: DateTime(2015, 9, 20), duration: null);
              },
              child: Text("跳转到 2015-09-20"),
            ),
            RaisedButton(
              onPressed: () {
                _calendarController.goToDate(dateTime: DateTime(2018, 1, 1), duration: const Duration(milliseconds: 250), curve: Curves.bounceIn);
              },
              child: Text("动画到 2018-01-01"),
            ),
            RaisedButton(
              onPressed: () {
                _calendarController.changeIsMinimal(!_calendarController.isMinimal, null);
              },
              child: Text(_calendarController.isMinimal ? "展开" : "折叠"),
            ),
            Builder(
              builder: (context) {
                return RaisedButton(
                  onPressed: () {
                    var date = _calendarController.currentDate;
                    final snackBar = SnackBar(
                      content: Text("${date.year}-${date.month}"), 
                    );
                    ScaffoldMessenger.of(context).showSnackBar(snackBar);
                  },
                  child: Text("显示当前月份"),
                );
              },
            )
          ],
        ),
      ),
    );
  }
}
1 回复

更多关于Flutter日历轮播插件calendar_carousel的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


calendar_carousel 是一个用于 Flutter 的日历轮播插件,它允许你在应用中显示一个可滚动的日历视图。你可以通过它来选择一个日期,或者查看某个特定日期的信息。下面是如何使用 calendar_carousel 插件的基本步骤。

1. 添加依赖

首先,你需要在 pubspec.yaml 文件中添加 calendar_carousel 插件的依赖:

dependencies:
  flutter:
    sdk: flutter
  calendar_carousel: ^2.0.0 # 请查看最新版本

然后运行 flutter pub get 来安装依赖。

2. 导入插件

在你的 Dart 文件中导入 calendar_carousel 插件:

import 'package:calendar_carousel/calendar_carousel.dart';

3. 使用 CalendarCarousel

接下来,你可以在你的应用中使用 CalendarCarousel 组件。以下是一个简单的示例:

import 'package:flutter/material.dart';
import 'package:calendar_carousel/calendar_carousel.dart';
import 'package:intl/intl.dart'; // 用于日期格式化

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  [@override](/user/override)
  Widget build(BuildContext context) {
    return MaterialApp(
      home: CalendarExample(),
    );
  }
}

class CalendarExample extends StatefulWidget {
  [@override](/user/override)
  _CalendarExampleState createState() => _CalendarExampleState();
}

class _CalendarExampleState extends State<CalendarExample> {
  DateTime _selectedDate = DateTime.now();

  [@override](/user/override)
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Calendar Carousel Example'),
      ),
      body: Column(
        children: <Widget>[
          CalendarCarousel(
            onDayPressed: (DateTime date, List<dynamic> events) {
              setState(() {
                _selectedDate = date;
              });
            },
            weekendTextStyle: TextStyle(
              color: Colors.red,
            ),
            thisMonthDayBorderColor: Colors.grey,
            daysHaveCircularBorder: true,
            selectedDateTime: _selectedDate,
            selectedDayButtonColor: Colors.blue,
            selectedDayBorderColor: Colors.blue,
            selectedDayTextStyle: TextStyle(
              color: Colors.white,
            ),
            weekFormat: false,
            height: 420.0,
            customGridViewPhysics: NeverScrollableScrollPhysics(),
            markedDateIconBuilder: (event) {
              return Icon(Icons.star, color: Colors.amber);
            },
            markedDatesMap: {
              DateTime(2023, 10, 5): [Event('Event 1', date: DateTime(2023, 10, 5))],
              DateTime(2023, 10, 10): [Event('Event 2', date: DateTime(2023, 10, 10))],
            },
          ),
          SizedBox(height: 20),
          Text(
            'Selected Date: ${DateFormat('yyyy-MM-dd').format(_selectedDate)}',
            style: TextStyle(fontSize: 20),
          ),
        ],
      ),
    );
  }
}

class Event {
  final String title;
  final DateTime date;

  Event(this.title, {required this.date});
}
回到顶部
AI 助手
你好,我是IT营的 AI 助手
您可以尝试点击下方的快捷入口开启体验!