DIGITALREP

How to make a basic WordPress pluginOctober 14, 2013

The WordPress plugin we will develop in this tutorial will use custom HTML and CSS to display and style a tag cloud. It will also load a couple of jQuery libraries and a jQuery script that will override the default hover method of the links in our tag cloud so we can add some special effects.

The plugin file

In the WordPress plugin file itself (custom_tag_cloud.php), begin by adding the required methods of the class:

class Custom_Tag_Cloud extends WP_Widget
{
  function __construct()
  {
  }
  function update($new_instance, $old_instance)
  {
  }
  function form($instance)
  {
  }
  function widget($args, $instance)
  {
  }
}

At the bottom of the script, outside of the class we just implemented, we need to write code that registers the widget during the normal WordPress widget initiation call:

function my_widget_init()
{
  register_widget(‘Custom_Tag_Cloud’);
  do_action(‘widgets_init’);
}
add_action(‘init’, ‘my_widget_init’, 1);

Now we can start filling out the methods in our Custom_Tag_Cloud class, starting with the constructor:

public function __construct()
{
  parent::__construct(
    custom_tag_cloud,
    __(‘Custom Tag Cloud’, ‘custom-tag-cloud’),
    array(‘description’ => __(‘A custom implementation of the Tag Cloud’, ‘custom-tag-cloud’)));
}

The first argument is the base id (it can be false, in which case WordPress will choose one for you based on the plugin name), and the second and third options are what your users will see as the widget’s title and description in the Widgets Administration screen.

The functions __() (and _e for echoing) allow a string to be translated into another language. The first argument is the string to translate and the second argument is the text domain. The text domain should be the base name of your plugin without underscores. Language translation requires several extra steps so it won’t be covered in this tutorial.

The update method

The next method to look at is the update method. It is used by WordPress to update the instance array (which contains all of our widget’s options) with up-to-date values. It fires when the user hits save on our widget’s option panel or the widget option panel is reloaded. Notice that any values taken from text inputs are properly sanitised:

function update($new_instance, $old_instance) {
  $instance[‘title’] = strip_tags(stripslashes($new_instance[‘title’]));
  $instance[‘taxonomy’] = $new_instance[‘taxonomy’];
  $instance[‘bgcolour’] = $new_instance[‘bgcolour’];
  $instance[‘txtcolour’] = strip_tags(stripslashes($new_instance[‘txtcolour’]));
  return $instance;
}

The form method

The next function to look at is form. This function displays the form that allows the user to update the widget’s options. It uses the instance array values to pre-populate form inputs so the user doesn’t have to enter the options when the widget options panel is reloaded.

When pre-populating text inputs all we have to do is set the value of the input to the appropriate instance variable, provided that variable is already set. These text inputs are for the title and text colour options:

