Как создать свой блок в Gutenberg - новом редакторе для WordPress. Разбираемся на живом примере.
Upd [16.02.2020]
Плагин - констуктор блоков: https://wordpress.org/plugins/lazy-blocks/
Upd [27.12.2018]:
Появился плагин для WP с функционалом добавления блоков: https://getblocklab.com/
Начиная с 5 версии Wordpress стандартный текстовый редактор заменят на Gutenberg. Обзор редактора, его плюсы и минусы можете найти в интернете. А мы сегодня будем расширять его функционал, добавляя свой блок.
Создание блоков и их отображение прописывается в js и css файлах. Но для того чтобы все корректно работало необходимо их правильно подключить.
Для добавления своего блока в Wordpress я добавил в папку с текущей темой новую папку my_gutenberg
и в неё скрипт init_my_custom_gutenberg_block.php
, который в свою очередь подключил в functions.php
.
Структура файлов получилась следующая (относительно папки с темой):
|- my_gutenberg/
|- init_my_custom_gutenberg_block.php
|- my_first_block/
|- script_editor.js
|- style_editor.css
|- style.css
Содержимое init_my_custom_gutenberg_block.php
представлено ниже:
function my_custom_block_for_gutenberg() {
wp_register_script(
'mcbfg_script_editor',
get_template_directory_uri() . '/my_gutenberg/my_first_block/script_editor.js',
array( 'wp-blocks', 'wp-element', 'wp-components' )
);
wp_register_style(
'mcbfg_style_editor',
get_template_directory_uri() . '/my_gutenberg/my_first_block/style_editor.css',
array( 'wp-edit-blocks' )
);
wp_register_style(
'mcbfg_style',
get_template_directory_uri() . '/my_gutenberg/my_first_block/style.css',
array( 'wp-blocks' )
);
register_block_type( 'my-gutenberg/my-first-block', array(
'editor_script' => 'mcbfg_script_editor',
'editor_style' => 'mcbfg_style_editor',
'style' => 'mcbfg_style'
) );
}
add_action( 'init', 'my_custom_block_for_gutenberg' );
На хук init
вешается функция которая подключит все неоходимые файлы в редакторе и на выводе во фронтальной части для нашего блока.
Подключение стилей и скриптов осуществляется как обычно с помощью wp_enqueue_style()
и wp_enqueue_scripts()
. Но с одной особенностью, а именно необходимо указать правильные зависимости.
Для скриптов в режиме редактирования:
array( 'wp-blocks', 'wp-element', 'wp-components' )
Для стилей в режиме редактирования:
array( 'wp-edit-blocks' )
Для стилей в режиме редактирования и во фронтальной части:
array( 'wp-blocks' )
После подключения стилей и скриптов необходимо вызвать функцию register_block_type()
для их инициализации в Gutenberg, передав массив параметров:
- editor_sctipt
- скрипт для редактора (именно в нем и происходит добавление нового блока)
- editor_style
- стили для редактора
- style
- стили для фронтальной части
Очередность подключения стилей в режиме редактирования следующая:
1. style
2. editor_style
То есть правила записанные в editor_style
имеют больший приоритет, чем правила в style
.
Чтобы создать новый блок, нам необходимо зарегистрировать его с помощью Gutenberg, вызвав registerBlockType(). Делать это следует в подключаемом JS файле:
registerBlockType(
'block-namespace/block-name',
{
// параметры создаваемого блока
}
);
Пример нашего первого блока:
var el = wp.element.createElement,
registerBlockType = wp.blocks.registerBlockType,
RichText = wp.editor.RichText;
registerBlockType( 'my-gutenberg/my-first-block', {
title: 'My First Block',
description: 'Description',
icon: {
background: '#7e70af',
foreground: '#fff',
src: 'format-aside',
},
attributes: {
content: {
type: 'array',
source: 'children',
selector: 'p',
}
},
category: 'common',
edit: function( props ) {
var content = props.attributes.content;
function onChangeContent( newContent ) {
props.setAttributes( { content: newContent } );
}
return el(
RichText,
{
tagName: 'p',
className: props.className,
onChange: onChangeContent,
value: content,
}
);
},
save: function( props ) {
var content = props.attributes.content;
return el( RichText.Content, {
tagName: 'p',
className: props.className,
value: content
} );
},
} );
Список параметров:
- title
(строка): отображается в редакторе в качестве метки блока поиска
- description
(необязательная строка): описывает назначение блока
- icon
(дополнительный элемент Dashicon или JSX): значок, связанный с блоком
- category
(строка): где блок появляется в диалоговом окне "Добавить блоки"
- keywords
(необязательный массив): до трех ключевых слов, используемых в поиске по блокам
- attributes
(необязательный объект): обрабатывает данные динамического блока
- edit
(функция): функция, возвращающая разметку для рендеринга в редакторе
- save
(функция): функция, которая возвращает разметку для отображения во фронтальной части сайта
- useOnce
(необязательный логический тип): запретить добавление блока более одного раза
- supports
(необязательный объект): определяет поддерживаемые блоком функции
title
- заголовок блокаПри вставке или поиске блока в редакторе заголовок будет отображаться в списке доступных блоков.
Он также отображается в окне настроек текущего блока вместе с описанием, если оно определено. Если окно настроек текущего блока не отображается, вы можете использовать значок шестеренки в правом верхнем углу редактора Gutenberg для переключения отображения.
description
- описание блокаОтображается в окне настроек текущего блока.
icon
- иконка блокаИконка блока, которая может быть выбрана из списка dashicons самого wordpress или иметь запись JSX формата, что позволит использовать любую SVG иконку (убедитесь, что она соответствует размеру остальных иконок - 20x20).
Стоит отметить, что если вы выбираете иконку из dashicons, то записывать значение в передаваемый параметр нужно без dashicon-
, например для иконки dashicons-format-aside
запись будет вида: format-aside
.
Значением может быть объект, в котором заданы свойста background
и foreground
, для указания фонового цвета и цвета иконки.
icon: {
background: '#7e70af',
foreground: '#fff',
src: 'format-aside',
}
category
- категория блокаВ настоящий момент доступны следующие категории:
- common
- Основные блоки
- formatting
- Форматирование
- layout
- Элементы разметки
- widgets
- Виджеты
- embed
- Вставки
keywords
- ключевые слова для поискаДля того, чтобы блок можно было проще найти, можно указать до трех ключевых слов. Лучше всего выбирать ключевые слова, которые тесно связаны с функциональностью нашего блока. И хотя добавление ключевых слов является необязательным, это отличный способ облегчить пользователям поиск наших блоков.
attributes
- атрибуты блокаАтрибуты блока являются необязательным параметром, т.к. для простых статичных блоков они не понадобятся. Однако, когда нужны динамические данные - без атрибутов не обойтись.
attributes: {
cover: {
type: 'string',
source: 'attribute',
selector: 'img',
attribute: 'src',
},
author: {
type: 'string',
source: 'children',
selector: '.book-author',
},
pages: {
type: 'number',
},
},
Параметр типа определяет с какими данными вы будете иметь дело. Это может быть array
, string
, number
, object
, url
или любой другой тип из руководства ReactJS
Данные в Gutenberg хранятся в виде HTML (за исключением мета данных) и для правильной работы с ними необходимо правильно их описать, а именно указать как будут извлекаться данные для обработки из хранимого HTML в редактируемый. Сам механизм работает на основе библиотеки hpq
attribute
- для извлечения значений из атрибутов html тегов (например: src
для img
)text
- для извлечения внутреннего текста из разметкиhtml
- для извлечения внутреннего HTML кода из разметкиchildren
- для извлечения дочерних элементов в виде массива виртуальных элементов (например: для извлечения элементов p
из RichText
)query
- для извлечения данных из разметки в виде массива в соответсвии с заданным запросом (например: извлечь все src
и alt
атрибуты из тегов img
){
images: {
source: 'query'
selector: 'img',
query: {
url: { source: 'attribute', attribute: 'src' },
alt: { source: 'attribute', attribute: 'alt' },
}
}
}
// {
// "images": [
// { "url": "https://lorempixel.com/1200/800/", "alt": "large image" },
// { "url": "https://lorempixel.com/50/50/", "alt": "small image" }
// ]
// }
meta
- для извлечения данных из мета данных записи, таких как: автор, дата публикации и пр.edit
Параметр edit
описывается с помощью функции:
edit: function( props ) {
// тело функции
}
Данная функция отвечает за отображение нашего блока при редактировании записи. Детальное рассмотрение.
save
Параметр save
также, как и edit
описывается с помощью функции:
save: function( props ) {
// тело функции
}
Данная функция отвечает за формирование хранимого и отображаемого HTML кода. Детальное рассмотрение.
useOnce
Это полезное свойство, которое позволяет вам блокировать добавление блока более одного раза на страницу. После добавления блока значок блока отображается серым цветом и не может быть выбран. По умолчанию useOnce
имеет значение false
.
supports
Определяет какие особенности имеет наш блок. Значения задаются в логическом типе данных.
- align
(по умолчанию: false)
свойство добавляет элементы управления блоком, которые позволяют изменять выравнивание блока. Важно: не работает с динамическими блоками.
- alignWide
(по умолчанию: true)
Gutenberg позволяет включить выравнивание по ширине для вашей темы. Чтобы отключить это поведение для одного блока, установите для этого флага значение false
.
- anchor
(по умолчанию: false)
Якоря позволяют напрямую ссылаться на конкретный блок на странице. Это свойство добавляет поле для ввода идентификатора для блока и кнопки для копирования прямой ссылки.
- customClassName
(по умолчанию: true)
Это свойство добавляет поле для определения пользовательского ClassName для оболочки блока.
- className
(по умолчанию: true)
По умолчанию Gutenberg добавляет класс с формой .wp-block-your-block-name
к корневому элементу вашей сохраненной разметки. Это помогает создать согласованный механизм для стилизации блоков, на которые могут влиять темы и плагины. Если по какой-либо причине класс не нужен в разметке, эта функция может быть отключена.
- html
(по умолчанию: true)
По умолчанию Gutenberg позволит редактировать разметку блока отдельно. Чтобы отключить это поведение, установите html
в false
.
- inserter
(по умолчанию: true)
По умолчанию все блоки появятся в вставке Gutenberg. Чтобы скрыть блок, чтобы его можно было вставлять только программно, установите inserter
равным false
.
- multiple
(по умолчанию: true)
Немножественный блок может быть вставлен в каждый пост, только один раз. Например, встроенный блок «More» не может быть вставлен снова, если он уже существует в редактируемом сообщении. Значок немножественного блока автоматически затемняется, чтобы предотвратить добавление несколько экземпляров.
edit
и save