社区新闻

如何扩展 WordPress 块

查看官方原文 ↗ 发布于

如果现有的 WordPress 块不能完全满足您的需求,您可能会想从头开始构建一个新块。这样做可以让您完全控制块以及用户将看到的内容。

虽然这种方法可行,但它通常会导致更多的工作和持续的维护,特别是当您只需要小的增强时。您不仅需要复制现有块的大部分功能,而且还会错过对原始块的未来更新和改进。这对于 WordPress 核心块尤其重要,因为它们经常更新新功能、改进的用户界面等。

自定义块始终是一个选项,但在构建自己的块之前,通常最好先尝试扩展现有块。

扩展块的方法有很多,本文涵盖了其中的大部分方法及其当前的局限性。为了简化讨论,我将方法分为两个部分:第一部分重点介绍用于修改块支持、添加块样式和注册块变体的 API,第二部分向您展示如何添加完全自定义的功能。

使用块 API

WordPress 包含多个允许您修改块的 API。开发者博客有大量内容涵盖这些方法,因此本节将简要概述每种方法,并提供进一步阅读的链接。

修改块支持

块支持 API 允许您轻松添加或修改块功能,例如对齐选项、颜色设置或间距控制。只需几行代码,您就可以为块选择加入或退出特定的支持,这随后将相应地修改编辑器中的块用户界面。例如,如果您移除了颜色支持,标题块将不再显示文本和背景颜色选择器。

如果您正在构建自定义块,在添加自己的功能之前,应始终使用可用的块支持。这样做可以为用户提供一致的编辑体验,并确保您的块与 WordPress 功能(例如 全局样式)集成。

支持通常在块的 block.json 文件中定义。您可以使用 PHP 或 JavaScript 修改这些值,但通常最好的方法是使用 PHP 中的 register_block_type_args 过滤器。这样做无需额外排入 JavaScript 文件,并确保您的修改在服务器上注册。

此过滤器的回调函数接受两个参数:

  • $args (数组):已注册块类型的块参数。
  • $block_type (字符串):块类型名称,包括命名空间。

以下代码将为媒体与文本块启用双色调支持。您可以将其放在主题的 functions.php 文件或实用插件中。

/**
 * Enable duotone for Media & Text blocks.
 *
 * @param array  $args       The block arguments for the registered block type.
 * @param string $block_type The block type name, including namespace.
 * @return array             The modified block arguments.
 */
function example_enable_duotone_to_media_text_blocks( $args, $block_type ) {
	
	// Only add the filter to Media & Text blocks.
	if ( 'core/media-text' === $block_type ) {
		$args['supports'] ??= [];
		$args['supports']['filter'] ??= [];
		$args['supports']['filter']['duotone'] = true;

		$args['selectors'] ??= [];
		$args['selectors']['filter'] ??= [];
		$args['selectors']['filter']['duotone'] = '.wp-block-media-text .wp-block-media-text__media';
	}

	return $args;
}
add_filter( 'register_block_type_args', 'example_enable_duotone_to_media_text_blocks', 10, 2 );

应用后,您将在设置侧边栏中看到 滤镜 面板和可用的双色调选项。

编辑器中媒体与文本块的滤镜(双色调)控件。

修改块支持也是编辑器定制的一种常见方法。它允许您将功能限制给特定用户、文章类型等。使用以下链接了解更多信息。

注册块样式

块样式 API 允许您通过注册不同的样式来自定义块的视觉外观。这些样式出现在块的设置侧边栏中,使用户可以轻松访问各种设计选项。例如,按钮块包含 WordPress 提供的几种内置样式。

编辑器中按钮块可用的块样式。

您可以通过多种方式注册块样式,但常见的方法是使用 register_block_style() PHP 函数。默认的 Twenty Twenty-Four 主题包含了这种方法的几个示例。

以下代码添加了一个自定义样式,当启用时,在标题块上方显示一个星号:

