Иконки и графические элементы

В Tom Select визуальная часть полностью отделена от логики, что позволяет гибко управлять тем, как отображаются элементы интерфейса: выбранные значения, пункты списка, подсказки, индикаторы состояния. Основной механизм кастомизации — переопределение шаблонов (render), через которые формируются DOM-элементы.

Каждый ключевой элемент интерфейса формируется отдельной функцией:

  • option — элемент выпадающего списка
  • item — выбранный элемент
  • option_create — создание нового значения
  • no_results — отображение пустого результата
  • optgroup_header — заголовки групп

Именно через эти шаблоны внедряются иконки, SVG-графика и любые визуальные компоненты.

new TomSelect("#select", {
  render: {
    option: function(data, escape) {
      return `
        <div class="option">
          <span class="icon icon-user"></span>
          <span class="label">${escape(data.text)}</span>
        </div>
      `;
    }
  }
});

В этом механизме отсутствуют ограничения на HTML-структуру, что делает возможным интеграцию как шрифтовых иконок, так и inline-SVG.


Использование иконок в списке опций

Добавление иконок в элементы списка чаще всего реализуется через данные, передаваемые в объекте опции. Каждая опция может содержать дополнительные поля: icon, image, type, color.

{
  value: "user_1",
  text: "Алексей",
  icon: "fa fa-user"
}

Далее эти данные используются в render.option:

render: {
  option: function(data, escape) {
    return `
      <div class="option-item">
        <i class="${data.icon}"></i>
        <span>${escape(data.text)}</span>
      </div>
    `;
  }
}

Такой подход позволяет отделять данные от представления, сохраняя единый формат источника информации.


Подключение Font Awesome и сторонних библиотек иконок

Часто для визуализации используются шрифтовые библиотеки, такие как Font Awesome. Tom Select не ограничивает выбор системы иконок, так как работает на уровне DOM.

Пример интеграции:

<link rel="stylesheet" href="fontawesome.css">
render: {
  item: function(data, escape) {
    return `
      <div class="item">
        <i class="${data.icon}"></i>
        <span>${escape(data.text)}</span>
      </div>
    `;
  }
}

Основной принцип — передача класса иконки через данные, без жесткой привязки к UI-слою.


SVG-иконки и встроенная графика

SVG обеспечивает более гибкий контроль над цветом, размером и анимацией. В отличие от шрифтовых иконок, SVG может быть инлайновым и динамически изменяемым.

render: {
  option: function(data, escape) {
    return `
      <div class="option">
        <svg class="icon" width="16" height="16" viewBox="0 0 24 24">
          <path d="${data.svgPath}"></path>
        </svg>
        <span>${escape(data.text)}</span>
      </div>
    `;
  }
}

SVG особенно полезен при необходимости состояния (active, selected, disabled), где цвет иконки меняется через CSS:

.option .icon {
  fill: currentColor;
}

Иконки в выбранных элементах (items)

Выбранные элементы отображаются отдельно от списка опций и формируются через render.item. Это позволяет создавать компактные визуальные компоненты, включающие иконку, текст и дополнительные индикаторы.

render: {
  item: function(data, escape) {
    return `
      <div class="selected-item">
        <span class="avatar"></span>
        <span class="text">${escape(data.text)}</span>
      </div>
    `;
  }
}

При необходимости можно добавить статусные индикаторы:

<span class="status status-online"></span>

или комбинировать несколько графических элементов внутри одного элемента.


Кастомизация caret-иконки и элементов управления

В интерфейсе Tom Select присутствуют управляющие элементы: стрелка раскрытия списка (caret), кнопка очистки, индикатор загрузки. Они также могут быть изменены через CSS и частично через настройки.

Caret-иконка часто заменяется через CSS:

.ts-control::after {
  content: "";
  background-image: url("data:image/svg+xml,...");
}

Либо полностью переопределяется через шаблон control:

render: {
  dropdown: function() {
    return `<div class="dropdown-custom"></div>`;
  }
}

Кнопка очистки и графические индикаторы состояния

Кнопка очистки может быть стилизована как иконка SVG или font-icon. В стандартной реализации она добавляется через CSS-класс clear-button.

.clear-button {
  background: url("close.svg") no-repeat center;
}

При использовании кастомного рендера возможно полное управление этим элементом:

render: {
  item: function(data) {
    return `
      <div class="item">
        <span>${data.text}</span>
        <span class="remove-icon">×</span>
      </div>
    `;
  }
}

Семантически кнопка удаления остается частью item, но визуально полностью контролируется разработчиком.


Индикатор загрузки и асинхронные состояния

При работе с удаленными источниками данных Tom Select отображает состояние загрузки. Этот элемент также может быть кастомизирован через render.loading.

render: {
  loading: function() {
    return `
      <div class="loading-state">
        <svg class="spinner" viewBox="0 0 50 50">
          <circle cx="25" cy="25" r="20"></circle>
        </svg>
      </div>
    `;
  }
}

CSS-анимация позволяет создать плавное вращение:

.spinner {
  animation: rotate 1s linear infinite;
}

Графические элементы в option groups

Группы опций (optgroup) позволяют структурировать список и добавлять визуальные маркеры для категорий.

render: {
  optgroup_header: function(data) {
    return `
      <div class="group-header">
        <span class="group-icon"></span>
        <span>${data.label}</span>
      </div>
    `;
  }
}

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


Использование данных для динамических иконок

Графические элементы часто зависят от состояния данных. Например, статус пользователя, тип объекта или уровень приоритета.

{
  value: 1,
  text: "Сервер 1",
  status: "online"
}
render: {
  option: function(data) {
    return `
      <div class="option">
        <span class="status ${data.status}"></span>
        <span>${data.text}</span>
      </div>
    `;
  }
}

Такой подход делает интерфейс реактивным к данным без изменения логики компонента.


Комбинирование изображений и иконок

Помимо иконок, могут использоваться аватары и миниатюры изображений. Tom Select одинаково корректно работает с <img>, SVG и CSS background.

render: {
  item: function(data) {
    return `
      <div class="item">
        <img src="${data.avatar}" class="avatar">
        <span>${data.text}</span>
      </div>
    `;
  }
}

Для оптимизации загрузки часто применяются fallback-изображения и lazy-loading через сторонние механизмы.


Стилизация через CSS-переменные и графические состояния

Графические элементы удобно контролировать через CSS variables, особенно при смене тем оформления.

:root {
  --icon-color: #444;
}

.option .icon {
  color: var(--icon-color);
}

Состояния hover и selected позволяют дополнительно изменять внешний вид:

.option.selected .icon {
  color: #2196f3;
}

Композиция сложных элементов интерфейса

Tom Select допускает создание сложных визуальных блоков внутри одного элемента: текст, иконка, бейдж, статус, прогресс-индикатор.

render: {
  item: function(data) {
    return `
      <div class="complex-item">
        <span class="icon"></span>
        <span class="label">${data.text}</span>
        <span class="badge">${data.count}</span>
      </div>
    `;
  }
}

Такая композиция позволяет строить интерфейсы, приближенные к полноценным UI-компонентам, а не просто селекту.