Block Registration

  • JNext lesson
  • KPrevious lesson
  • FSearch lessons
  • EscClear search

How Blocks Are Discovered

On the acf/init hook (priority 5), the function acf_blocks_load_blocks() scans the blocks/ directory for subdirectories containing a block.json file. For each valid block directory, three things happen:

  1. The block is registered with WordPress via register_block_type().
  2. ACF field groups are loaded from JSON files in the same directory.
  3. An extra.php file is included if it exists.

block.json Format

Every block uses ACF Block API v3 with standard WordPress block metadata. Here is a representative example:

{
  "apiVersion": 3,
  "name": "acf/accordion",
  "title": "Accordion",
  "description": "A customizable accordion block with FAQ schema support.",
  "category": "acf-blocks",
  "icon": "list-view",
  "keywords": ["accordion", "faq", "toggle"],
  "acf": {
    "renderTemplate": "accordion-block.php",
    "blockVersion": 3
  },
  "supports": {
    "align": ["wide", "full"],
    "mode": true,
    "jsx": true,
    "anchor": true
  },
  "style": "file:./accordion.css",
  "editorStyle": "file:./accordion.css"
}

Key fields:

  • name – Must start with acf/. This is the block’s unique identifier.
  • category – Set to acf-blocks so the block appears in the ACF Blocks inserter category.
  • acf.renderTemplate – The PHP file used to render the block. Path is relative to the block directory.
  • acf.blockVersion – Set to 3 for ACF Block v3 behavior.
  • supports.jsx – When true, the block supports InnerBlocks.
  • supports.mode – When true, the block can switch between edit and preview mode.
  • style – Path to the block’s CSS file, loaded on the frontend (conditional) and in the editor.
  • editorStyle – Path to editor-only styles (often the same file as style).

Field Group Registration

The function acf_blocks_register_field_groups() scans each block directory for *.json files, skipping block.json. Each JSON file should contain an ACF field group definition with a key and fields array. The function calls acf_add_local_field_group() for each valid group.

Both single group objects and arrays of groups are supported:

{
  "key": "group_accordion_fields",
  "title": "Accordion",
  "fields": [ ... ],
  "location": [[
    { "param": "block", "operator": "==", "value": "acf/accordion" }
  ]],
  "active": true
}

The location rule ties the field group to its block. This is standard ACF configuration.

Because field groups are registered with acf_add_local_field_group(), they are “local” to the plugin. They do not appear in the ACF field group admin UI for editing and cannot be accidentally overwritten by database-stored groups.

Style Pre-Registration

On init (priority 5), acf_blocks_register_styles() scans all block directories and calls wp_register_style() for each block’s CSS file. The handle format is {block-name}-style (e.g. acf-accordion-style).

This pre-registration is what enables conditional loading. WordPress automatically enqueues a registered block style only on pages where that block is rendered, rather than loading all 29 stylesheets on every page.

The extra.php File

If a block directory contains an extra.php file, it is require_once‘d during block registration. This file typically registers AJAX handlers, content filters, or additional scripts.

Five blocks include extra.php:

  • star-rating-block – Registers the frontend rating submission script and the AJAX handler for saving ratings.
  • post-display – Optimizes the ACF relationship field query for better performance.
  • section-block – Registers an editor-only script with a custom InnerBlocks component.
  • toc-block – Adds heading ID attributes to post content and injects scroll-margin CSS.
  • url-preview – Registers the admin AJAX handlers for fetching URL metadata and importing images.

Adding a New Block

To add a new block:

  1. Create a new directory under blocks/ (e.g. blocks/my-block/).
  2. Add a block.json with the required metadata.
  3. Add a block-data.json with the ACF field group definition.
  4. Create the render template (e.g. my-block.php).
  5. Optionally add a CSS file and reference it in block.json.
  6. Optionally add an extra.php for additional hooks.

The block is automatically registered on the next page load. No changes to any other file are needed.