Programando Bloques para WordPress con Advanced Custom Fields (ACF Blocks)

ACF Blocks es una herramienta poderosa incluida en el plugin Advances Custom Fields PRO (Versión Premium) que nos ayudará a desarrollar cualquier bloque para WordPress que tengamos en nuestra imaginación e integrarle todo tipo de habilidades de diseño.

Antes de crear un bloque, debemos pensar en las funciones que vamos a necesitar y determinar cuales partes de nuestro bloque van a ser editables y cuales se comportarán de una forma estática o dinámica.

Con ACF Blocks, no hay límites para lo que puedes construir. Desde bloques estáticos sencillos hasta bloques dinámicos más complejos a los que le puedes añadir las mismas características que se encuentran en los bloques principales de WordPress, incluso variaciones de diseño entre otras muchas opciones. Los bloques se desarrollan por lo general en PHP, HTML y CSS, además también pueden contener JavaScript personalizado para potenciar la interactividad.

¿Qué son exactamente estos ACF Blocks? Son la clave para desbloquear la versatilidad y el potencial de personalización en tu sitio web. Puedes crear una colección de bloques basados en los diseños de un proyecto con todas sus características, como InnerBlocks, Variaciones y Estilos, y así tener el control total sobre su apariencia y funcionalidad.

Una parte muy importante es la escalabilidad de estos bloques por si en un momento determinado se requieren de nuevas funciones o contenidos que no estaban estipulados en los diseños.

ACF Blocks construye la estructura y contenido sobre la marcha a partir de una plantilla PHP, mientras que ACF maneja su representación.

En este tutorial, veremos el proceso de creación de un bloque de «Features» utilizando ACF Blocks, explorando cómo registrar los campos requeridos en ACF para llevar el diseño al siguiente nivel.

Este es el diseño del bloque «Features» que vamos a desarrollar.

A tener en cuenta