function form($instance) {
  <?
  <p>
    <label for=”get_field_id(‘title’); ?>”>
      <?php _e(‘Title:’, ‘custom-tag-squares’) ?>
    </label>
    <input
      type=”text”
      class=”widefat”
      id=”<?php echo $this->get_field_id(‘title’); ?>”
      name=”<?php echo $this->get_field_name(‘title’); ?>”
      value=”<?php if(isset($instance[‘title’])) {
        echo esc_attr($instance[‘title’]);
      } ?>”
    />
  </p>
  <p>
    <label for=”<?php echo $this->get_field_id(‘txtcolour’); ?>”>
      <?php _e(‘Text Colour: (i.e. blue or #003366)’, ‘custom-tag-cloud’) ?  >
    </label>
    <input
      type=”text”
      class=”widefat”
      id=”<?php echo $this->get_field_id(‘txtcolour’); ?>”
      name=”<?php echo $this->get_field_name(‘txtcolour’); ?>”
      value=”<?php if (isset($instance[‘txtcolour’])) {
        echo esc_attr( $instance[‘txtcolour’] );
      } ?>”
    />
  </p>

I also want to display a dropdown box that offers colour choices for the user to select from.

  <?php
    $colours = array(
      “#FFFF00” => “Yellow”,
      “#0000FF” => “Blue”,
      “#FFA500” => “Orange”,
      “#008000” => “Green”);
  ?>

When populating dropdown boxes, or indeed, any other type of input element (checkbox, radio, etc), in order to populate it with predetermined values, you just need to record what is currently selected and then check it against each option in order to determine whether to set that option as ‘selected’ or not. In the case of our ‘select’ element, if nothing is currently selected then the default (first) option will be used.

  <?php $current_colour = $instance[‘bgcolour’]; ?>
  <p>
    <label for=”<?php echo $this->get_field_id(‘bgcolour’); ?>”>
      <?php _e(‘Background Colour:’, ‘custom-tag-cloud’) ?>
    </label>
    <select
      class=”widefat”
      id=”get_field_id(‘bgcolour’); ?>”
      name=”get_field_name(‘bgcolour’); ?>”>
      <?php foreach($schemes as $option => $name) : ?>
        <option value=”<?php echo $option ?>”
        <?php if($current_colour == $option) {
          echo ‘selected=”selected”‘;
        }?>>
        <?php echo $name; ?>
        </option>
      <?php endforeach; ?>
    </select>
  </p>

The next select element is built by making a call get_taxonomies to get the list of taxonomies, be they categories, tags, or other custom taxonomies. Each taxonomy object is extracted by calling get_taxonomy. Each object returned by get_taxonomy has its own properties set, one of which (show_tagcloud) determines whether we are allowed to show its children in a tag cloud. If that is set to true then it will be shown as an option, otherwise it won’t be and the loop will continue on to the next object.

At the very top is a check to see if $instance[‘taxonomy’] exists yet or if it’s empty (i.e. if this is the very first time the widget has been loaded). If it’s empty or doesn’t exist yet we set the current taxonomy to ‘tags’, otherwise set it to whatever it has been set to by the user.

The only other thing to note here is that WordPress has its own in-built function to check which option is already selected (selected($variable_to_check, $what_is_already_selected)):

  <?php
    if(!empty($instance[‘taxonomy’]) && taxonomy_exists($instance[‘taxonomy’])) {
      $current_taxonomy = $instance[‘taxonomy’];
    } else {
      $current_taxonomy = ‘post_tags’;
    }
  ?>
  <p>
    <label for=”<?php echo $this->get_field_id(‘taxonomy’); ?>”>
      <?php _e(‘Taxonomy:’, ‘digitalrep-tag-squares’) ?>
    </label>
    <select
      class=”widefat”
      id=”<?php echo $this->get_field_id(‘taxonomy’); ?>”
      name=”<?php echo $this->get_field_name(‘taxonomy’); ?>”>
      <?php foreach(get_taxonomies() as $taxonomy) :
        $tax = get_taxonomy($taxonomy);
        if(!$tax->show_tagcloud || empty($tax->labels->name))
          continue;
      ?>
        <option value=”<?php echo esc_attr($taxonomy) ?>”
        <?php selected($taxonomy, $current_taxonomy) ?>>
          <?php echo $tax->labels->name; ?>
        </option>
      <?php endforeach; ?>
    </select>
  </p>
  <?php
}

The widget logic

The widget function will contain the logic for displaying our custom tag cloud.

At the top of this script we will extract the widget options and load them into local variables (these options include theme-specific markup that is added before and after the widget markup). We will also grab the form instance variables. Take note that unlike the drop-down menus the text inputs (title and txtcolour) can be left empty, so it’s a good idea to set default values for them if this is the case:

function widget($args, $instance)
{
  extract($args);

  $bgcolour = $instance[‘bgcolour’];
  $taxonomy = $instance[‘taxonomy’];

  if(!empty($instance[‘txtcolour’])) {
    $txtcolour = $instance[‘txtcolour’];
  } else {
    $txtcolour = “#000000”;
  }

  if(empty($title)) {
    $title = ‘Tag Cloud’;
  } else {
    $title = $instance[‘title’];
  }

Next, we build an array of items based on the chosen taxonomy by passing it to get_terms() along with an array containing any display options we want to include (the maximum number of terms to display, the display order, etc). Once we have our array of terms, we loop through it and display each term wrapped in inline CSS that incorporates the text and background colour determined by the widget’s options:

  echo $before_widget;
  echo $before_title . $title . $after_title;
  echo ‘<div id=”tagcloud” style=”overflow: hidden;”>’;

  $tags = get_terms($taxonomy, array(‘orderby’ => ‘id’, ‘order’ => ‘DESC’, ‘hide_empty’ => 0, ‘number’ => 12));

  if(empty($tags) || is_wp_error($tags)) {
    return;
  } else {
    foreach($tags as $key => $tag) {
      echo “<a style=’float: left; padding: 4px; margin: 4px; background: $bgcolour; color: $txtcolour;’ class=’tagcloud_term'”;
      echo “href=’get_term_link(intval($tag->term_id), $tag->taxonomy)’>$tag->name</a>”;
    }
  }

  echo “</div>\n”;
  echo $after_widget;
}

Including Scripts

With this plugin I will be including both the jQuery library and my own jQuery script; I will also include a CSS file just to show you how to do it, despite the fact that it’s not really necessary for this plugin.

At the bottom of the Custom_Tag_Cloud class, after the my_widget_init() function and the add_action call, add this function:

function my_include_js()
{
  wp_enqueue_style(‘custom-tag-cloud-style’, plugins_url(‘custom_tag_cloud/style.css’));
  wp_enqueue_script(‘base-library’, ‘https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js’);
  wp_enqueue_script(‘custom-script’, plugins_url(‘custom_tag_cloud/js/custom.js’));
}

As you can see above wp_enqueue_style loads your plugin’s CSS, and wp_enqueue_script loads your plugin’s JS. Both functions take two arguments – the name of the script/style and its location. (Note that if you name any of the scripts ‘jquery’ it will cause WordPress to load its own local version of jQuery which may or may not work properly with your code).

As before with the widget initialisation, you have to use a WordPress action hook (wp_enqueue_scripts) in order to execute this function:

add_action(‘wp_enqueue_scripts’, ‘my_include_js’);

Custom jQuery Script

I’ve included the jQuery user interface library so that we can do something fancy (albeit impractical) with the terms in our widget.

When you include jQuery in a WordPress plugin, you can’t just use the coveted dollar sign as you usually would as there could be conflicts with other plugins (they might forget to give it back after borrowing it, for example). So you do it like this to avoid heartache:

jQuery(document).ready(function()
{
  jQuery(“.tagcloud_term”).hover(function() {
    jQuery(this).animate({ opacity:0.4 }, 300);
  }, function() {
    jQuery(this).animate({ opacity:1 }, 300);
  });
});

The jQuery above simply animates the opacity of each of our tag cloud links. Animate is called first with a CSS object {property:numeric value} and secondly with a time for the animation to take to complete. The callback function below the .hover function simply fires when the .hover action has completed.

Folder Structure

All files are contained within a folder named custom_tag_squares/. Inside of that lives style.css, custom_tag_squares.php and a folder called js/. Inside the folder js/ is custom.js.

All that you need to do now is to add to a .zip file (custom_tag_squares.zip) and upload it to WordPress using the Plugins > Add New menu in the Administration Screen.

Category: Tutorials
Tags:  

Leave a Reply

Your email address will not be published. Required fields are marked *