Как описать временные метки на основе текущей разницы во времени, например, в списке уведомлений
В моем предыдущем блоге я клонирую пользовательский интерфейс носителя уведомлений (версия для Android). В статье объяснялось, как я конвертирую снимок экрана в код Flutter.
Если вы читали статью выше, я выделил в конце шага 2 временные метки уведомлений. А теперь, это продолжение той статьи.
К концу этой статьи мы сможем описать отметку времени на основе текущей разницы во времени. Например, на обложке выше есть 2 уведомления. Первое уведомление было описано как 17 минут назад, а второе уведомление из Twitter — 29 минут назад. С помощью класса DateTime мы создадим новый метод расширения, чтобы мы могли описывать время без дополнительных пакетов.
Прежде всего, этот метод был вдохновлен примером выражения переключения на #GoogleIO2023. Для достоверности показываю скриншоты из видео.
Из примера на этом рисунке метод обрабатывает разницу во времени только для дней. Я возьму его и извлеку как метод обработчика дней.
- Дней
если вы используете dart v3.x
, вы можете использовать то же, что и в примере:
String dayHandler2(Duration diff) => switch(diff) { Duration(inDays: -1) => "Yesterday", Duration(inDays: 1) => "Tomorrow", Duration(inDays: 0) => "Today", Duration(inDays: int d, isNegative: true) => "${d.abs()} days ago", Duration(inDays: int d, isNegative: false) => "$d days from now", };
но если вы все еще используете dart v2.x
, которое является выражением переключения, еще не доступным, вы можете использовать этот оператор переключения.
String dayHandler(Duration day) { String result = ""; switch (day) { case Duration(inDays: -1): result = "Yesterday"; case Duration(inDays: 1): result = "Tomorrow"; case Duration(inDays: 0): result = "Today"; case Duration(inDays: int d, isNegative: true): result = "${d.abs()} days ago"; case Duration(inDays: int d, isNegative: false): result = "$d days from now"; } return result; }
- Часов
В этой части нам нужно обработать условие, когда разница во времени между 59 минутами и 24 часами.
Я делаю это максимально просто, передавая целочисленное значение разницы во времени. Итак, у меня есть метод, как показано ниже:
String hrsHandler(int hrs) { return hrs.isNegative ? "${hrs.abs()} hours ago" : "$hrs hours from now"; }
Когда целое число hrs
отрицательное, это означает, что разница просрочена, мы возвращаем x hours ago
. Но для положительных моментов это означает, что впереди несколько часов. Возвращаем x hours from now.
- Минуты
В этом случае мы хотим обрабатывать, когда разница во времени составляет менее 60 минут. Метод будет таким:
String minsHandler(int min) { return min.isNegative ? "${min.abs()} minutes ago" : "$min minutes from now"; }
Он использует ту же логику, что и в hrsHanlder
, проверяя отрицательные или положительные значения. Затем возвращает метку времени, описываемую ее значением.
Вы можете создать другой обработчик для более полного метода. Например, monthHandler
или yearHandler
. Но пока я расскажу только о днях, часах и минутах.
При реализации описанного выше метода окончательный результат метода расширения будет таким:
extension DescribeTimeDiff on DateTime { String getDifferences() { final now = DateTime.now(); final diff = difference(DateTime( now.year, now.month, now.day, now.hour, now.minute, now.second)); String a = diff.inHours.abs() > 23 // ? dayHandler(diff) // if you use dart 2 ? dayHandler2(diff) // if you use dart 3 : diff.inHours.abs() < 24 && diff.inMinutes.abs() > 59 ? hrsHandler(diff.inHours) : minsHandler(diff.inMinutes); return a; } }
Если вам интересно, почему я до сих пор использую if-else
в этом методе, то это потому, что выражения переключения и операторы переключения требуют выражения постоянного значения. Я пробовал несколько простых способов, используя переключающие выражения. Но у меня нет идей. Не стесняйтесь оставлять комментарии, если у вас есть какие-либо идеи для этого.
Полный код вы можете увидеть здесь и попробовать самостоятельно на Dartpad:
https://dartpad.dev/?id=b213bd69e1d44e2f0263081f9954af6a
Хорошо, мы уже протестировали метод, и он работает хорошо. Теперь мы реализуем это в пользовательском интерфейсе.
вот старые данные, которые у меня есть:
List<NotifModel> notifData = [ NotifModel( id: 1, userName: "Pmatatias", notifType: NotifType(id: 1, name: "responded to"), articleTitle:"The article title will be here", time: "59 minutes ago"),
и теперь мы используем форматированную строку для данных времени.
List<NotifModel> notifData = [ NotifModel( id: 1, userName: "Pmatatias", notifType: NotifType(id: 1, name: "responded to"), articleTitle:"The article title will be here", time: "2023-05-30 16:23:32.000"),
как использовать?
Сначала разберите отформатированную строку даты в объект DateTime. А затем описать время методом расширения. И не забудьте указать import
путь, если вы помещаете расширениеметод в отдельный файл.
import 'your path file where you put the time_difference method'; Text(DateTime.parse(data.time).getDifferences())
Теперь давайте посмотрим на окончательный результат клонирования пользовательского интерфейса среднего уведомления с описанной меткой времени.
Спасибо за конец. Это моя 6-я статья о методе расширения. Вы можете прочитать предыдущий метод расширения из предложения в конце этой статьи.
Кстати, я также собираю все методы extension в репозиторий GitHub. Вы можете получить его через репозиторий ниже. Не стесняйтесь вносить свой вклад, если у вас есть расширенный метод и вы хотите им поделиться.
Если вам понравилась эта статья, не забудьте похлопать 👏👏👏👏👏👏👏👏👏👏
И не стесняйтесь оставлять любые комментарии ниже. 😃
Приятного чтения!!!