Перейти к содержанию
Инструкция

Как отформатировать дату в формате Ydiff (например, «2 года»)

Как вывести разницу между датой и сегодняшним днём словами – «2 года», «6 месяцев», «3 дня». Разбираем относительный формат FormatDate «Ydiff» в Битрикс, автоматическое склонение и как разбить результат на число и слово.

Обновлено 22 июля 6 минут чтения

Иногда дату нужно показать не как «01.01.2014», а как прожитый интервал: «Мы на рынке 2 года», «Акция началась 6 месяцев назад». В 1С-Битрикс это делает относительный формат Ydiff функции FormatDate() – он сам вычисляет разницу между датой и текущим моментом и подбирает подходящую единицу измерения со склонением.

Что такое формат Ydiff

FormatDate() умеет не только раскладывать дату по шаблону (d.m.Y), но и выводить относительные интервалы. Формат Ydiff возвращает разницу между переданной датой и «сейчас», округляя до самой крупной подходящей единицы: годы, если прошло больше года; месяцы, если меньше; дальше – дни, часы, минуты. Результат – готовая строка вида «2 года» или «6 месяцев» с уже правильным русским склонением из локали сайта.

$first_date = '01.01.2014 00:00:00'; // исходная дата
$diff = FormatDate('Ydiff', MakeTimeStamp($first_date));
echo $diff; // например: 2 года

MakeTimeStamp() переводит строку в Unix-timestamp, а FormatDate('Ydiff', ...) сравнивает его с текущим временем. Третьим аргументом можно передать «точку отсчёта» вместо текущего момента – тогда считается разница между двумя датами:

echo FormatDate('Ydiff', MakeTimeStamp('01.01.2014'), MakeTimeStamp('01.01.2016'));
// 2 года

Как разбить результат на число и слово

Строка «2 года» – это число и единица через пробел. Если их нужно оформить по-разному (крупная цифра и подпись под ней), разбейте результат функцией explode():

$diff = FormatDate('Ydiff', MakeTimeStamp($first_date));
$parts = explode(' ', $diff); // ['2', 'года']

echo '<span class="num">' . $parts[0] . '</span>';   // 2
echo '<span class="unit">' . $parts[1] . '</span>'; // года

Родственные относительные форматы

Кроме Ydiff у FormatDate есть и «человекочитаемые» форматы вроде «X дней назад». Их удобно применять к датам публикаций и комментариев. Логика та же: функция сама выбирает единицу и склонение. Если же нужен обычный «02 июня, 2016», это уже задача буквенных шаблонов – она разобрана в гайде «Сменить формат даты в CMS Битрикс».

Подводные камни

  • Склонение – из локали. Правильные формы «год / года / лет» подставляет русская языковая тема. На английской локали получите «years» – проверьте активный язык сайта.
  • Только целые крупные единицы. Ydiff не покажет «2 года 3 месяца» одной строкой – он округляет до одной старшей единицы. Для составного вывода считайте интервал вручную (например, через DateTime::diff() чистого PHP) и собирайте строку сами.
  • Кэш «замораживает» интервал. Внутри кэшируемого шаблона компонента результат вычисляется в момент генерации кэша и потом не меняется, пока кэш жив. Для точных относительных дат считайте их вне кэша или сбрасывайте кэш по времени.
  • Часовой пояс. MakeTimeStamp трактует строку в часовом поясе сайта. При включённых пользовательских часовых поясах разница у разных посетителей может отличаться на границе суток.
  • Не путайте с датой публикации. Если исходная дата в будущем, «разница до сейчас» будет считаться от будущей точки – для обратного отсчёта до события используйте таймер, а не Ydiff (см. гайды ниже).

Смежные приёмы работы с датами и временем – в гайдах «Сменить формат даты в CMS Битрикс», «Вывод текущего года на PHP», «Счётчик обратного отсчёта в списке новостей» и «Скрипт отсчёта времени до конца акции».

Частые вопросы

Как в Битрикс вывести дату как «2 года» или «6 месяцев»?

Используйте относительный формат FormatDate('Ydiff', MakeTimeStamp($date)). Функция сама вычисляет разницу между датой и текущим моментом и подбирает крупную единицу со склонением.

Можно ли посчитать разницу между двумя произвольными датами?

Да. Передайте вторую дату третьим аргументом: FormatDate('Ydiff', MakeTimeStamp($from), MakeTimeStamp($to)). Тогда точкой отсчёта будет не «сейчас», а $to.

Почему выводится «years» вместо «года»?

Склонение единиц берётся из активной языковой темы. Английский вариант означает, что на сайте активна не русская локализация.

Как показать «2 года 3 месяца» одной строкой?

Формат Ydiff округляет до одной старшей единицы и такой составной вывод не даёт. Для него посчитайте интервал вручную, например через DateTime::diff() чистого PHP, и соберите строку сами.

Почему относительная дата не обновляется на странице?

Внутри кэшируемого шаблона компонента результат вычисляется в момент генерации кэша и застывает. Считайте относительные даты вне кэша или настройте сброс кэша по времени.

Валентина Меланина

Хотите обсудить свой проект?

Помогу с разработкой, аналитикой и AI-видимостью вашего сайта

Если у вас есть задача — от внедрения разметки и аналитики до полной переработки сайта — напишите, обсудим объём и подход.