if ( ! function_exists( 'twentytwentyfour_block_styles' ) ) :
	/**
	 * Register custom block styles
	 *
	 * @since Twenty Twenty-Four 1.0
	 * @return void
	 */
	function twentytwentyfour_block_styles() {
		register_block_style(
			'core/heading',
			array(
				'name'         => 'asterisk',
				'label'        => __( 'With asterisk', 'twentytwentyfour' ),
				'inline_style' => "
				.is-style-asterisk:before {
					content: '';
					width: 1.5rem;
					height: 3rem;
					background: var(--wp--preset--color--contrast-2, currentColor);
					clip-path: path('M11.93.684v8.039l5.633-5.633 1.216 1.23-5.66 5.66h8.04v1.737H13.2l5.701 5.701-1.23 1.23-5.742-5.742V21h-1.737v-8.094l-5.77 5.77-1.23-1.217 5.743-5.742H.842V9.98h8.162l-5.701-5.7 1.23-1.231 5.66 5.66V.684h1.737Z');
					display: block;
				}

				/* Hide the asterisk if the heading has no content, to avoid using empty headings to display the asterisk only, which is an A11Y issue */
				.is-style-asterisk:empty:before {
					content: none;
				}

				.is-style-asterisk:-moz-only-whitespace:before {
					content: none;
				}

				.is-style-asterisk.has-text-align-center:before {
					margin: 0 auto;
				}

				.is-style-asterisk.has-text-align-right:before {
					margin-left: auto;
				}

				.rtl .is-style-asterisk.has-text-align-left:before {
					margin-right: auto;
				}",
			)
		);
	}
endif;

add_action( 'init', 'twentytwentyfour_block_styles' );

请注意该函数如何接受块的名称 (core/heading) 和一个参数数组。这些参数包括名称、标签以及与块样式关联的任何内联样式。

一旦注册了此块样式,带星号 按钮将出现在所有标题块的设置侧边栏中。当用户选择此选项时,name 会以 is-style- 为前缀,并作为 CSS 类添加到块中。在这种情况下,类将是 is-style-asterisk

编辑器中标题块的“带星号”块样式。

块样式是扩展块的绝佳方式,特别是随着 WordPress 6.6 中 区域样式 的引入。开发者博客上的几篇文章更详细地介绍了此 API,包括注册和使用它们来扩展块的其他方法。以下是一些入门文章:

块样式 API 有一些限制,最显著的是每次只能应用一种块样式。尽管 Gutenberg 仓库中有一个 开放议题 来解决这个问题,但开发者博客上的 超越块样式 系列文章探讨了自定义块扩展作为替代方法。

注册块变体

块变体 API 是本部分讨论的最后一个 API。变体允许您通过预定义属性或内部块来创建现有块的不同版本。与依赖 CSS 进行视觉更改的块样式不同,块变体功能更强大,使您能够从用户的角度创建看似全新的块。

例如,在 WordPress 中,行和堆叠块是组块的变体。同样,每个嵌入选项,如 YouTube 嵌入和 Vimeo 嵌入,都是主要嵌入块的变体。

变体可以使用 JavaScript 或 PHP 注册,但最常见的方法是使用 registerBlockVariation() JavaScript 函数。与注册块样式类似,此函数接受块名称和一个包含变体名称、标题、属性、内部块等的对象。完整的属性列表可在 API 文档 中找到。

以下代码示例演示了如何为媒体与文本块注册一个变体。此变体设置 alignbackgroundColor 属性,并包含两个内部块。

import { registerBlockVariation } from '@wordpress/blocks';

registerBlockVariation(
	'core/media-text',
	{
		name: 'media-text-default',
		title: 'Media & Text (Custom)',
		attributes: {
			align: 'wide',
			backgroundColor: 'tertiary'
		},
		innerBlocks: [
			[
				'core/heading',
				{
					level: 3,
					placeholder: 'Heading'
				} 
			],
			[
				'core/paragraph',
				{
					placeholder: 'Enter content here...'
				} 
			],
		],
		isDefault: true,
	}
);

通常,注册块变体会在插入器中创建一个具有指定自定义项的新“块”。但是,如果您将 isDefault 属性设置为 true,您的变体将替换块的默认实例,如上文代码所示。

注册此块变体后,每当用户向文章添加媒体与文本块时,它都将预配置为定义的属性和内部块。

编辑器中媒体与文本块的块变体。

