Как использовать функции time_diff и ago (time ago) в Dates для представлений Twig в Symfony 3

Во многих веб-приложениях и веб-сайтах вы можете видеть даты и легко их читать, не зная, какой сегодня день, или не зная, какой день — 21 мая, январь и т. Д. Эта функция обычно достигается в браузере с использованием JavaScript. Так в чем проблема? Библиотеки для форматирования не являются (обычно) легкими, и у вас будет как минимум 3 библиотеки для достижения чего-то подобного. Если вы хотите реализовать такую ​​функцию в своем приложении и вам не нужно динамически обновлять даты в представлении, вы можете выполнить эту задачу на своем собственном сервере.

В этой статье мы покажем вам 2 способа отображения даты в формате времени назад: с помощью KnpTimeBundle (a) или реализации Twig_Extensions_Extension_Date продолжение Twig. Оба они предоставляют одинаковую функциональность, но реализация 1 может быть более длительной для некоторых разработчиков, поэтому вам решать, какой метод проще реализовать для вас.

А. Пучок (легкий) способ

Если вам не нужно беспокоиться о размере вашего приложения, и вам разрешено устанавливать сторонние пакеты, тогда вам будет легче достичь своей цели (намного проще):

1. Установите и зарегистрируйте KnpTimeBundle

Мы говорим о KnpTimeBundle. Этот пакет выполняет одну простую работу: принимает даты и возвращает дружественные сообщения типа «2 часа назад». Чтобы установить этот пакет в вашем проекте Symfony, выполните следующую команду на терминале:

composer require knplabs/knp-time-bundle

Для получения дополнительной информации об этом комплекте, пожалуйста, посетите официальный репозиторий на Github здесь. После завершения установки комплекта обязательно включите комплект в ядре Symfony (app/AppKernel.php):

И вы готовы перейти к следующему шагу.

2. Добавить локаль приложения и включить переводчик

Обычно в каждом приложении Symfony по умолчанию локаль уже существует, и она по умолчанию en (английский). Это значение используется во всем приложении, а не только в комплекте. Если он не существует, укажите для параметра locale идентификатор вашего языка:

Заметка

Есть много поддерживаемых языков, поэтому обязательно проверьте файлы переводов чтобы увидеть, какие языки поддерживаются.

parameters:
locale: en
# Or the locale of your language e.g : es,de,nl,pt,pl etc

Далее вам нужно включить переводчик, потому что он обычно комментируется, поэтому убедитесь, что вы установили переводчик в app/config/config.yml Файл не закомментирован, и в качестве запасного варианта используется предыдущий объявленный параметр локали:

framework:
translator: { fallbacks: ['%locale%'] }

Как только это будет сделано, вы сможете использовать фильтр назад пакета для отображения удобочитаемого описания разницы во времени.

3. Использование фильтра Twig ago

KnpTimeBundle предоставляет новый фильтр веток, а именно ago, Этот фильтр ожидает в качестве цели объект DateTime, который ссылается на $since (дата происхождения) и необязательный параметр $to это указывает, откуда следует делать различие (другой объект DateTime), например:

