'Wordpress Gutenberg Anchor Support for Dynamic Block
I want to have anchor support for my dynamic wordpress block. I did
//in registerBlockType
supports: {
anchor: true,
},
This adds the HTML Anchor control under the sidebar panel.
My block is a dynamic block that has
save: ( props ) => {
return <InnerBlocks.Content />;
}
I tried everything to get the anchor
attribute to to frontend. According to this github issue I should add
anchor: {
type: 'string',
source: 'attribute',
attribute: 'id',
selector: '*',
},
to the blocks attributes. This will make the anchor
available in the save
function via props.anchor
, however it never appears in my render_callback
$attributes
.
This is basically a port of the github issue to SO. Hope anyone can help here.
Solution 1:[1]
if anyone is still interested this worked for me:
so this is my custom block registering, this statement will enable standard wordpress HTML anchor field (with valuable validation for spaces etc.) under Advanced tab of selected gutenberg block:
supports: {
anchor: true
}
then in the same place we define:
attributes: {
anchor: {
type: 'string'
}
}
then in save function (I have it exactly for the same purpose of InnerBlocks
):
save: function(props) {
const { anchor } = props.attributes;
return (
el( anchor, {}),
el( InnerBlocks.Content, {})
);
}
if you are using jsx
, the save function could look like this:
save: function(props) {
const { anchor } = props.attributes;
return (
<div id={anchor}>
<InnerBlocks.Content />
</div>
);
}
then in your render callback function (in php) it's going to be available via first arg's (which is array) element
function your_callback( $block, $content ) {
// display your anchor value
echo $block['anchor'];
}
Solution 2:[2]
Have you tried manually adding a field that will take care of the ID attribute?
Something like this:
<InspectorControls>
<PanelBody title={ __( 'Element Settings' ) }>
<TextControl
label={ __( 'Element ID', 'fleximpleblocks' ) }
value={ elementID}
placeholder={ __( 'Type in the element ID…' ) }
onChange={ ( value ) => setAttributes( { elementID: value } ) }
/>
</PanelBody>
</InspectorControls>
And then:
save: ( props ) => {
return <InnerBlocks.Content id={ props.attributes.elementID } />;
}
I'm not sure if it'll work, I'm just taking a wild guess here. Let me know how it goes :)
Solution 3:[3]
You could use this filter (targeting whatever blocks you want)
const withAnchor = props => {
if (props.attributes) { // Some blocks don't have attributes
props.attributes = {
...props.attributes,
anchor: {
type: 'string'
}
}
}
return props
}
wp.hooks.addFilter(
'blocks.registerBlockType',
'namespace/with-anchor',
withAnchor
)
And then you can access the 'anchor' attribute in the render callback
'render_callback' => function($attributes) {
echo $attributes['anchor'];
}
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | honk31 |
Solution 2 | Rodrigo D'Agostino |
Solution 3 | Rice_Crisp |