Add Button To Editor For All Shortcodes

WordPress shortcodes was introduced in WordPress version 2.5 and is a great way of adding full flexibility and control of certain functionality to the editor of your WordPress CMS. The best thing about shortcodes is that it allows editors to run a certain bit of code within the content area of your site. Having the ability of adding shortcodes means that the editor can also select the position to place this bit of content.

An example shortcode that comes in the WordPress core is the gallery shortcode.

[gallery]

This allows you to add a number of images into the content of your post. The flexibility of this feature means that it can allow developers to also attach a number of different attributes so the editor can choose different things to customise the functionality.

[gallery id="123" size="medium"]

I think this is one of the most powerful features that comes with WordPress. But this features isn't very user friendly to your average user, it's kind of like writing HTML in the editor, some users aren't used to this and can get confused.

Another problem you can face with shortcodes is that you are relying on the developer to provide good documentation of exactly what the shortcode does and exactly what attributes you can use. Even if the developer did provide good documentation on the shortcodes then you will always need this to hand when writing content.

Because we are developing in WordPress we have full control over what we can do in the CMS which means we can create a button to add to the TinyMCE editor which lists all the shortcodes we can use in your application. The following tutorial will go through all the code we need to create this shortcodes button so the editor can select the shortcode they want to use from a dropdown.

shortcode-dropdown

Create Plugin

First we are going to start off by creating a new plugin and defining the methods that we are going to need to use. We start off by adding the plugin header comments to define the plugin.

/*
Plugin Name: Paulund Shortcode TinyMCE Plugin
Description: A WordPress plugin that will add a button to the tinyMCE editor to add shortcodes
Plugin URI: http://www.paulund.co.uk
Author: Paulund
Author URI: http://www.paulund.co.uk
Version: 1.0
License: GPL2
*/

Then we can create a new class with the following methods:

  • Constructor
  • pu_shortcode_button
  • pu_add_buttons
  • pu_register_buttons
  • pu_get_shortcodes
new Shortcode_Tinymce();
class Shortcode_Tinymce
{
    public function __construct()
    {

    }

    public function pu_shortcode_button()
    {

    }

    public function pu_add_buttons( $plugin_array )
    {

    }

    public function pu_register_buttons( $buttons )
    {

    }

    public function pu_get_shortcodes()
    {

    }
}
?>

Constructor

The constructor is used to add two actions, one will run on the admin init which will be used to add the new buttons to the TinyMCE editor.

The second action is going to add some Javascript code to the footer of the page which we will use to know what data to add to the dropdown.

public function __construct()
    {
        add_action('admin_init', array($this, 'pu_shortcode_button'));
        add_action('admin_footer', array($this, 'pu_get_shortcodes'));
    }

pu_shortcode_button()

On the admin init action we are going to run this method, which will setup the filters we need to add buttons to the TinyMCE editor. The editor comes with a number of filters that we can use to customise TinyMCE as much as we want, but the filters we are going to use are:

  • mce_external_plugins
  • mce_buttons

mce_external_plugins - Allows you to add extra Javascript that we can use to add the data into the dropdown.

mce_buttons - This allows you to add the ID of the new buttons we are going to add.

public function pu_shortcode_button()
    {
        if( current_user_can('edit_posts') &&  current_user_can('edit_pages') )
        {
            add_filter( 'mce_external_plugins', array($this, 'pu_add_buttons' ));
            add_filter( 'mce_buttons', array($this, 'pu_register_buttons' ));
        }
    }

pu_add_buttons()

This method will run on the mce_external_plugins filter, and we will use this to add the Javascript file we need to add our shortcode content in the editor.

public function pu_add_buttons( $plugin_array )
    {
        $plugin_array['pushortcodes'] = plugin_dir_url( __FILE__ ) . 'js/shortcode-tinymce-button.js';

        return $plugin_array;
    }

pu_register_buttons()

The register buttons method is going to run on the mce_buttons filter, this method has a parameter which is an array of buttons that are being applied to the editor. To add new buttons to the editor we just need to append new IDs to the array.

public function pu_register_buttons( $buttons )
    {
        array_push( $buttons, 'separator', 'pushortcodes' );
        return $buttons;
    }

pu_get_shortcodes()

This method is ran on the admin_footer action of the plugin, we are going to use this method to create a Javascript variable which is an array of all the shortcodes that are currently registered with WordPress. We can get all the shortcodes by using the global variable of $shortcode_tags.

public function pu_get_shortcodes()
    {
        global $shortcode_tags;

        echo '<script type="text/javascript">
        var shortcodes_button = new Array();';

        $count = 0;

        foreach($shortcode_tags as $tag => $code)
        {
            echo "shortcodes_button[{$count}] = '{$tag}';";
            $count++;
        }

        echo '</script>';
    }

