In the evolving world of web development, the WordPress Block Editor (Gutenberg) has revolutionized how we design and manage content. In this blog post, we’ll walk through the entire process—from setup to seeing our custom block in action.

Why Create Custom Blocks?

While WordPress provides plenty of built-in blocks, we often find ourselves needing tailor-made solutions for unique layouts, content types, or interactive components. That’s where custom blocks shine. With @wordpress/scripts, we get a modern development environment with Webpack, Babel, and other tools already configured.

What Is @wordpress/scripts?

@wordpress/scripts is a package maintained by the WordPress core team. It abstracts away the configuration complexity, letting us focus on writing our block logic using modern JavaScript (React + JSX) and CSS.

Creating a custom block

Step 1: Set Up the Plugin Folder

We start by creating a plugin directory in wp-content/plugins/

mkdir my-basic-block
cd my-basic-block

Now, we create the main plugin file: my-basic-block.php

<?php
/**
 * Plugin Name: My Basic Block
 * Description: A simple custom Gutenberg block.
 * Version: 1.0.0
 * Author: DarkMatter-999
 */

defined( 'ABSPATH' ) || exit;

function my_basic_block_register_block() {
    register_block_type( __DIR__ . '/build/my-basic-block' );
}
add_action( 'init', 'my_basic_block_register_block' );

Step 2: Initialize Node.js and Install Dependencies

Initialize a Node.js project

npm init -y
npm install @wordpress/scripts --save-dev

Update package.json with build scripts

{
  "name": "my-basic-block",
  "version": "1.0.0",
  "scripts": {
    "start": "wp-scripts start",
    "build": "wp-scripts build"
  },
  "devDependencies": {
    "@wordpress/scripts": "^28.0.0"
  }
}

Step 3: Create Block Source Files

block.json — Block Metadata

Create the block metadata file: src/my-basic-block/block.json

{
  "$schema": "https://schemas.wp.org/trunk/block.json",
  "apiVersion": 3,
  "name": "learning/my-basic-block",
  "version": "0.1.0",
  "title": "My Basic Block",
  "category": "text",
  "icon": "universal-access-alt",
  "description": "A basic Gutenberg block built manually.",
  "textdomain": "my-basic-block",
  "editorScript": "file:./index.js"
}

index.js — Block Code

Now register the block using the metadata we defined: src/my-basic-block/index.js

import { registerBlockType } from '@wordpress/blocks';
import metadata from './block.json';

registerBlockType(metadata.name, {
	edit: () => {
		return <p>Hello World! This is my basic block. (Editor)</p>;
	},
	save: () => {
		return <p>Hello World! This is my basic block. (Frontend)</p>;
	},
});

Step 4: Build the Block

npm run build

After this, a build/ directory will be created, and the compiled version of our block will be ready for WordPress.

Step 5: Activate and Use the Block

  1. Go to Plugins → Installed Plugins in our WordPress dashboard.
  2. Activate My Basic Block.
  3. Create or edit a post.
  4. Search for “My Basic Block” and insert it into the page.
  5. We’ll see the static message in both editor and frontend.

Bonus: Why Not Use create-block?

npx @wordpress/create-block@latest my-basic-block

Well, that command is great for quickly scaffolding a full-featured plugin with everything preconfigured. But doing it manually — like we did — helps us understand how block metadata, build scripts, PHP registration, and block JavaScript all connect together. It’s a great learning experience.

Wrapping Up

We just created our first custom Gutenberg block from scratch, using modern tools like @wordpress/scripts. This is the foundation for building dynamic, reusable, and powerful blocks in WordPress. Going forward, we can add interactivity, styling, and advanced features like block controls, Inspector panels, and even dynamic server-side rendering.

Leave a Reply

Your email address will not be published. Required fields are marked *