Работа с кнопками

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

Кнопки добавляются в тулбар статическим addButton, который принимает параметры:

  • $button - либо наследник Bitrix\UI\Buttons\Button либо массив описывающий кнопку
  • $location один из вариантов размещения кнопки: ButtonLocation::AFTER_TITLE или ButtonLocation::AFTER_FILTER, любое другое значение трактуется как ButtonLocation::RIGHT

Код базовой модели от которой мы будем отталкиваться:

use \Bitrix\UI\Toolbar\Facade\Toolbar;
use \Bitrix\UI\Toolbar\ButtonLocation;

// <-- Define `$button` here

Toolbar::addButton($button, $location = ButtonLocation::RIGHT);

Несколько простых примеров:

use \Bitrix\UI\Toolbar\Facade\Toolbar;
Toolbar::addButton([
	"link" => "https://cp.bitrix.ru",
	"text" => "Some link"
]);

Создание кнопки

Технически, нет никакой разницы будете ли вы передавать массив или объект-наследник класса Bitrix\UI\Buttons\Button, но почему так? Все дело в том, что конструктор Button-наследника принимает и обрабатывает этот массив, так что между следующими фрагментами кода нет никакой разницы:

// Example 1:
$button = [
	"link" => "https://cp.bitrix.ru",
	"text" => "Home"
];

// Example 2:
use \Bitrix\UI\Buttons\Button;

$button = new Button([
	"link" => "https://cp.bitrix.ru",
	"text" => "Home"
]);

Более того, многие методы класса и ключи массива имеют схожие названия, поэтому указанные выше фрагменты кода эквивалентны следующему:

use \Bitrix\UI\Buttons\Button;

$button = (new Button())
	->setText("Home")
	->setLink("https://cp.bitrix.ru");

Вы сами вольны выбирать стиль написания кода, а мы остановимся на более простом и понятном описании в виде массива.

Основные параметры кнопки

Мы можем провести условное деление кнопок по их реакции на события: одни кнопки будут являться кнопками перехода другие скриптовыми. Как уже понятно из названия кнопки перехода переводят пользователя на другую страницу, в то время как скриптовые обрабатывают действия на той же странице.

Кнопки перехода имеют обязательный аттрибут link - ссылку для перехода. Мы уже использовали ее ранее для демонстрации стилей.

Со скриптовыми кнопками гораздо интереснее: их поведение задается через событие нажатия и в текущем виде можно реализовать несколькими способами (демонстрирую способы в порядке приоритета - каждый следующий перекрывает предыдущий):


$myJsAction = "SomeAction"; // ... JS handler read later
$button [
	// ... other params

	// Example 1
	'click' => $myJsAction,

	// Example 2
	'onclick' => $myJsAction,

	// Example 3
	'events' => [
		'click' => $myJsAction,
	],
];

Все три примера эквивалентны, все допустимы к использованию, но использовать одновременно все 3 не имеет смысла. Теперь когда мы рассмотрели как навесить обработчик, поговорим о самом обработчике (значении $myJsAction).

В действительности обработчик на стороне backend (создание кнопки) представляет собой объект класса (\Bitrix\UI\Buttons\JsHandler), который состоит из названия JS-функции обработчик и опционального контекста выполнения (строка). Вы можете не создавать объект сразу, ведь подобно классу Button вы можете передать строку и объект создадут за вас, но контекст обработчику можно присвоить только при самостоятельном создании.

В данный момент контекст не обрабатывается. Контекст пробрасывается в data-аттрибут, но получить к нему доступ через методы нельзя.

Пример добавления кнопки в тулбар с js-обработчиком:

$button = [
	'text'    => 'MyButton',
	'onclick' => "MyEventHandler",
];

Если не написать обработчик кнопки, то нажатие на нее будет генерировать предупреждение вида: BX.UI.ButtonManager.createFromNode: be aware, the handler MyEventHandler is not a function. в консоли и никаких действий происходить не будет.

Теперь, когда мы сделали вывод кнопки, необходимо добавить обработчик нажатия на кнопку. В JS коде обработчик представляет собой функцию или статический метод, который принимает 2 аргумента: объект кнопки и событие:

function MyEventHandler(button, event)
{
	// Your code here
}

Подробнее о работе с кнопками на JS можно ознакомиться в документации, а мы расскажем лишь о самом полезном.

Какие наиболее распространенные действия можно сделать с кнопкой:

  1. Изменить ее доступность:
button.setDisabled(true); // true - deactivate button, false - activate
  1. Заменить текст/иконку на часы (например после нажатия нужно выполнить долгу операцию):
button.setClocking(true); // true - activate clock, false - deactivate

Аналогично, можно заменить не на часы, а на загрузчик или ожидание, дял этого использовать метод setWaiting

  1. Получить data-аттрибуты кнопки:
let myDataset = button.getDataSet();

Иконки

Каждой кнопке в дополнение к тексту (или замене) мы можем назначить иконку:

use \Bitrix\UI\Buttons\Icon;

$button = [
	// ..other button parameters
	
	"icon" => Icon::ADD,
];

Передавая в ключе icon значение одной из константы класса \Bitrix\UI\Buttons\Icon вы можете установить иконку для своей кнопки. Однако в классе перечислены не все доступные иконки и существует альтернативный способ задания иконки - вы можете передать css-класс иконки через classList:

$button = [
	// ..other button parameters
	
	'classList' => [
		"ui-btn-icon-add"
	],
];

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

Если по умолчанию кнопка не имеет иконки, то в атрибуте data-toolbar-collapsed-icon необходимо указать класс иконки, которая появится при схлопывании. Если у кнопки нет ни иконки, ни дата-атрибута, она не схлопывается и в консоль выводится предупреждение.

use \Bitrix\UI\Buttons\Icon;

$button = [
	// ..other button parameters

	'dataset' => [
		'toolbar-collapsed-icon' => Icon::ADD
	]
];

Передавать константу Icon-класса не обязательно - можно воспользоваться css-классом

Внешний вид

Существуют несколько параметров отвечающих за внешний вид кнопок:

  • color - Цвет (\Bitrix\UI\Buttons\Color)
  • size - Размер (Bitrix\UI\Buttons\Size)
  • noCaps - Если передан - текст кнопки не будет приведен к верхнему регистру (bool)
  • round - Если передан - кнопка будет скруглена (bool)
  • dropdown - Если передана - кнопке будут добавлены элементы представления в виде списка (треугольник для развертывания) (bool)

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

Кнопки с выпадающим меню

Работа кнопки с выпадающем меню обеспечивается js-классом битрикс BX.PopupMenuWindow и структура блока меню аналогична.

Пример подобной кнопки:

use \Bitrix\UI\Buttons\JsHandler;

$button = [
	// ..other button parameters

	"menu" => [
		"items" => [
			[
				"text" => "Детальное описание",
				"href" => "/path/to/page"
			],
			[
				"text" => "Редактировать",
				"disabled" => true
			],
			["delimiter" => true],
			[
				"text" => "Уничтожить", 
				"onclick" => new JsHandler(
					"BX.SomeModule.handleClick"
				)
			],
		],
	],
];

Больше возможностей

Редко, но иногда при конструировании кнопки стандартных параметров нехватает и появляется необходимость задавать дополнительные пользовательские аттрибуты, например aria. Сделать это можно получи коллекцию аттрибутов через метод getAttributeCollection объекта класса Button. Получить объект класса Bitrix\UI\Buttons\ButtonAttributes вы можете манипулировать его реальными значениями получить доступ ко всем необходимым вам свойствам.

Полезная литература

  1. Кнопки в документации по Тулбару
  2. UI кнопок