Contents
Introducción
Este artículo explica paso a paso cómo crear un bloque personalizado para WordPress usando InnerBlocks y controles personalizados en JavaScript. Cubriremos la estructura del proyecto, el registro del bloque, el desarrollo del componente de edición con InnerBlocks, controles en la barra lateral (InspectorControls) y la renderización de la salida con InnerBlocks.Content. También incluimos ejemplos completos de código para cada archivo necesario.
Requisitos previos
- WordPress 5.0 (mejor con 5.8 )
- Node.js y npm instalados
- Conocimientos básicos de ESNext, React/JSX y la API de bloques de Gutenberg
- Herramientas de compilación: recomendamos @wordpress/scripts para simplificar
Estructura del proyecto
Un plugin simple para este bloque podría tener la siguiente estructura:
- my-innerblocks-block/
- block.json
- src/
- index.js
- edit.js
- save.js
- build/ (generado)
- plugin.php
- style.css (opcional)
- editor.css (opcional)
1. block.json (metadatos)
Usar block.json facilita el registro del bloque con register_block_type_from_metadata. Define atributos, estilos, y scripts a enlazar.
{
apiVersion: 2,
name: mi-plugin/innerblocks-con-controles,
title: Sección con InnerBlocks y Controles,
category: layout,
icon: columns,
description: Bloque que permite anidar bloques con controles personalizados,
supports: {
html: false
},
editorScript: file:./build/index.js,
editorStyle: file:./build/editor.css,
style: file:./build/style.css,
attributes: {
backgroundColor: {
type: string,
default: #ffffff
},
showTitle: {
type: boolean,
default: true
},
columns: {
type: number,
default: 2
}
}
}
2. plugin.php (registro en PHP)
Archivo principal del plugin que registra el bloque usando los metadatos y encola los assets compilados.
3. index.js (entrada JS)
Archivo de entrada que registra la edición y la save. Importa edit y save desde src.
import { registerBlockType } from @wordpress/blocks import edit from ./edit import save from ./save import metadata from ../block.json registerBlockType( metadata.name, { ...metadata, edit, save, } )4. edit.js (componente de edición con InnerBlocks y controles)
Este es el núcleo: muestra la interfaz de edición con InnerBlocks, Panel lateral con controles y controles en la barra del bloque. Usamos componentes de @wordpress/block-editor y @wordpress/components.
import { __ } from @wordpress/i18n import { useBlockProps, InnerBlocks, InspectorControls, BlockControls } from @wordpress/block-editor import { PanelBody, ToggleControl, RangeControl, ToolbarGroup, ToolbarButton } from @wordpress/components import { Fragment } from @wordpress/element import { useState } from @wordpress/element const ALLOWED_BLOCKS = [ core/heading, core/paragraph, core/image, core/gallery ] export default function Edit( props ) { const { attributes, setAttributes, clientId } = props const { backgroundColor, showTitle, columns } = attributes const blockProps = useBlockProps( { style: { backgroundColor: backgroundColor, padding: 1rem, }, className: mi-innerblocks-block columns-{ columns }, } ) const template = [ [ core/heading, { placeholder: Título de la sección, level: 3 } ], [ core/paragraph, { placeholder: Escribe el contenido... } ], ] return () } setAttributes( { showTitle: val } ) } /> setAttributes( { columns: val } ) } min={ 1 } max={ 4 } /> setAttributes( { showTitle: ! showTitle } ) } /> { showTitleTítulo de sección
}Explicación clave del edit.js
- useBlockProps: aplica atributos y estilos al wrapper del bloque de forma compatible con la API.
- InspectorControls: panel lateral donde colocamos ToggleControl y RangeControl para modificar atributos.
- BlockControls: controla la barra superior del bloque con botones personalizados.
- InnerBlocks: permite anidar bloques aquí se pasan allowedBlocks, template, templateLock y renderAppender.
5. save.js (salida del bloque)
En la función save usamos InnerBlocks.Content para serializar el contenido anidado y produce la salida HTML final que se guarda en el contenido de la entrada.
import { useBlockProps, InnerBlocks } from @wordpress/block-editor
export default function Save( props ) {
const { attributes } = props
const { backgroundColor, showTitle, columns } = attributes
const blockProps = useBlockProps.save( {
style: {
backgroundColor: backgroundColor,
padding: 1rem,
},
className: mi-innerblocks-block columns-{ columns },
} )
return (
{ showTitle Título de sección
}
)
}
6. estilo básico (editor y front-end)
Ejemplo de CSS para columnas adaptables y espaciado.
.mi-innerblocks-block {
box-sizing: border-box
}
.mi-innerblocks-block .mi-seccion-titulo {
margin-top: 0
}
.mi-innerblocks-block.columns-1 > .wp-block {
width: 100%
}
.mi-innerblocks-block.columns-2 > .wp-block {
width: 50%
}
.mi-innerblocks-block.columns-3 > .wp-block {
width: 33.3333%
}
.mi-innerblocks-block.columns-4 > .wp-block {
width: 25%
}
/ Asegúrate de que los bloques hijos se comporten como elementos en fila /
.mi-innerblocks-block > .wp-block {
display: inline-block
vertical-align: top
}
7. Compilar con @wordpress/scripts
Configura package.json con scripts para compilación:
{
name: mi-innerblocks-block,
version: 1.0.0,
scripts: {
build: wp-scripts build,
start: wp-scripts start
},
devDependencies: {
@wordpress/scripts: ^25.0.0
}
}
Coloca la entrada en src/index.js y configura block.json para apuntar a build/index.js. Ejecuta npm run build o npm run start mientras desarrollas.
8. Buenas prácticas y consejos
- Usa atributos en block.json para que Gutenberg pueda serializarlos correctamente.
- Prefiere InnerBlocks.Content en save para dejar que Gutenberg serialice los bloques hijos.
- Si necesitas controlar la estructura inicialmente, usa template. Si quieres bloquear completamente la estructura, usa templateLock: all.
- Define allowedBlocks para evitar que se inserten bloques no deseados.
- Para estilos personalizados en el editor, registra editor.css y asegúrate de compilarlo en build/editor.css.
- Prueba la accesibilidad y la edición con diferentes tamaños de pantalla.
9. Ejemplo avanzado: renderAppender personalizado
Puedes quitar el renderizador por defecto y usar uno propio para ofrecer un botón con etiqueta personalizada.
import { InnerBlocks } from @wordpress/block-editor
import { Button } from @wordpress/components
function CustomAppender() {
return (
)
}
// En el edit:
10. Consideraciones sobre compatibilidad y rendimiento
- Evita ejecutar lógica costosa en el componente de edición guarda lo mínimo necesario en atributos.
- Si necesitas contenido dinámico (p. ej. basado en visitas o consultas), usa renderizado del lado servidor (server-side render) con render_callback en PHP.
- Usa className y estilos en CSS en lugar de inline cuando puedas, para facilitar la cache y la separación de responsabilidades.
Conclusión
Crear un bloque con InnerBlocks y controles personalizados en JS te permite construir secciones flexibles y potentes para editores de contenido en WordPress. La clave es entender la separación entre edición (edit.js) y salida (save.js), usar InnerBlocks para la anidación y aprovechar InspectorControls y BlockControls para exponer configuraciones al usuario. Con block.json y @wordpress/scripts la experiencia de desarrollo es mucho más sencilla y estandarizada.
|
|
Acepto donaciones de BAT's mediante el navegador Brave 🙂 |
