WPML
WPML 只能按照语言配置文件中的声明翻译自定义区块的属性。Blockstudio 会将每个字段值存储在区块注释中的 blockstudio.attributes 下,因此每个区块都需要一个条目,将 WPML 指向其文本字段和附件 ID。wp bs wpml config 命令会为每个已注册的区块写入这些条目。
为什么区块需要配置
WPML会从当前启用的主题和每个已启用插件的根目录中名为wpml-config.xml的文件读取配置。对于单文件的必需插件,文件夹名称就是文件名去掉.php后的部分。请参阅语言配置文件和使自定义Gutenberg区块支持翻译。
没有条目的区块会交由WPML自动检测字符串,它会将区块的每个字符串属性提供给翻译。对于包含选择值、文件引用、URL 和CSS类的Blockstudio区块,译者会在真实文本旁看到这些技术值,而翻译后的选择值或类可能会导致区块无法正常工作。
生成配置
打印配置,并将其保存到提供这些区块的主题或插件的根目录中:
wp bs wpml config > wp-content/themes/my-theme/wpml-config.xml
也可以让命令写入文件:
wp bs wpml config --file=wp-content/themes/my-theme/wpml-config.xml
一个包含文本字段、图像、链接和重复器的区块:
{
"name": "my-theme/cards",
"title": "Cards",
"blockstudio": {
"attributes": [
{ "id": "heading", "type": "text", "label": "Heading" },
{ "id": "gallery", "type": "files", "label": "Gallery", "multiple": true },
{
"id": "style",
"type": "select",
"label": "Style",
"options": [
{ "value": "light", "label": "Light" },
{ "value": "dark", "label": "Dark" }
]
},
{
"id": "cards",
"type": "repeater",
"label": "Cards",
"attributes": [
{ "id": "title", "type": "text", "label": "Title" },
{ "id": "image", "type": "files", "label": "Image" },
{ "id": "link", "type": "link", "label": "Button" }
]
}
]
}
}
会变成:
<wpml-config>
<gutenberg-blocks>
<!-- blockstudio:start -->
<!-- Generated by wp bs wpml config. Run it again after changing block fields; edits between the markers are replaced. -->
<gutenberg-block type="my-theme/cards" translate="1" label="Cards">
<key name="blockstudio">
<key name="attributes">
<key name="heading" label="Heading" />
<key name="gallery">
<key name="*" type="post-ids" sub-type="attachment" />
</key>
<key name="cards">
<key name="*">
<key name="title" label="Cards: Title" />
<key name="image" type="post-ids" sub-type="attachment" />
<key name="link">
<key name="title" label="Cards: Button: Link text" />
<key name="url" type="link" label="Cards: Button: URL" />
</key>
</key>
</key>
</key>
</key>
</gutenberg-block>
<!-- blockstudio:end -->
</gutenberg-blocks>
</wpml-config>
style值未声明,因此WPML会原样复制到翻译中。gallery和image ID 也会被复制,渲染区块时,WPML会将每个 ID 替换为当前页面语言对应的附件,因此翻译后的图像可以拥有自己的替代文本。请参阅使自定义Gutenberg区块支持翻译中的“自动转换区块中的 ID”。如果附件没有对应的翻译,WPML会保留原始 ID。
声明内容
命令会读取已注册的区块,此时custom/字段和区块字段已展开,并已应用覆盖项和属性筛选器。扩展添加到Blockstudio区块的字段也会包含在内。扩展添加到核心区块或其他插件区块的字段则不会包含,因为这些区块从WPML或各自所属的插件中获取配置。
| 字段 | 声明 |
|---|---|
text、textarea、richtext、wysiwyg |
可翻译文本。 |
link |
将title作为文本,将url与type="link"一起使用,因此WPML会在有可用翻译时将链接替换为对应译文。 |
files |
带有type="post-ids"和sub-type="attachment"的已存附件 ID。使用multiple时,为列表指定名为*的层级;这也匹配字段选择单个文件时存储的单个 ID。 |
repeater |
指定名为*的层级以匹配每一行,并包含行字段的声明。嵌套重复器的工作方式相同。 |
带有id的group |
组内字段,以组 ID 作为键前缀(组cta中的字段text使用cta_text)。 |
没有id的group,tabs |
这些字段没有自己的层级。 |
注册时将translate设为true的自定义字段类型 |
可翻译文本,类似text字段。 |
| 其他所有内置类型 | 不声明。WPML会原样复制该值。 |
没有声明文本字段的区块会获得translate="0"。随后WPML会复制其中的所有值,不会提供任何内容供翻译。其files字段仍会在条目中声明,因为WPML无论translate如何设置,都会转换附件 ID。内部区块仍按常规方式翻译。
未声明的字段:
- 带有
hidden的字段,因为编辑者不会写入这些值。 - 带有
"translate": false的字段,见下文。 - 自定义字段类型中未将
translate设为true的字段。命令会为每个此类字段打印警告,因为只有字段类型才知道其值是否包含文本。对字段显式设置"translate": false也会抑制该字段的警告。见下文。 - 区块在原生
attributes中声明、而非作为Blockstudio字段声明的属性。 - 字段类型不同的存储键,见下文。
每个文本字段都会被声明,包括保存技术值的字段,例如CSS类,除非它设置了"translate": false。
排除字段
文本字段可能保存必须在所有语言中保持一致的值,例如账号名称、电子邮件地址、锚点或CSS类。WPML会像处理其他文本一样将其提供给翻译,而翻译后的值可能会导致区块无法正常工作。将translate设为false,即可从配置中排除该字段,让WPML将其值原样复制到翻译中:
{
"id": "account",
"type": "text",
"label": "Account handle",
"translate": false
}
对于group、tabs或repeater,"translate": false适用于其中的每个字段,包括嵌套容器。子项无法通过"translate": true覆盖已选择排除的容器。对于files字段,false也会排除附件 ID,因此翻译会保留原始附件。
省略translate或将其设为true会保留现有行为:由字段类型决定。它不会让隐藏字段或select等值类型变得可翻译。此选项适用于区块字段和扩展字段,不会隐藏或禁用其编辑器控件,也不会更改其存储值。更改设置后,请再次运行wp bs wpml config,并使用生成的配置更新你的wpml-config.xml。
每个键的label是字段标签,前面带有具有 ID 的外层重复器和组的标签。WPML会在翻译编辑器中将其显示为字段名称。link字段的两个键会在标签中添加Link text和URL。这些后缀会翻译成站点语言,因此请使用译者工作的语言区域设置运行命令。
自定义字段类型
存储纯文本字符串的字段类型会在注册时声明这一点。在定义中将translate设为true,并确保attribute为string:
bs_register_field_type('acme/headline', [
'attribute' => 'string',
'translate' => true,
]);
该命令随后会将此类型的每个字段都声明为可翻译文本。字段仍可设置 "translate": false,将自身排除在外。未启用此选项时,此类型的字段会像以前一样被排除并报告。
更改标签
字段标签是为区块编辑器编写的,可能带有“图像(可选)”之类的提示,而这些提示在翻译编辑器中毫无意义。blockstudio/wpml/config/label 过滤器会在标签写入之前接收每个标签,并附带键的上下文:
block:区块名称。path:blockstudio.attributes下方字段的存储路径,每个重复器行还会有一个*层级,例如cards/*/link。field:字段定义。parents:外层重复器和带 ID 的分组标签。part:文本字段的text,链接字段两个键的title或url。
add_filter('blockstudio/wpml/config/label', function ($label, $context) {
return str_replace(' (optional)', '', $label);
}, 10, 2);
返回空字符串即可排除某个键的标签,这样 WPML 就会显示区块标签。返回非字符串值则会保留原标签。更改过滤器后,请再次运行该命令。
存储键相同的字段
两个字段最终可能使用相同的存储键,例如区块字段和扩展字段具有相同的 id,或者 ID 为 cta 的分组中有字段 text,同时还有 ID 为 cta_text 的字段。只有在明确该键存储的内容时,命令才会声明此类键:
- 在区块字段中,重复器行之外,Blockstudio 会为每个存储键注册一个属性,因此后面的字段会替换前面的字段,无论它们的类型如何。区块扩展中的字段也遵循相同规则:后面的字段,或后注册的扩展中的字段,会替换前面的字段。
- 具有相同键的区块字段和扩展字段都会生效。区块模板接收按区块字段定义的值,而扩展则使用自己的字段应用该值。只有当两个字段需要相同声明时,该键才只声明一次:两个字段都是文本字段(
text、textarea、richtext或wysiwyg),两个都是链接,两个都是files字段(任一字段带有multiple时,该键会采用*层级),或者两个字段都不声明,例如一个select和一个number。两个重复器会按行逐字段比较。标签取自区块字段。 - 同一重复器各行中具有相同
id的两个字段也都会生效,并按相同方式比较。
类型不同时,例如区块中的 text 字段与扩展中的 select,存储值可能是文本,也可能是选择项,具体取决于写入该值的控件。命令不会声明该键,并会打印一条警告:
Warning: Not declared, the fields that store this key have different types: my-theme/cards: tone (text in the block, select in an extension)
重命名其中一个字段,或将两个字段设为相同类型,即可声明该键。
保持配置为最新状态
添加、移除或重命名字段后,请再次运行该命令,并将更新后的文件随主题或插件一同发布。重新生成在 7.7.5 之前创建的配置,以纳入附件 ID 声明。对于原始内容更新后才出现的新字段,已有内容即可进行翻译,具体如上方 WPML 指南所述。
使用 --file 时,命令会创建缺失的文件。对于已有文件,命令只会替换 <!-- blockstudio:start --> 与 <!-- blockstudio:end --> 之间的文本,因此其他区块的章节和条目会保持原样:
<wpml-config>
<custom-types>
<custom-type translate="1">book</custom-type>
</custom-types>
<gutenberg-blocks>
<gutenberg-block type="my-plugin/map" translate="1">
<key name="caption" />
</gutenberg-block>
<!-- blockstudio:start -->
<!-- blockstudio:end -->
</gutenberg-blocks>
</wpml-config>
要使用尚无标记的现有文件,请在其 gutenberg-blocks 元素内添加这两行标记,或者在文件尚无 gutenberg-blocks 元素时添加一个带有标记的元素。如果缺少标记,或者结果不是有效配置,命令会保持文件不变并报错退出。
手动编写的 Blockstudio 区块条目(例如用于隐藏技术值的 translate="0" 条目)在生成章节涵盖该区块后便不再需要。命令会对每个重复声明的区块发出警告,因此可以移除这些条目。
翻译任务中的图像文本
WPML 会将页面所用图像的文本加入该页面的翻译任务:标题、替代文本、说明文字和描述。任务完成后,WPML 会将译文写入目标语言的附件;如果目标语言尚无对应附件,则会创建一个。请参阅如何翻译媒体。
WPML 会查找内容中的 <img> 标签、图库、特色图像以及它支持的区块中的图像。Blockstudio 区块会在区块注释中存储附件 ID,因此 WPML 找不到其中的图像。
启用 WPML 后,Blockstudio 会将页面区块字段中存储的附件加入已找到的图像 WPML:
files字段(包括隐藏字段),以及带有media的attributes字段;区块编辑器会将这些相同字段作为媒体加载。- 分组、选项卡、重复器行和内部区块中的字段。
- 扩展的字段,包括核心区块和其他插件的区块中的字段,因为这些值存储在被扩展区块的属性中。
非附件 ID 的值会被排除。无需进行任何配置,也不会涉及 wpml-config.xml。未启用 WPML 时,不会扫描翻译任务,也不会加载媒体集成类。
这与附件 ID 转换彼此独立:生成的 XML 会告知 WPML 应渲染哪个译文附件,而此集成会告知它应将哪些附件文本加入翻译任务。字符串引用和非附件文章的 ID 不会加入媒体任务。在 Blockstudio 区块中,已保存的嵌套字段值优先于顶层值,渲染时也是如此。
只有启用了 WPML > Settings > Media Translation 下的某个图像文本选项时,这些文本才会成为任务的一部分:“自动检测翻译图像文本的最佳选项”或“翻译内容时翻译媒体库文本”。核心区块中的图像也是如此。
Blockstudio 通过筛选器报告图像
wpml_ids_of_media_used_in_post,该筛选器 WPML 会应用于
PostWithMediaFiles 中帖子的媒体。若要将某张图像排除在任务之外,请在优先级高于 10 的同一筛选器回调中移除其 ID:
add_filter(
'wpml_ids_of_media_used_in_post',
function ( $ids ) {
return array_values( array_diff( $ids, array( 42 ) ) );
},
20
);