Search code examples
javascriptwordpresswordpress-gutenberg

extending a core block doesn't work inside the editor


i want to extend the group core block, and add to it a rotate inline style. i read and use the hooks. when i add the rotate it is saved and display correctly in the front. But nothing is changed in the editor even though i have a function to update the attribute.

this is my code for the edit part to extend the core group block:

const testingAdvancedControls = wp.compose.createHigherOrderComponent(

(BlockEdit) => {

return (props) => {

    // prepare all the variables needed 

    //const { post_id, block_count } = this.props; 

    const { Fragment } = wp.element;

    const {
        PanelBody,
        RangeControl,
    } = wp.components;

    const { InspectorAdvancedControl, InspectorControls, ColorPalette } = wp.blockEditor;

    const { attributes, setAttributes, isSelected, post_id, block_count, clientId, context } = props;


    //functions 

    const updateRotate = (newR) => {
        setAttributes({ rotate: (newR === undefined ? '' : newR) });
    }

    return (

        <Fragment>
            <BlockEdit {...props} />
            {isSelected &&
                <InspectorControls>

                    {isSelected && (props.name == 'core/group') &&

                        <PanelBody title={__('test rotate', 'testing')}
                            initialOpen={false}>

                            <RangeControl
                                label={__('Rotate', 'testing')}
                                value={attributes.rotate}
                                onChange={updateRotate}
                                min={-50}
                                max={50}
                                step={0.1}
                                help={__('Rotate the group', 'testing')}
                                allowReset={true}
                                initialPosition={0}
                            />

                        </PanelBody>
                    }

                </InspectorControls>

            }

        </Fragment>

    )

}

  }, 'testingAdvancedControls'

  );

   wp.hooks.addFilter(
    'editor.BlockEdit',
    'gutrs/add-testing-controls',
    testingAdvancedControls
);

why the rotation doesn't displayed inside the editor? any idea? if i give the rotete attribute a value in the editor it is passed to the front end but nothing in the editor.

any ideas?


Solution

  • The Editor renders classNames and styles differently to the frontend; with added specificity. To add your own rotate control that updates the visual style the Editor, there are 3 key steps:

    1. Add a rotate attribute to core/group via registerBlockType:
    function addRotateAttribute(settings, name) {
        if (name !== 'core/group') {
            return settings;
        }
    
        return lodash.assign({}, settings, {
            attributes: lodash.assign({}, settings.attributes, {
                rotate: {
                    type: 'number',
                    default: 0
                },
            }),
        });
    }
    
    wp.hooks.addFilter(
        'blocks.registerBlockType',
        'gutrs/add-rotate-attribute',
        addRotateAttribute
    );
    
    1. Add the Inspector Controls to the target block (simplified version of your code)
    const { createHigherOrderComponent } = wp.compose;
    const { InspectorControls } = wp.blockEditor;
    const { PanelBody, RangeControl } = wp.components;
    
    const testingAdvancedControls = createHigherOrderComponent((BlockEdit) => {
    
        return (props) => {
            const { attributes, setAttributes } = props;
    
            return (
                <>
                    <BlockEdit {...props} />
                    {props.name == 'core/group' && (
                        <InspectorControls>
                            <PanelBody title={__('test rotate', 'testing')}
                                initialOpen={false}>
                                <RangeControl
                                    label={__('Rotate', 'testing')}
                                    value={attributes.rotate}
                                    onChange={(val) => setAttributes({ rotate: val })}
                                    min={-50}
                                    max={50}
                                    step={0.1}
                                    help={__('Rotate the group', 'testing')}
                                    allowReset={true}
                                    initialPosition={0}
                                />
                            </PanelBody>
                        </InspectorControls>
                    )}
                </>
            );
        };
    }, 'testingAdvancedControls');
    
    wp.hooks.addFilter(
        'editor.BlockEdit',
        'gutrs/add-testing-controls',
        testingAdvancedControls
    );
    
    1. Alter the props of BlockListBlock to add an inline style for rotate using the block attributes for the Editor only:
    const withRotate = createHigherOrderComponent(
        (BlockListBlock) => {
    
            return (props) => {
    
                const {
                    name: blockName,
                    attributes: { style, rotate },
                    wrapperProps,
                } = props;
              
                if (rotate === undefined) {
                    // Block doesn't support rotate, return default props
                    return <BlockListBlock {...props} />;
                }
    
                // Setup new props to add inline rotate style
                const newProps = {
                    ...props,
                    wrapperProps: {
                        ...wrapperProps,
                        style: {
                            rotate: rotate + 'deg',
                            ...wrapperProps?.style,
                        },
                    },
                };
    
                return <BlockListBlock {...newProps} />;
            }
        },
        'withRotateStyle'
    );
    
    wp.hooks.addFilter(
        'editor.BlockListBlock',
        'gutrs/with-rotate-style',
        withRotate
    );
    

    Reference: Based on how withChildLayoutStyles is implemented.

    Result: Group Block with Rotate

    It's an interesting result that could make adding more content a bit tricky, but I was curious to see how it would work out..