123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422 |
- /// month->days.
- Map<int, int> MONTH_DAY = {
- 1: 31,
- 2: 28,
- 3: 31,
- 4: 30,
- 5: 31,
- 6: 30,
- 7: 31,
- 8: 31,
- 9: 30,
- 10: 31,
- 11: 30,
- 12: 31,
- };
- /// ISO 8601 标准的时间格式字符串
- /// 时间与日期的格式化工具类(自定义基于Dart原生Api-DateTime实现)
- class DateTimeUtils {
- static String full = 'yyyy-MM-dd HH:mm:ss'; //如 2023-05-25 12:05:03
- // ===================================== 反格式化时间 ↓ =====================================
- /*
- 根据指定日期格式得到原生的DateTime对象
- 使用:
- final date = DateTimeUtils.getDateTime('2023-10-21');
- 打印结果 DateTime 对象为:2023-10-21 00:00:00.000
- final date = DateTimeUtils.getDateTime('2023-10-21 12:08:55');
- 打印结果 DateTime 对象为:2023-10-21 12:08:55.000
- final date = DateTimeUtils.getDateTime('2023-10-21 12:55');
- 打印结果 DateTime 对象为:2023-10-21 12:55:00.000
- final date = DateTimeUtils.getDateTime('2023/10/21 12:08:55');
- 这样就不行,因为 2023/10/21 12:08:55 不是标准格式无法转换为 DateTime 对象,必须要 2012-02-27 或 2012-02-27 13:27:00 标准格式
- */
- static DateTime? getDateTime(String dateStr, {bool? isUtc}) {
- DateTime? dateTime = DateTime.tryParse(dateStr);
- if (isUtc != null) {
- if (isUtc) {
- dateTime = dateTime?.toUtc();
- } else {
- dateTime = dateTime?.toLocal();
- }
- }
- return dateTime;
- }
- /*
- 根据指定的毫秒时间戳得到原生的DateTime对象
- 使用:
- final date = DateTimeUtils.getDateTimeByMs(1682304352000)
- 打印结果 DateTime 对象为:2023-04-24 10:45:52.000
- */
- static DateTime getDateTimeByMs(int ms, {bool isUtc = false}) {
- return DateTime.fromMillisecondsSinceEpoch(ms, isUtc: isUtc);
- }
- /*
- 根据日期格式得到对应的毫秒值
- 使用:
- final date = DateTimeUtils.getDateMsByTimeStr('2023-10-21');
- 打印结果为:1697817600000
- final date = DateTimeUtils.getDateMsByTimeStr('2023-10-21 12:08:55');
- 打印结果为:1697861335000
- final date = DateTimeUtils.getDateMsByTimeStr('2023-10-21 12:55');
- 打印结果为:1697864100000
- */
- static int? getDateMsByTimeStr(String dateStr, {bool? isUtc}) {
- DateTime? dateTime = getDateTime(dateStr, isUtc: isUtc);
- return dateTime?.millisecondsSinceEpoch;
- }
- /*
- 获取当前系统日期的毫秒值
- 使用:
- final date = DateTimeUtils.getNowDateMs();
- 打印结果为:1697817600000
- */
- static int getNowDateMs() {
- return DateTime.now().millisecondsSinceEpoch;
- }
- // ===================================== 反格式化时间 ↑ =====================================
- // ===================================== 格式化时间 ↓ =====================================
- /*
- 获取当前系统日期的格式化时间值。默认格式为 yyyy-MM-dd HH:mm:ss
- 使用:
- final date = DateTimeUtils.getNowDateStr();
- 打印结果为:2023-10-09 09:54:26
- final date = DateTimeUtils.getNowDateStr(format: 'yyyy-MM-dd');
- 打印结果为:2023-10-09
- final date = DateTimeUtils.getNowDateStr(format: 'yyyy-MM-dd HH:mm');
- 打印结果为:2023-10-09 09:55
- final date = DateTimeUtils.getNowDateStr(format: 'yyyy-MMM-dd HH:mm');
- 打印结果为:2023-Oct-09 09:56
- final date = DateTimeUtils.getNowDateStr(format: 'yyyy/MMM/dd HH:mm');
- 打印结果为:2023/Oct/09 09:57
- final date = DateTimeUtils.getNowDateStr(format: 'dd MMM yyyy HH:mm');
- 打印结果为:09 Oct 2023 09:58
- */
- static String formatNowDateStr({String? format, bool isMonthEn = true, bool isMonthEnShort = true}) {
- return formatDate(DateTime.now(), format: format, isMonthEn: isMonthEn, isMonthEnShort: isMonthEnShort);
- }
- /*
- 根据指定的毫秒时间戳格式化时间值。默认格式为 yyyy-MM-dd HH:mm:ss
- 使用:
- final date = DateTimeUtils.formatDateMs(1682304352000,format: 'yyyy-MM-dd')
- 打印结果为:2023-04-24
- final date = DateTimeUtils.formatDateMs(1682304352000,format: 'dd MMM yyyy HH:mm');
- 打印结果为:24 Apr 2023 10:45
- */
- static String formatDateMs(int ms,
- {bool isUtc = false, String? format, bool isMonthEn = true, bool isMonthEnShort = true}) {
- return formatDate(getDateTimeByMs(ms, isUtc: isUtc),
- format: format, isMonthEn: isMonthEn, isMonthEnShort: isMonthEnShort);
- }
- /*
- 根据指定的日期字符串格式化时间值。默认格式为 yyyy-MM-dd HH:mm:ss
- @Parmas dateStr 参数必须是标准格式如 2012-02-27 或 2012-02-27 13:27:00 ,format的转换格式可以随便写
- 使用:
- final date = DateTimeUtils.formatDateStr('2023-10-21 12:08:55',format: 'dd MMM yyyy');
- 打印结果为:21 Oct 2023 12:08
- final date = DateTimeUtils.formatDateStr('2023-10-21 12:08:55',format: 'yyyy-MM-dd');
- 打印结果为:2023-10-21
- final date = DateTimeUtils.formatDateStr('2023/10/21 12:08:55',format: 'yyyy-MM-dd');
- 这样就不行,因为 2023/10/21 12:08:55 不是标准格式无法转换为 DateTime 对象
- */
- static String formatDateStr(String dateStr,
- {bool? isUtc, String? format, bool isMonthEn = true, bool isMonthEnShort = true}) {
- return formatDate(getDateTime(dateStr, isUtc: isUtc),
- format: format, isMonthEn: isMonthEn, isMonthEnShort: isMonthEnShort);
- }
- /*
- 总方法 - 根据标准的 DateTime 来格式化时间。默认格式为 yyyy-MM-dd HH:mm:ss
- 使用:
- final date = DateTimeUtils.formatDate(date, format: "yyyy-MM-dd");
- 打印结果为:2023-10-09
- */
- static String formatDate(DateTime? dateTime, {String? format, bool isMonthEn = true, bool isMonthEnShort = true}) {
- if (dateTime == null) return '';
- format = format ?? full;
- //对Year的处理
- if (format.contains('yy')) {
- String year = dateTime.year.toString();
- if (format.contains('yyyy')) {
- format = format.replaceAll('yyyy', year);
- } else {
- format = format.replaceAll('yy', year.substring(year.length - 2, year.length));
- }
- }
- //对Month的处理
- int month = dateTime.month;
- if (format.contains("M")) {
- if (format.contains("MM")) {
- if (format.contains("MMM")) {
- if (format.contains("MMMM")) {
- //处理4个M,英文显示
- format = format.replaceAll("MMMM", getMonthEnStr(month, true, false));
- } else {
- //处理3个M,英文显示
- format = format.replaceAll("MMM", getMonthEnStr(month, isMonthEn, isMonthEnShort));
- }
- } else {
- //处理2个M
- format = format.replaceAll("MM", month < 10 ? '0$month' : month.toString());
- }
- } else {
- //处理1个M
- format = format.replaceAll("M", month.toString());
- }
- }
- //对其他的处理
- format = _comFormat(dateTime.day, format, 'd', 'dd');
- format = _comFormat(dateTime.hour, format, 'H', 'HH');
- format = _comFormat(dateTime.minute, format, 'm', 'mm');
- format = _comFormat(dateTime.second, format, 's', 'ss');
- format = _comFormat(dateTime.millisecond, format, 'S', 'SSS');
- return format;
- }
- //格式化1位数为2位数,前面加0 如:2008-01-05 08:05:04
- static String _comFormat(int value, String format, String single, String full) {
- if (format.contains(single)) {
- if (format.contains(full)) {
- format = format.replaceAll(full, value < 10 ? '0$value' : value.toString());
- } else {
- format = format.replaceAll(single, value.toString());
- }
- }
- return format;
- }
- // 返回自己的月份字符串信息
- static String getMonthEnStr(int month, bool isMonthEn, bool isMonthEnShort) {
- String monthStr = month.toString();
- switch (month) {
- case 1:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Jan" : "January";
- break;
- case 2:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Feb" : "February";
- break;
- case 3:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Mar" : "March";
- break;
- case 4:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Apr" : "April";
- break;
- case 5:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "May" : "May";
- break;
- case 6:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Jun" : "June";
- break;
- case 7:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Jul" : "July";
- break;
- case 8:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Aug" : "August";
- break;
- case 9:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Sep" : "September";
- break;
- case 10:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Oct" : "October";
- break;
- case 11:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Nov" : "November";
- break;
- case 12:
- monthStr = !isMonthEn ? month.toString() : isMonthEnShort ? "Dec" : "December";
- break;
- }
- return monthStr;
- }
- /// 获取输入时间是星期几
- static String getWeekdayByMs(int milliseconds, {bool isUtc = false, String languageCode = 'en', bool short = false}) {
- DateTime dateTime = getDateTimeByMs(milliseconds, isUtc: isUtc);
- return getWeekday(dateTime, languageCode: languageCode, short: short);
- }
- /*
- 根据标准的 DateTime 对象,获取 weekDay 属性,并返回自己的星期字符串
- */
- static String getWeekday(DateTime? dateTime, {String languageCode = 'zh', bool short = false}) {
- if (dateTime == null) return "";
- String weekday = "";
- switch (dateTime.weekday) {
- case 1:
- weekday = languageCode == 'zh' ? '星期一' : 'Monday';
- break;
- case 2:
- weekday = languageCode == 'zh' ? '星期二' : 'Tuesday';
- break;
- case 3:
- weekday = languageCode == 'zh' ? '星期三' : 'Wednesday';
- break;
- case 4:
- weekday = languageCode == 'zh' ? '星期四' : 'Thursday';
- break;
- case 5:
- weekday = languageCode == 'zh' ? '星期五' : 'Friday';
- break;
- case 6:
- weekday = languageCode == 'zh' ? '星期六' : 'Saturday';
- break;
- case 7:
- weekday = languageCode == 'zh' ? '星期日' : 'Sunday';
- break;
- default:
- break;
- }
- return languageCode == 'zh'
- ? (short ? weekday.replaceAll('星期', '周') : weekday)
- : weekday.substring(0, short ? 3 : weekday.length);
- }
- /// 在今年的第几天.
- static int getDayOfYear(DateTime dateTime) {
- int year = dateTime.year;
- int month = dateTime.month;
- int days = dateTime.day;
- for (int i = 1; i < month; i++) {
- days = days + MONTH_DAY[i]!;
- }
- if (isLeapYearByYear(year) && month > 2) {
- days = days + 1;
- }
- return days;
- }
- /// 在今年的第几天.
- static int getDayOfYearByMs(int ms, {bool isUtc = false}) {
- return getDayOfYear(DateTime.fromMillisecondsSinceEpoch(ms, isUtc: isUtc));
- }
- /// 是否是当天.
- static bool isToday(int? milliseconds, {bool isUtc = false, int? locMs}) {
- if (milliseconds == null || milliseconds == 0) return false;
- DateTime old = DateTime.fromMillisecondsSinceEpoch(milliseconds, isUtc: isUtc);
- DateTime now;
- if (locMs != null) {
- now = DateTimeUtils.getDateTimeByMs(locMs);
- } else {
- now = isUtc ? DateTime.now().toUtc() : DateTime.now().toLocal();
- }
- return old.year == now.year && old.month == now.month && old.day == now.day;
- }
- /// 是否是昨天.
- static bool isYesterday(DateTime dateTime, DateTime locDateTime) {
- if (yearIsEqual(dateTime, locDateTime)) {
- int spDay = getDayOfYear(locDateTime) - getDayOfYear(dateTime);
- return spDay == 1;
- } else {
- return ((locDateTime.year - dateTime.year == 1) &&
- dateTime.month == 12 &&
- locDateTime.month == 1 &&
- dateTime.day == 31 &&
- locDateTime.day == 1);
- }
- }
- /// 是否是昨天.
- static bool isYesterdayByMs(int ms, int locMs) {
- return isYesterday(DateTime.fromMillisecondsSinceEpoch(ms), DateTime.fromMillisecondsSinceEpoch(locMs));
- }
- /// 是否是本周.
- static bool isWeek(int? ms, {bool isUtc = false, int? locMs}) {
- if (ms == null || ms <= 0) {
- return false;
- }
- DateTime _old = DateTime.fromMillisecondsSinceEpoch(ms, isUtc: isUtc);
- DateTime _now;
- if (locMs != null) {
- _now = DateTimeUtils.getDateTimeByMs(locMs, isUtc: isUtc);
- } else {
- _now = isUtc ? DateTime.now().toUtc() : DateTime.now().toLocal();
- }
- DateTime old = _now.millisecondsSinceEpoch > _old.millisecondsSinceEpoch ? _old : _now;
- DateTime now = _now.millisecondsSinceEpoch > _old.millisecondsSinceEpoch ? _now : _old;
- return (now.weekday >= old.weekday) &&
- (now.millisecondsSinceEpoch - old.millisecondsSinceEpoch <= 7 * 24 * 60 * 60 * 1000);
- }
- /// 是否同年.
- static bool yearIsEqual(DateTime dateTime, DateTime locDateTime) {
- return dateTime.year == locDateTime.year;
- }
- /// 是否同年.
- static bool yearIsEqualByMs(int ms, int locMs) {
- return yearIsEqual(DateTime.fromMillisecondsSinceEpoch(ms), DateTime.fromMillisecondsSinceEpoch(locMs));
- }
- /// 是否是闰年
- static bool isLeapYear(DateTime dateTime) {
- return isLeapYearByYear(dateTime.year);
- }
- /// 是否是闰年
- static bool isLeapYearByYear(int year) {
- return year % 4 == 0 && year % 100 != 0 || year % 400 == 0;
- }
- /// 输入时间距离当前时间有多少年
- static int distanceCurrentYear(DateTime date) {
- Duration difference = DateTime.now().difference(date);
- return (difference.inDays / 365).floor();
- }
- /// 输入时间距离当前时间有多少天
- static int distanceCurrentDay(DateTime date) {
- Duration difference = DateTime.now().difference(date);
- return difference.inDays;
- }
- }
|