A WordPress Macro Shortcode

Avoiding the Post Editor’s HTML Mode

Good News Everyone! The post/page editor is getting an upgrade with the soon-to-be-released version 3.2 of WordPress. This solves the problem of disappearing Google maps and YouTube videos. Both rely on iframe elements to embed the contents of one webpage into another. Unfortunately, the current version of WordPress’ built-in editor doesn’t like iframes* and you have to limit yourself to working in the editor’s HTML mode. Once you switch to Visual mode, the iframe elements are stripped out of your post or page and the map or video disappears.

In WordPress 3.2RC1 (aka: Release Candidate 1) currently running on this blog, iframe elements are saved as I switch between the editor’s Visual and HTML modes. So are most of the new HTML5 tags including: the canvas and video elements – but not the audio element! This has been reported as a bug.

In the discussions on blogs and WordPress forums, one of the solutions for working with iframes was to use a general purpose shortcode to work around the editor’s restrictions. This approach is worth a second look because it gives authors the capability to embed anything they damn well please in a post without ever having to use the editor’s HTML mode – a big plus for some of my clients who go totally cross-eyed whenever they look at HTML.

The Macro Shortcode

Say you want to show a Google map in a post about an event happening in your neighborhood park. Getting the map is easy:

Example of using Google Maps embed code

The idea behind the Macro Shortcode is that the embed code from Google (an iframe element) is pasted into a custom field for the post. The name of the custom field can be something descriptive, like “google-map”. In the WordPress editor, inside the Custom Fields box, click on the “Enter New” link to create a new custom field with the name, “google-map”.

inserting embed code into a custom field

Now, you can place a shortcode anywhere in the content of a post or page where you want the map to appear:

[macro name="g00gle-map"]

To make this work, you need to define the macro shortcode and add it to your theme. The following PHP code added to your theme’s functions.php file does the trick.

// macro shortcode — a function to insert the value of a custom field into a post
// [macro page=<page_id> name="post-custom-field-key"]

function my_macro( $atts, $content = null ) {
    extract(shortcode_atts(array( 'page'=>'', 'name'=>'' ), $atts));
    global $post;
    if (!is_numeric($page)) $page = $post->ID;
    return get_post_meta($page, $name, true);
add_shortcode('macro', 'my_macro');

Make sure you first backup the file. See the WordPress Codex for more information on the get_post_meta() and add_shortcode() functions.

The macro shortcode will also accept a post or page id parameter which gets a custom field from some other page or post. This is handy when a small block of marked up content is needed in more than one place on the site. For example, to create a customized signature macro that can be added to the ends of posts (like you do with emails,) you could add a custom field to your bio page. Let’s say this bio page has an id of  3 and you’ve created a custom field attached to that page, named it “signature” and gave it the following value:

<p style="text-align: right; color: red;">That's All Folks! 
&mdash;<a href="http://loonytunes.fun/bios/bugs"><em>B.Bunny</em></a></p>

Now, all you have to do is insert this shortcode at the end of your posts:

[macro page=3 name="signature"]

and it will be replaced with your red, right-aligned sign-off message.



* TinyMCE, the WordPress built-in editor, is a JavaScript program that runs in the user’s browser. It doesn’t like the  iframe element because it’s not valid xhtml which the editor is compelled to output when operating in the Visual mode. In the HTML mode, it doesn’t care; you’re on your own.