В редакторе Gutenberg изначально заложено множество типовых блоков, но предположим что нам нужно создать блок с собственными полями для определенной верстки. Создадим пользовательский блок.
Создаем плагин пользовательского блока
Содержимое основного файла в одноименной папке в директории /plugins/
<?php
/**
* Plugin Name: Custom Gutenberg Block
* Author: John Doe
* Version: 1.0.0
*/
function loadMyBlock() {
wp_enqueue_script(
'my-new-block',
plugin_dir_url(__FILE__) . 'test-block.js',
array('wp-blocks','wp-editor'),
true
);
}
add_action('enqueue_block_editor_assets', 'loadMyBlock');
В данном коде мы регистрируем новый блок и указываем что его настройки содержаться в файле скрипта test-block.js.
В скрипте используется JavaScript с библиотекой React.
// В этом разделе кода регистрируется новый блок, устанавливается значок и категория, а также указывается тип полей, которые он будет включать.
wp.blocks.registerBlockType('brad/border-box', {
title: 'Simple Box',
icon: 'smiley',
category: 'common',
attributes: {
content: {type: 'string'},
color: {type: 'string'}
},
// Это настраивает, как будут работать поля содержимого и цвета, и устанавливает необходимые элементы
edit: function(props) {
function updateContent(event) {
props.setAttributes({content: event.target.value})
}
function updateColor(value) {
props.setAttributes({color: value.hex})
}
return React.createElement(
"div",
null,
React.createElement(
"h3",
null,
"Simple Box"
),
React.createElement("input", { type: "text", value: props.attributes.content, onChange: updateContent }),
React.createElement(wp.components.ColorPicker, { color: props.attributes.color, onChangeComplete: updateColor })
);
},
save: function(props) {
return wp.element.createElement(
"h3",
{ style: { border: "3px solid " + props.attributes.color } },
props.attributes.content
);
}
})
Блок уведомления
Создадим еще один блок для примера. На этот раз блок для вывода уведомлений.
Подключаем файл скрипта (лучше в виде плагина)
<?php
function riad_enqueue_blocks() {
wp_enqueue_script(
'riad-block',
plugins_url( 'block.js', __FILE__ ),
array( 'wp-blocks', 'wp-element' )
);
}
add_action( 'enqueue_block_editor_assets', 'riad_enqueue_blocks' );
function riad_enqueue_styles() {
wp_enqueue_style(
'riad-block-style',
plugins_url( 'myblock.css', __FILE__ ),
array( ),
filemtime( plugin_dir_path( __FILE__ ) . 'myblock.css' )
);
}
add_action( 'enqueue_block_assets', 'riad_enqueue_styles' );
Содержимое файла myblock.js
var el = wp.element.createElement,
registerBlockType = wp.blocks.registerBlockType;
registerBlockType( 'riad/alert', {
title: 'Alert Block',
icon: 'warning',
category: 'common',
attributes: {
type: {
type: 'string',
default: 'danger',
},
message: {
type: 'string',
source: 'html',
selector: 'div',
},
},
edit: function( props ) {
var className = props.className;
var type = props.attributes.type;
var message = props.attributes.message;
function updateMessage( event ) {
props.setAttributes( { message: event.target.value } );
}
return el(
'p',
{ className: className + ' alert-' + type },
el(
'textarea',
{ value: message, onChange: updateMessage }
)
);
},
save: function( props ) {
var type = props.attributes.type;
var message = props.attributes.message;
return el(
'p',
{ className: 'alert-' + type },
message
);
},
} );
Также нужно добавить стили:
.wp-block-riad-alert.alert-danger { color: red; }
.wp-block-riad-alert.alert-success { color: green; }
.wp-block-riad-alert.alert-warning { color: orange; }
Создадим динамический блок
Блок вывода последней записи
<?php
function riad_render_block_latest_post( $attribites ) {
$recent_posts = wp_get_recent_posts( array(
'numberposts' => 1,
'post_status' => 'publish',
) );
if ( count( $recent_posts ) === 0 ) {
return 'No posts';
}
$post = $recent_posts[ 0 ];
$post_id = $post['ID'];
return sprintf(
'<a class="wp-block-riad-latest-post" href="%1$s">%2$s</a>',
esc_url( get_permalink( $post_id ) ),
esc_html( get_the_title( $post_id ) )
);
}
register_block_type( 'riad/latest-post', array(
'render_callback' => 'riad_render_block_latest_post',
) );
Содержимое myblock.js
var el = wp.element.createElement,
registerBlockType = wp.blocks.registerBlockType,
withSelect = wp.data.withSelect;
registerBlockType( 'riad/latest-post', {
title: 'Latest Post',
icon: 'megaphone',
category: 'widgets',
edit: withSelect( function( select ) {
return {
posts: select( 'core' ).getEntityRecords( 'postType', 'post' )
};
} )( function( props ) {
if ( props.posts && props.posts.length === 0 ) {
return "No posts";
}
var className = props.className;
var post = props.posts[ 0 ];
return el(
'a',
{ className: className, href: post.link },
post.title.rendered
);
} ),
save: function() {
// Rendering in PHP
return null;
},
} );
Взаимодействие с мета-полями
var el = wp.element.createElement,
registerBlockType = wp.blocks.registerBlockType;
registerBlockType( 'riad/book-title', {
title: 'Book Title',
icon: 'book',
category: 'common',
attributes: {
title: {
type: 'string',
meta: 'book-title',
source: 'meta'
},
}
edit: function( props ) {
var className = props.className;
var title = props.attributes.title;
function updateTitle( event ) {
props.setAttributes( { title: event.target.value } );
}
return el(
'p',
{ className: className },
el(
'textarea',
{ value: title, onChange: updateTitle }
)
);
},
save: function() {
return null;
},
} );
Из-за некоторых ограничений REST API необходимо регистрировать мета в вашем типе записи
function gutenberg_my_block_init() {
register_meta( 'post', 'book-title', array(
'show_in_rest' => true,
'single' => true,
) );
}
add_action( 'init', 'gutenberg_my_block_init' );
[site-socialshare]