Search code examples
javascriptphpwordpress-gutenberggutenberg-blocks

How to add multiple of same custom gutenberg block on same page?


I've made a custom gutenberg button and it works fine, both in editor and frontend. The problem is when i add multiple of the same block on one page, only the first one is showing up.

Gutenberg Editor: Gutenberg Editor

Frontend: Frontend


My custom block:

theme/blocks/sst_button/block.json

{
    "apiVersion": 2,
    "name": "sst/button",
    "version": "0.1.0",
    "title": "button",
    "category": "sst",
    "description": "Example block written with ESNext standard and JSX support – build step required.",
    "supports": {
        "html": false,
        "url": true,
        "align": ["wide"]
    },
    "textdomain": "sst-button",
    "attributes": {
        "style": {
            "type": "string",
            "default": ""   
        },
        "link": {
            "type": "object",
            "default": {"opensInNewTab": true, "link": null}    
        },
        "opensInNewTab": {
            "type": "boolean",
            "default": false    
        },
        "alignment": {
            "type": "string",
            "default": "left"   
        },
        "text": {
            "type": "string",
            "default": "Button text"    
        }
    }
}

theme/blocks/sst_button/sst_button.php

<?php

function sst_button_init() {
    wp_register_script( 'sst-button-js', get_template_directory_uri() . '/blocks/sst_button/build/index.js', array( 'wp-server-side-render','wp-block-editor', 'wp-blocks', 'wp-element', 'wp-i18n', 'wp-polyfill' ));
    wp_register_style( 'sst-button-editor-style', get_template_directory_uri() . '/blocks/sst_button/build/index.css');
    wp_register_style( 'sst-button-style', get_template_directory_uri() . '/blocks/sst_button/build/style-index.css');
    
    register_block_type( __DIR__,
        array(
            'editor_script'   => 'sst-button-js',
            'editor_style'    => 'sst-button-editor-style',
            'style'           => 'sst-button-style',
            'render_callback' => 'sst_button_dynamic_render_callback',
        ) 
    );
}
add_action( 'init', 'sst_button_init' );

function sst_button_dynamic_render_callback( $attributes, $content ) {
    ob_start();
    include_once __DIR__ . "/template.php";
    return ob_get_clean();
}

theme/blocks/sst_button/template.php

<?php 
    // $attributes, $content
    $classes = $attributes['align']? 'align-'. $attributes['align'] : '';   
    $style = $attributes['style'] ? "style-".$attributes['style'] : '';
    $text = $attributes['text'];
    $opensInNewTab = $attributes['link']['opensInNewTab'];
    $link = $attributes['link']['url'];
    $alignment = $attributes['alignment'];
?>


<div class="wp-block-sst-button" style="--alignment:<?php echo $alignment ?>">
    <a href="<?php echo $link;?>" target="<?php echo $opensInNewTab? "_blank" : '';?>" class="sst_button <?php echo $style;  ?>">
        <?php echo $text; ?>
    </a>
</div>

theme/blocks/sst_button/src/index.js

import { registerBlockType } from '@wordpress/blocks';
import './style.scss';
import Edit from './edit';
registerBlockType( 'sst/button', {
    edit: Edit,
    save: () => null,
} );

theme/blocks/sst_button/src/edit.js

import { __ } from '@wordpress/i18n';
import { useBlockProps,BlockControls, AlignmentToolbar, RichText} from '@wordpress/block-editor';
import './editor.scss';
import CustomInspectorControls from '../components/CustomInspectorControls';

export default function Edit(props) {
    
    const { attributes, setAttributes } = props;
    const {style, alignment} = attributes;
    return (
        <>
            <div { ...useBlockProps() }  style={{"--alignment":alignment}}>
                <button className={`sst_button ${style && `style-${style}`}`}>
                        <RichText
                            value={ attributes.text } 
                            allowedFormats={ [ 'core/bold', 'core/italic' ] } 
                            onChange={ ( text ) => setAttributes( { text } ) } 
                            placeholder={ __( 'Button text' ) } 
                        />
                </button>
                <BlockControls>
                        <AlignmentToolbar
                            value={ alignment }
                            onChange={ (alignment)=> setAttributes({alignment}) }
                        />
                </BlockControls>
            </div>
            <CustomInspectorControls attributes={attributes} setAttributes={setAttributes}/>
        </>
    );
}

Solution

  • Changed include_once to include in 'sst_button.php' and got it working