Hay varias opciones para organizar los bloques de ACF, lo puedes hacer desde el child theme que estés utilizando, organizarlos dentro de un plugin de personalizaciones o crearte un tema hijo pensado para bloques (WordPress tiene una herramienta para generar estos temas muy fácilmente https://wordpress.org/plugins/create-block-theme/).

Necesitarás tener acceso a la carpeta /wp-content/plugins/{plugin-personalizaciones} o /wp-content/themes/{child-theme}. Esto se puede hacer desde un gestor por FTP y trabajar con un editor de código como puede ser Visual Studio Code.
*importante: al modificar código PHP o Javascript puede ser que un error te deje sin acceso a la web, asegurate de tener siempre un plan B para poder recuperar un estado accesible de la web.

Comenzamos…

Lo primero que tenemos que hacer es registrar el o los bloques en el functions.php del child theme o en el archivo nombre-plugin-persoanilades.php que se ejecutará en el caso de hacerlo mediante un plugin. Para ello utilizaremos la función de WordPress register_block_type(), a la cual le pasaremos la ruta del directorio del bloque la cual llevará dentro un archivo block.json.

function spirit_register_acf_blocks() {
    /**
     * We register our block's with WordPress's handy
     * register_block_type();
     *
     * @link https://developer.wordpress.org/reference/functions/register_block_type/
     */
    register_block_type( __DIR__ . '/blocks/features' );
}

add_action( 'init', 'spirit_register_acf_blocks' );

Con esta acción, ACf ya puede reconocer que existe un bloque llamado «features».

Toca crear directorios y archivo. En el child theme crearemos los directorios /blocks y /acf-json. En el primero irán listados todos los directorios de los bloques que vamos a necesitar y acf-json almacenará de forma automática los grupos de campos de ACF que asociemos a nuestros bloques.

Ahora en nuestro caso dentro del directorio /blocks vamos a crear un directorio /features donde irán 3 archivos que recogerán toda la lógica y estructura del bloque: block.json, features.php y features.css

El archivo block.json contiene toda la información en forma de metadatos del bloque.

{
    "name": "acf/features",
    "title": "Features",
    "description": "Bloque para mostrar las características mas importantes de mi proyecto.",
    "style": [ "file:./features.css" ],
    "category": "formatting",
    "icon": "block-default",
    "keywords": ["Bloque Features"],
    "acf": {
        "mode": "preview",
        "renderTemplate": "features.php"
    },
    "supports": {
        "anchor": true,
        "color": true,
        "multiple": true,
        "spacing": {
            "margin": ["bottom", "top"],
            "padding": true
        }
    }
}

¿Qué significa cada uno de los metadatos del archivo block.json?

  • name: Identificador único, si no lo indicas ACF especifica uno.
  • title: Etiqueta del bloque, lo que vas a ver en la interfaz de ACF y WordPress.
  • description: Explicación breve del propósito del bloque.
  • style: Referencia del archivo CSS. En este caso features.css
  • category: Categoría de los bloques nativos de WordPress donde se añadirá este bloque. Opciones permitidas: text, media, design, widgets, theme, embed.
  • icon: Icono del bloque utilizando la librería dashicon o un SVG.
  • Keywords: Palabras clave para encontrar el bloque.
  • acf: Configuración del modo de vista previa (preview, auto o edit) y del archivo de plantilla utilizado para renderizar los campos de ACF. En este caso features.php
  • supports: Objeto para indicar las características del bloque. Permite anular ciertos supports, interesante para añadir opciones de alineación, colores o espaciados como margin o padding.
Representación de soporte colores y espaciados.

Puedes obtener mas información en: https://developer.wordpress.org/block-editor/reference-guides/block-api/block-metadata/

Crear grupo de campos con ACF para el bloque

Para mi bloque he creado un grupo de campos de la siguiente forma, cabe destacar que hay un campo repeater (Versión PRO de ACF). Este campo me permite añadir sub grupos de campos tantas veces quiera o le haya indicado. En mi caso añade un sub grupo con imagen, encabezado y descripción corta.

*Importante indicar donde vamos a querer que se muestren estos campos. Buscamos en bloque que sea igual a features.

*Te recomiendo que cada campo tenga un nombre de campo único. Yo suelo repetir nombres de etiqueta por ejemplo Encabezado pero luego el nombre del campo le suele poner encabezado_bloque_features para no tener un conflicto de campos duplicados.

Desarrollamos el Template y la hoja de estilos

La parte mas complicada es la de crear el template del bloque, no te asustes, la documentación de Advanced Custom Fields para la creación de bloques es muy buena. Te dejo algunos enlaces que puedes consultar.

https://www.advancedcustomfields.com/resources/blocks/

https://www.advancedcustomfields.com/resources/create-your-first-acf-block/

https://www.advancedcustomfields.com/resources/acf-blocks-key-concepts/

La manera de renderizar el contenido de los campos de ACF lo tienes o bien en la documentación de Advanced Custom Fields o también existe un plugin llamado ACF Theme Code for Advanced Custom Fields tiene una versión gratuita pero para lo que estamos haciendo necesitas tener la versión PRO.

Te explico en que consiste la estructura que he montado para mi bloque «features». Puedes ver el código mas abajo.

Lo que hago primero es poner en variables todos los campos que introduzco a través de acf, de esta forma hago una llamada a la base de datos y puedo reutilizar ese contenido todas las veces que necesite, es una buena práctica para el rendimiento de la web.

Luego introduzco 3 condicionales:

  • Hacemos referencia del id del bloque el cual puedo utilizar como anchor, en este caso hace una comprobación y si dentro del bloque en WordPress no le he indicado un id en la sección avanzado del bloque «Anclaje HTML» entonces ACF crea un id único para mi bloque. Introducimos el resultado en una variable llamada $id.
  • De igual forma hacemos referencia a la clase del bloque o classname. La encontramos en la sección avanzada del bloque «Clase(s) CSS adicional(es)». Este condicional añade tantas clases sean necesarias concatenándolas dentro de la variable llamada $classes.
  • Condicional que detecta si el bloque que hemos creado tiene asignada una alineación. En ese caso añadirá nuevas clases asignadas a esas características del bloque, de nuevo concatenándolas dentro la variable $classes.

Por último tenemos que crear una estructura semántica del bloque. Utiliza HTML y PHP para maquetar todo el contenido, extrae la información de la base de datos mediante funciones de ACF como get_field() y get_sub_field().

Comprueba si los campos tienen contenido para evitar renderizar espacios es blanco con if get_field() o if sub_get_field(). Cerrando el condicional siempre con endif;

Utiliza las variables que hemos ido creando por toda la estructura del bloque. Coloca este código en el archivo features.php.

<?php
/**
 * Block template file: features.php
 *
 * Features Block Template.
 *
 * @param   array $block The block settings and attributes.
 * @param   string $content The block inner HTML (empty).
 * @param   bool $is_preview True during AJAX preview.
 * @param   (int|string) $post_id The post ID this block is saved to.
 */


 // Load values and assign defaults.
 $encabezado_sup        = get_field( 'encabezado_sup_bloque_features' );
 $encabezado_principal  = get_field( 'encabezado_principal_bloque_features' );
 $color_fondo           = get_field( 'color_fondo_bloque_features' ); 
 $text_color            = get_field( 'color_textos_bloque_features' );
 $colo_borde            = get_field( 'color_bordes_bloque_features' );


// Create id attribute allowing for custom "anchor" value.
$id = 'features-' . $block['id'];
if ( ! empty($block['anchor'] ) ) {
    $id = $block['anchor'];
}

// Create class attribute allowing for custom "className" and "align" values.
$classes = 'block-features';
if ( ! empty( $block['className'] ) ) {
    $classes .= ' ' . $block['className'];
}
if ( ! empty( $block['align'] ) ) {
    $classes .= ' align' . $block['align'];
}

?>

<style type="text/css">
	<?php echo '#' . $id; ?> {
		/* Add styles that use ACF values here */
	}
</style>

<section id="<?php echo esc_attr( $id ); ?>" class="bloque__features <?php echo esc_attr( $classes ); ?>">
    <?php if ( !empty( $encabezado_sup ) ) :?>
	    <p class="bloque__features__encabezado-sup"><?php echo wp_kses_post( $encabezado_sup ); ?></p>
    <?php endif;?>
	<h2 class="bloque__features__encabezado-principal"><?php echo wp_kses_post( $encabezado_principal ); ?></h2>
    <div class="bloque__features__grupo">
        <?php if ( have_rows( 'features_bloque_features' ) ) : ?>
            <?php while ( have_rows( 'features_bloque_features' ) ) : the_row(); ?>
                <?php
                $icono                 = get_sub_field( 'icono_feature_bloque_features' );
                $encabezado_feature    = get_sub_field( 'encabezado_feature_bloque_features' );
                $descripcion_feature   = get_sub_field( 'descripcion_corta_feature_bloque_features' ); 
                ?>
            	<article class="bloque__features__grupo__feature">
                    <?php if ( $icono ) : ?>
                        <img class="bloque__features__grupo__feature-icon" src="<?php echo wp_kses_post( $icono ); ?>" />
                    <?php endif ?>
                    <h3 class="bloque__features__grupo__feature-encabezado"><?php echo wp_kses_post( $encabezado_feature ); ?></h3>
                    <p class="bloque__features__grupo__feature-descripcion-corta"><?php echo wp_kses_post( $descripcion_feature ); ?> ?></p>
            	</article>
            <?php endwhile; ?>
        <?php else : ?>
            <?php // No rows found ?>
        <?php endif; ?>
    </div>
</section>

?>

Mediante el archivo features.css no hay limitaciones para dar estilo al bloque, las posibilidades son infinitas. Incluso programando una buena lógica entre campos y estructura puedes tener variaciones de un mismo bloque con multiples interpretaciones del mismo.

.bloque__features {
    padding-block: 3rem;
    --color-border-spirit:#D9D9D9;
}

p.bloque__features__encabezado-sup {
    margin-block: 0 !important;
    text-transform: uppercase;
    text-align: center;
}

h2.bloque__features__encabezado-principal {
    font-size: clamp(2rem, 2.5vw + 1.5rem, 3.5rem);
    line-height: 100%;
    font-weight: 900;
    text-align: center;
    max-width: 520px;
    margin-block:0;
    margin-inline: auto;
    text-transform: uppercase;
    letter-spacing: -4px;
}

.bloque__features__grupo {
    display: grid;
    grid-template-columns: repeat(3, minmax(0, 1fr));
    text-align: center;
    margin-block: 2%;
    padding: 2rem;
}

article.bloque__features__grupo__feature {
    padding: 1rem;
}

h3.bloque__features__grupo__feature-encabezado {
    margin-top: 1rem;
    margin-bottom: 10px;
    font-size: 24px;
    letter-spacing: -1px;
}

p.bloque__features__grupo__feature-descripcion-corta {
    max-width: 310px;
    margin-inline: auto;
    line-height: 21px;
    font-size: 16px;
    letter-spacing: 2px;
    font-weight: 500;
}

article.bloque__features__grupo__feature {
    border-right: 1px solid var(--color-border-spirit);
}

article.bloque__features__grupo__feature:nth-child(3) {
    border-right: 0px;
}

article.bloque__features__grupo__feature:nth-child(6) {
    border-right: 0px;
}

article.bloque__features__grupo__feature:nth-child(1) {
    border-bottom: 1px solid var(--color-border-spirit);
}

article.bloque__features__grupo__feature:nth-child(2) {
    border-bottom: 1px solid var(--color-border-spirit);
}

article.bloque__features__grupo__feature:nth-child(3) {
    border-bottom: 1px solid var(--color-border-spirit);
}


@media (max-width: 900px) {

    .bloque__features__grupo {
        grid-template-columns: repeat(2, minmax(0, 1fr));
    }

    article.bloque__features__grupo__feature {
        border-right: 1px solid var(--color-border-spirit) ;
    }

    article.bloque__features__grupo__feature:nth-child(3) {
        border-right: 1px solid var(--color-border-spirit);
    }

    article.bloque__features__grupo__feature:nth-child(2) {
        border-right: 0px;
    }

    article.bloque__features__grupo__feature:nth-child(4) {
        border-right: 0px;
    }

    article.bloque__features__grupo__feature:nth-child(4) {
        border-bottom: 1px solid var(--color-border-spirit);
    }
}

@media (max-width: 600px) {

    .bloque__features__grupo {
        grid-template-columns: repeat(1, minmax(0, 1fr));
    }

    article.bloque__features__grupo__feature {
        border-right: 0px;
        border-bottom: 1px solid var(--color-border-spirit);
    }

    article.bloque__features__grupo__feature:nth-child(3) {
        border-right: 0;
    }
}

Introduciendo el bloque y el contenido

Ahora ya tienes todos el bloque montado, lo que tienes que hacer es ir a editar una página de WordPress y buscar entre los bloques el nuestro «features».

Cuando lo añades, en la barra lateral derecha te aparecen todos los campos que hemos puesto con ACF, conforme los vas rellenando puedes ver como el bloque se va montando. Lo bueno y por lo que me gusta mucho esta técnica es que el cliente nunca puede romper los estilos que ya están preparados específicamente para cada bloque.

Conclusión

Mucha gente piensa que hacer tus bloques con ACF es una pérdida de tiempo, a mi parecer, si que se necesita tiempo para desarrollarlos de forma óptima. Cuando estoy creando mis propios bloques no me importa ni el diseño que me han enviado ni la funcionalidad que me piden que haga, al final todo se puede desarrollar.

Esta práctica tiene muchos beneficios, por un lado ganas en velocidad de carga, no utilizo maquetadores visuales que pueden sobrecargar la web, tengo la posibilidad de escalar un bloque a niveles elevados, posibilidad de hacer variaciones útiles para mis clientes y lo que es mejor, no recibo llamadas o emails de clientes diciéndome que se han cargado el diseño de la web.

Esto que te he contado solo es la punta del iceberg en la creación de bloques personalizados, existe mucha mas información que te ayudarán a ser un mejor desarrollador de proyectos a medida.

Si crees que me falta algo o necesitas saber mas de este tema, házmelo saber a través del formulario o comentarios.

Otras funciones para mejorar tus bloques de ACF

Recomendaciones Extra

  • Considera crear en HTML y CSS un prototipo del bloque que quieres desarrollar. Luego es mas sencillo la incorporación del contenido mediante PHP o el dinamismo con Javascript.

Herramientas útiles

Sobre el autor

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *