I’m a big fan of the social media icons block in WordPress:
Social media links are such a common design element, and it’s now one less thing to think about when building a new website. No more icon libraries or grainy PNGs of social media logos.
One downside of the social links block is that you have to manually enter the URLs every time you place them on a template, in the footer, etc. For a project I’m working on, we’re building a custom settings page where the user can enter basic business info- hours, location, Facebook page- and then we’ll dynamically populate it throughout the site. (I’m not using an ACF Options page for this, but you certainly could.)
To accomplish this, we’re going to take advantage of the render_block_*
filter available in WordPress. By using the block name to build the filter, we’ll end up with something like this: add_filter( 'render_block_core/social-link', ... )
which will allow us to filter the $block_content
– the actual HTML markup of the social link block as the page is rendering it.
Note that we’re filtering the core/social-link
block, not the core/social-links
block – that extra s
at the end is for the parent block that holds all of the links in the row. We want to modify the inner block that contains the single link itself.
The general function will look something like this:
function filter_social_icons_block( $block_content, $block ) {
// Do stuff.
return $block_content;
}
add_filter( 'render_block_core/social-link', 'filter_social_icons_block', 10, 2 );
Code language: PHP (php)
The filter also provides us with a second argument: $block
, the full block array, including the attribute values. This will be important because which social network service the block is rendering will be saved as an attribute value in there: $block['attrs']['service']
. We check the service, looking for the social network we want to filter, and then swap out the URL.
To swap the actual URL, we’ll use the WP_HTML_Tag_Processor
to find the link and set the href
attribute:
if ( 'twitter' === $block['attrs']['service'] && '' !== $new_twitter_url ) {
$new_content = new WP_HTML_Tag_Processor( $block_content );
if ( $new_content->next_tag( 'a' ) ) {
$new_content->set_attribute( 'href', $new_twitter_url );
}
$block_content = $new_content->get_updated_html();
}
Code language: PHP (php)
And that’s basically it! Let’s put it all together:
The options here are pretty open. You could use this method to add a CSS class or force links to open in a new tab. You could show different social link URLs in different situations, for example swapping in an author’s personal Twitter link on a single blog post template.
Of course, there are some limitations: the social icons do have to be added to the template- you can’t dynamically pick which icons to display (at least not with this filter). But this is just one example of the flexibility available when you embrace the render_block
filter. Just remember that the filter only runs on the front of your website, not in the block editor, so anything you do with it will not show up inside the editor, only on the final page render.
Update: Reader Nahuai Badiola pointed out an alternate method, where you add the URL to the attributes earlier using the render_block_data
filter. I think I might actually prefer this approach (though there are definitely use cases when modifying the rendered block HTML is the way to do it). Since the URL is stored as a block attribute, we can just swap it out before the block is actually rendered. Here’s a link to his gist.
Leave a Reply