SVG иконки для плагинов Redmine 6

Redmine 6+ перешел на использование SVG-спрайтов для иконок вместо традиционных PNG. Это улучшает производительность, уменьшает количество HTTP-запросов и упрощает управление иконками.

Данный документ описывает, как правильно подключить SVG-иконки в новый плагин, учитывая официальные рекомендации Redmine.

1. Использование стандартных иконок Redmine

Перед добавлением кастомных иконок в плагин рекомендуется использовать встроенные SVG-иконки Redmine. Это делается с помощью метода sprite_icon:

<%= sprite_icon('pencil', l(:button_edit)) %>
<%= sprite_icon('plus', l(:button_add)) %>
<%= sprite_icon('trash', l(:button_delete)) %>
<%= sprite_icon('specific_plugin_icon', l(:button_delete)), plugin: :redmine_plugin_name %>

Этот метод автоматически использует icons.svg, встроенный в Redmine.

Важно! Некоторые иконки, такие как add, delete, copy, edit, уже существуют в общем спрайте Redmine. Их необходимо использовать без указания плагина, чтобы избежать дублирования:

<%= sprite_icon('add', l(:button_add)) %>
<%= sprite_icon('delete', l(:button_delete)) %>
<%= sprite_icon('copy', l(:button_copy)) %>

Если указать параметр plugin, Redmine будет искать эти иконки в спрайте плагина, но они уже есть в общем наборе Redmine, и их повторное создание не требуется.


2. Подключение кастомных иконок в плагин

Шаг 1: Создание config/icon_source.yml

Чтобы использовать дополнительные иконки, необходимо создать config/icon_source.yml в папке плагина. Этот файл позволяет скачивать SVG-иконки из Tabler Icons и автоматически включать их в спрайт.

Пример config/icon_source.yml:

# This file is used by icons rake task to download SVG icons from Tabler
# Keys description:
#   - name: destination icon name (используется в sprite_icon)
#     svg: source icon name from Tabler Icons
#     style: outline (default) or filled

- name: custom-icon
  svg: star
- name: reload
  svg: refresh

- name — название иконки, которое будет использоваться в sprite_icon. - svg — оригинальное название иконки в Tabler Icons. - style — необязательный параметр (outline или filled).


Шаг 2: Генерация icons.svg для плагина

После настройки config/icon_source.yml необходимо выполнить команду:

rake icons:plugin:generate NAME=<redmine_plugin_name>
Эта команда:
  1. Загружает нужные иконки из Tabler Icons.
  2. Создает icons.svg в папке public/plugin_assets//images/.
  3. Генерирует SVG-спрайт, который можно использовать в шаблонах.

После выполнения команды можно проверить содержимое файла icons.svg и при необходимости внести правки вручную.


Шаг 3: Использование кастомных иконок в шаблонах

После генерации icons.svg можно использовать иконки в шаблонах плагина:

<%= sprite_icon('custom-icon', plugin: :<redmine_plugin_name>) %>
<%= sprite_icon('reload', plugin: :<redmine_plugin_name>) %>

Важно! Использовать plugin необходимо только для кастомных иконок, которых нет в общем наборе Redmine.


3. CSS-правила для совместимости с PNG-иконками

Для обратной совместимости с CSS-классами, которые использовали PNG-файлы, необходимо обновить CSS. Используем :not(:has(svg)), чтобы подставлять PNG только там, где нет SVG.

Пример app/assets/stylesheets/.css:

.icon-edit:not(:has(svg)) { background-image: url(../images/pencil.png); }
.icon-add:not(:has(svg)) { background-image: url(../images/circle-plus.png); }
.icon-copy:not(:has(svg)) { background-image: url(../images/copy.png); }
.icon-del:not(:has(svg)) { background-image: url(../images/trash.png); }

Если браузер не поддерживает :has(), используйте JavaScript для удаления background-image у элементов с <svg>.

document.querySelectorAll('.icon').forEach(icon => {
  if (icon.querySelector('svg')) {
    icon.style.backgroundImage = 'none';
  }
});

4. Дополнительные rake-задачи для работы с иконками

Команда Описание
rake icons:download Загружает стандартные иконки Redmine
rake icons:generate Загружает иконки и создаёт SVG-спрайт
rake icons:plugin:download Загружает SVG-иконки для плагина
rake icons:plugin:generate Загружает иконки и создаёт спрайт для плагина
rake icons:plugin:sprite Генерирует только спрайт для плагина
rake icons:sprite Генерирует общий SVG-спрайт

Используйте rake icons:plugin:generate NAME=, чтобы обновить спрайт.


5. Поддержка старых версий Redmine

Для обратной совместимости с Redmine 5 и ниже, где sprite_icon может отсутствовать, используйте патч совместимости.

Добавление поддержки в init.rb

require 'redmineup/patches/compatibility_patch'

Этот патч автоматически адаптирует работу с иконками на старых версиях Redmine.


6. Возможные ошибки и их решения

Ошибка Решение
Иконка не отображается Убедитесь, что указан plugin: : в sprite_icon.
Иконка не добавилась в icons.svg Проверьте, что config/icon_source.yml содержит правильные значения и повторно запустите rake icons:plugin:generate.
Изменения в icons.svg не применяются Выполните rake assets:precompile, чтобы пересобрать файлы.
Отображаются старые PNG-иконки Добавьте :not(:has(svg)) в CSS, чтобы отключить background-image.

Итог

  1. Использовать стандартные иконки Redmine без plugin, чтобы не дублировать их.
  2. Создать config/icon_source.yml и указать список кастомных иконок.
  3. Сгенерировать icons.svg с помощью rake icons:plugin:generate.
  4. Использовать sprite_icon('custom-icon', plugin: :) только для новых иконок.
  5. Добавить CSS-фильтр :not(:has(svg)) для отключения старых иконок.
  6. Пересобрать ассеты (rake assets:precompile).
  7. Для обратной совместимости подключить compatibility_patch.

Соблюдение этих рекомендаций обеспечит корректное отображение SVG-иконок в плагине и совместимость с Redmine 6+.

Примечания

  • Осталась проблема с иконками на странице активности. Проблема связана с тем, что метод activity_event_type_icon не учитывает иконки из ресурсов плагинов, даже после исправлений в версии 6.0.2.
Was this article helpful? Yes  No
242 from 242 found this helpful