{#
In this example we convert the now string to a date
The date can be retrieven from the controller etc.
#}
{% set myDate = "now"|date %}
{#
Modify our date by removing 4 days
#}
{% set myDate = myDate|date_modify('-4 day') %}
{# Displays according to your locale:
4 days ago
vor 4 Tagen
hace 4 días
etc
#}
{{ myDate|ago}}
{#
And if you need to differentiate the date from another day but not now
provide the first argument:
#}
{% set fromTomorrow = "now"|date_modify('+1 day') %}
{# Displays according to your locale:
5 days ago
vor 5 Tagen
hace 5 días
etc
#}
{{ myDate|ago(fromTomorrow)}}

Легко не так ли?

B. Самореализованный способ

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

1. Создайте расширение Twig_Extensions_Extension_Date

Первое, что вам нужно сделать, это создать в своем проекте Twig_Extensions_Extension_Date расширение в вашем проекте. Этот класс относится к официальное продление даты Twig Фабьен Потенсье. Преимущества следующего класса в том, что он также может использовать модуль-переводчик Symfony, поэтому он похож на пакет первого шага.

Создайте файл расширения, а именно Twig_Extensions_Extension_Date.php в некотором каталоге вашего приложения и измените пространство имен в соответствии с вашим. В этом случае мы создаем класс внутри Extensions папка в AppBundle:

 'year',
'm' => 'month',
'd' => 'day',
'h' => 'hour',
'i' => 'minute',
's' => 'second',
);
/**
* @var TranslatorInterface
*/
private $translator;
public function __construct(TranslatorInterface $translator = null)
{
$this->translator = $translator;
}
/**
* {@inheritdoc}
*/
public function getFilters()
{
return array(
new Twig_SimpleFilter('time_diff', array($this, 'diff'), array('needs_environment' => true)),
);
}
/**
* Filter for converting dates to a time ago string like Facebook and Twitter has.
*
* @param Twig_Environment $env  a Twig_Environment instance
* @param string|DateTime  $date a string or DateTime object to convert
* @param string|DateTime  $now  A string or DateTime object to compare with. If none given, the current time will be used.
*
* @return string the converted time
*/
public function diff(Twig_Environment $env, $date, $now = null)
{
// Convert both dates to DateTime instances.
$date = twig_date_converter($env, $date);
$now = twig_date_converter($env, $now);
// Get the difference between the two DateTime objects.
$diff = $date->diff($now);
// Check for each interval if it appears in the $diff object.
foreach (self::$units as $attribute => $unit) {
$count = $diff->$attribute;
if (0 !== $count) {
return $this->getPluralizedInterval($count, $diff->invert, $unit);
}
}
return '';
}
protected function getPluralizedInterval($count, $invert, $unit)
{
if ($this->translator) {
$id = sprintf('diff.%s.%s', $invert ? 'in' : 'ago', $unit);
return $this->translator->transChoice($id, $count, array('%count%' => $count), 'date');
}
if (1 !== $count) {
$unit .= 's';
}
return $invert ? "in $count $unit" : "$count $unit ago";
}
/**
* {@inheritdoc}
*/
public function getName()
{
return 'date';
}
}

2. Добавить локаль приложения и включить переводчик

Обычно в каждом приложении Symfony по умолчанию локаль уже существует, и она по умолчанию en (английский). Это значение используется во всем приложении, а не только в комплекте. Если он не существует, укажите для параметра locale идентификатор вашего языка:

parameters:
locale: en
# Or the locale of your language e.g : es,de,nl,pt,pl etc

Далее вам нужно включить переводчик, потому что он обычно комментируется, поэтому убедитесь, что вы установили переводчик в app/config/config.yml Файл не закомментирован, и в качестве запасного варианта используется предыдущий объявленный параметр локали:

framework:
translator: { fallbacks: ['%locale%'] }

Как только это будет сделано, вы сможете использовать модуль переводчика в своем добавочном номере.

3. Зарегистрируйте расширение

Далее, зарегистрируйте расширение с помощью службы переводчика в качестве аргумента и укажите путь к классу предыдущего шага:

services:
twig.extension.date:
# the namespace with the name of the Twig Extensions created class
class: AppBundle\Extensions\Twig_Extensions_Extension_Date
arguments: ["@translator"]
tags:
-  { name: twig.extension }

4. Создание файлов перевода

Следующим шагом вам нужно создать файлы перевода, однако для таких ленивых разработчиков, как я, всегда есть способ сделать все просто. Файлы перевода в этом случае будут в формате xliff, потому что мы можем копировать переводы KnpTimeBundle, и поэтому нам не нужно будет писать наши собственные файлы перевода. Однако обратите внимание, что пространство имен в KnpTimeBundle время, но в этом расширение date из-за предоставленного названия услуги twig.extension.date,

Идти к файлы перевода KnpTimeBundle здесь и выберите те, которые вам нужны, и скопируйте их в app/Resources/translations/ папка вашего проекта (если папка переводов не существует, то создайте ее). Например, следующий файл (app/Resources/translations/date.de.xliff) обеспечивает перевод наших дат на немецкий язык:

Важный

Обратите внимание, что id каждого trans-unit это строка В хранилище KnpTimeBundle идентификаторы являются числами, поэтому обязательно измените идентификатор на содержание атрибута источника, в противном случае Symfony не найдет ничего для перевода. Имя файлов xliff должно соответствовать шаблону имени файла (в этом случае) date..xliff,


diff.ago.year
vor einem Jahr|vor %count% Jahren
diff.ago.month
vor einem Monat|vor %count% Monaten
diff.ago.day
vor %count% Tag|vor %count% Tagen
diff.ago.hour
vor einer Stunde|vor %count% Stunden
diff.ago.minute
vor einer Minute|vor %count% Minuten
diff.ago.second
vor einer Sekunde|vor %count% Sekunden
diff.empty
jetzt
diff.in.second
in einer Sekunde|in %count% Sekunden
diff.in.hour
in einer Stunde|in %count% Stunden
diff.in.minute
in einer Minute|in %count% Minuten
diff.in.day
in einem Tag|in %count% Tagen
diff.in.month
in einem Monat|in %count% Monaten
diff.in.year
in einem Jahr|in %count% Jahren

5. Используйте фильтр time_diff в представлениях

Точно так же, как делает фильтр назад из KnpTimeBundle, time_diff фильтр ожидает в качестве цели объект DateTime, который ссылается на $since (дата происхождения) и необязательный параметр $to это указывает, откуда следует делать различие (другой объект DateTime), например:

{#
In this example we convert the now string to a date
The date can be retrieven from the controller etc.
#}
{% set myDate = "now"|date %}
{#
Modify our date by removing 4 days
#}
{% set myDate = myDate|date_modify('-4 day') %}
{# Displays according to your locale:
4 days ago
vor 4 Tagen
hace 4 días
etc
#}
{{ myDate|time_diff}}
{#
And if you need to differentiate the date from another day but not now
provide the first argument:
#}
{% set fromTomorrow = "now"|date_modify('+1 day') %}
{# Displays according to your locale:
5 days ago
vor 5 Tagen
hace 5 días
etc
#}
{{ myDate|time_diff(fromTomorrow)}}
Ссылка на основную публикацию
Adblock
detector