块变体通常在本节讨论的 API 中提供最大的灵活性,特别是与自定义功能或其他 API(如 块绑定)结合使用时。要了解有关在项目中利用变体的更多信息,请探索以下文章:

添加自定义功能

一旦您探索了可用的 API 并且仍然需要进一步扩展块,有几个过滤器允许您添加完全自定义的功能。探索此方法的最佳方式是通过一个实际示例,您可以将其应用到自己的站点。在本节中,您将学习如何通过添加新设置并根据该设置自定义其前端标记来扩展 WordPress 中的图像块。

目标

为了演示如何向现有块添加自定义功能,请考虑以下场景:

您希望向任何装饰性图像块添加 role="presentation",以确保屏幕阅读器出于可访问性目的正确处理它。装饰性图像 不会为页面或文章的内容提供有意义的信息,屏幕阅读器应忽略它。

将图像的 alt 文本设置为 null 是 W3C 网络可访问性倡议 (WAI) 推荐的使装饰性图像可访问的最常见方法。但是,添加 role="presentation" 属性是确保屏幕阅读器忽略这些元素的另一种受支持的方法。

目标是创建一个块扩展插件,实现以下功能:

  1. 添加一个块设置,用于存储图像块是否为装饰性。
  2. 在编辑器中添加一个用户界面,允许用户配置此设置。
  3. 根据此设置修改块的标记。

装饰性图像块的前端标记最终应如下所示:

<!-- Before -->
<figure class="wp-block-image size-full">
<img src="https://example.com/image-path.png" class="wp-image-12345" alt=""/>
</figure>

<!-- After -->
<figure class="wp-block-image size-full">
<img src="https://example.com/image-path.png" class="wp-image-12345" alt="" role="presentation"/>
</figure>

以下是编辑器中最终结果的预览。您也可以通过点击下面的“实时预览”链接来演示此功能。

图像块的设置侧边栏,带有自定义的“图像是装饰性的”切换开关。这是完成的示例。

设置

如果您想跟随并自己构建此插件,有一些先决条件。创建块扩展类似于构建自定义块,因此您需要一个开发环境。有关更多信息,请参阅 块开发环境 文档。

一旦您的本地 WordPress 环境启动并运行:

  • 导航到 plugins 文件夹。
  • 添加一个名为 enable-decorative-images 的新文件夹。
  • 在其中添加一个名为 enable-decorative-images.php 的文件。
  • 将以下插件头部添加到文件中。
<?php
/**
 * Plugin Name:         Enable Decorative Images
 * Description:         Easily make Image blocks decorative.
 * Version:             0.1.0
 * Requires at least:   6.5
 */

从 WordPress 管理仪表板激活插件,然后:

  • 在主插件文件夹内添加一个 src 文件夹。
  • src 文件夹内添加一个空的 index.js 文件。
  • 在主插件文件夹中添加一个 package.json 文件,内容如下。
{
  "name": "enable-decorative-images",
  "scripts": {
    "build": "wp-scripts build",
    "start": "wp-scripts start"
  },
  "devDependencies": {
    "@wordpress/scripts": "^28.5.0"
  }
}

这是比您在大多数项目中看到的更简化的 package.json 版本,但本示例只需要这些。

保存文件并运行终端命令 npm install。安装完成后,运行 npm start 以启动由 wp-scripts 包提供的构建过程。您应该会看到在新建的 build 文件夹中生成的 index.jsindex.asset.php 文件。

接下来,将以下代码添加到 enable-decorative-images.php 文件中。这将排入构建文件,确保任何文本字符串可翻译,并使 JavaScript 在编辑器中可用。

/**
 * Enqueue Editor scripts.
 */
function example_enqueue_block_editor_assets() {
	$asset_file = include plugin_dir_path( __FILE__ ) . 'build/index.asset.php';

	wp_enqueue_script(
		'enable-decorative-images-editor-scripts',
		plugin_dir_url( __FILE__ ) . 'build/index.js',
		$asset_file['dependencies'],
		$asset_file['version']
	);

	wp_set_script_translations(
		'enable-decorative-images-editor-scripts',
		'enable-decorative-images'
	);
}
add_action( 'enqueue_block_editor_assets', 'example_enqueue_block_editor_assets' );

您的块扩展插件的基本结构现已完成。