Shortcode Editor Javascript

In the method pu_add_buttons() we define a Javascript file that we are going to use in the plugin. This Javascript file will use the array of shortcodes we create with pu_get_shortcodes() and populate the dropdown on the editor.

The following Javascript code is what we will use to populate the dropdown and execute the command to add the shortcodes to the TinyMCE editor.

WordPress 3.8 or lower

The following Javascript code will only work for WordPress 3.8 and lower.
(function() {
    tinymce.create('tinymce.plugins.pushortcodes', {

        init : function(ed, url) {
            var t = this;
            t.editor = ed;
        },

        //Creates the dropdown
        createControl : function(n, cm)
        {
            if(n=='pushortcodes')
            {
                var button = cm.createListBox('shortcode_dropdown',
                {
                     title : 'Shortcodes',
                     onselect : function(code) {
                        if(tinyMCE.activeEditor.selection.getContent() == '')
                        {
                            tinyMCE.activeEditor.selection.setContent( '['+code+']' );
                        }
                        else
                        {
                            tinyMCE.activeEditor.execCommand('mceReplaceContent', false, '['+code+']{$selection}[/'+code+']');
                        }
                        return false;
                     }
                });

                //Add the options to the dropdown
                for(var count=0; count<shortcodes_button.length; count++)
                {
                    button.add('['+shortcodes_button[count]+']', shortcodes_button[count]);
                }

                return button;
            }
            return null;
        }
    });

    tinymce.PluginManager.add('pushortcodes', tinymce.plugins.pushortcodes);

})();

WordPress 3.9

In WordPress 3.9 TinyMce was upgraded to version 4 so following Javascript code will only work for WordPress 3.9.
(function() {

    tinymce.PluginManager.add('pushortcodes', function( editor )
    {
        var shortcodeValues = [];
        jQuery.each(shortcodes_button, function(i)
        {
            shortcodeValues.push({text: shortcodes_button[i], value:i});
        });

        editor.addButton('pushortcodes', {
            type: 'listbox',
            text: 'Shortcodes',
            onselect: function(e) {
                var v = e.control._value;

                tinyMCE.activeEditor.selection.setContent( '[' + v + '][/' + v + ']' );
            },
            values: shortcodeValues
        });
    });
})();

All the above code is used so that we can create a button for the editor to easily select a shortcode from the TinyMCE toolbar.

shortcode-dropdown

This now makes it very easy for the editor to select a shortcode and it will automatically be added to the content of the post.

Full Plugin Code

<?php
/*
Plugin Name: Shortcode TinyMCE Plugin
Description: A WordPress plugin that will add a button to the tinyMCE editor to add shortcodes
Plugin URI: http://www.paulund.co.uk
Author: Paulund
Author URI: http://www.paulund.co.uk
Version: 1.0
License: GPL2
*/

/*

    Copyright (C) Year  Author  Email

    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License, version 2, as
    published by the Free Software Foundation.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
*/
new Shortcode_Tinymce();
class Shortcode_Tinymce
{
    public function __construct()
    {
        add_action('admin_init', array($this, 'pu_shortcode_button'));
        add_action('admin_footer', array($this, 'pu_get_shortcodes'));
    }

    /**
     * Create a shortcode button for tinymce
     *
     * @return [type] [description]
     */
    public function pu_shortcode_button()
    {
        if( current_user_can('edit_posts') &&  current_user_can('edit_pages') )
        {
            add_filter( 'mce_external_plugins', array($this, 'pu_add_buttons' ));
            add_filter( 'mce_buttons', array($this, 'pu_register_buttons' ));
        }
    }

    /**
     * Add new Javascript to the plugin scrippt array
     *
     * @param  Array $plugin_array - Array of scripts
     *
     * @return Array
     */
    public function pu_add_buttons( $plugin_array )
    {
        $plugin_array['pushortcodes'] = plugin_dir_url( __FILE__ ) . 'js/shortcode-tinymce-button.js';

        return $plugin_array;
    }

    /**
     * Add new button to tinymce
     *
     * @param  Array $buttons - Array of buttons
     *
     * @return Array
     */
    public function pu_register_buttons( $buttons )
    {
        array_push( $buttons, 'separator', 'pushortcodes' );
        return $buttons;
    }

    /**
     * Add shortcode JS to the page
     *
     * @return HTML
     */
    public function pu_get_shortcodes()
    {
        global $shortcode_tags;

        echo '<script type="text/javascript">
        var shortcodes_button = new Array();';

        $count = 0;

        foreach($shortcode_tags as $tag => $code)
        {
            echo "shortcodes_button[{$count}] = '{$tag}';";
            $count++;
        }

        echo '</script>';
    }
}
?>

Advertise here

Comment