Create An Image Slide Plugin Part 6: Create Taxonomy Term Meta

Create An Image Slide Plugin Part 6: Create Taxonomy Term Meta

In this post we’ll be adding a few pieces of metadata to the sliders we’ll be creating using the taxonomy we added to our custom post type in an earlier post.

In the previous post we talked about metadata and we created a custom meta box in which we collect additional information about each slide we create.

The metadata we’ll be adding in this post will concern each slider that will be created for collecting multiple slides. The new metadata will affect the behavior of each slider in various ways.

The metadata for each slider will consist of:

  • Transition type
  • Transition duration
  • Timeout between slides
  • Show navigation
  • Pause slider on hover over slide
  • Autoplay
  • Aspect ratio

To add the term metadata we’ll be extending the term edit form which you can see in the screenshot:

WordPress taxonomy term meta

Create Taxonomy Term Meta In WordPress

If you want to follow along I’ve set up a GitHub repository where you’ll find the code from this series. The finished code for this post is in the part_6 branch. If you want to follow along please download the part_5 branch.

In this post we’re gonna be working in two files: /includes/class-monospace-slides.php and /admin/class-monospace-slides-taxonomy-term-meta.php which doesn’t exist so we’ll have to create it.

Adding metadata to taxonomy terms is done by using dynamically built hooks. So, we’ll be using a hook like {$taxonomy}_add_form_fields to add the meta fields. For our mnsp_slider custom taxonomy this will be mnsp_lider_add_form_fields.

In order to save the term metadata we’ll hook into the action that fires when the term is being saved, that hook being created_{$taxonomy}. For our specific taxonomy that is created_mnsp_slider.

When we want to update the term meta we’ll need to use yet another hook in the form of {$taxonomy}_edit_form_fields. In the case of our slider taxonomy we’ll be using the mnsp_slider_edit_form_fields hook.

The last scenario is for saving the updated fields which uses a hook in the form of edited_{$taxonomy}. Applied to our taxonomy, the hook becomes edited_mnsp_slider.

Now, let’s get on to coding the functionality we’ve outlined above.

Starting in the first file we mentioned earlier, we’re gonna tell the constructor of the class to run a function that defines the hooks needed for our taxonomy term metadata.

We’ll do this on the last line from the function below in the same way we added the hooks for the custom meta box.

/**
 * Define the core functionality of the plugin.
 *
 * Set the plugin name and the plugin version that can be used throughout the plugin.
 * Load the dependencies, define the locale, and set the hooks for the admin area and
 * the public-facing side of the site.
 *
 * @since    1.0.0
 */
public function __construct() {
	if ( defined( 'PLUGIN_NAME_VERSION' ) ) {
		$this->version = PLUGIN_NAME_VERSION;
	} else {
		$this->version = '1.0.0';
	}
	$this->plugin_name = 'monospace-slides';

	$this->load_dependencies();
	$this->set_locale();
	$this->define_admin_hooks();
	$this->define_public_hooks();

	$this->define_metabox_hooks();
	$this->define_term_meta_hooks();

}

Next, we need to create the define_term_meta_hooks()  function in which we’ll define the hooks needed to create the term metadata. The function below contains that code.

Add the code below after the define_metabox_hooks() function, near the end of the file.

/**
 * Register all of the hooks related to taxonomy term meta
 *
 * @since 		1.0.0
 * @access 		private
 */
private function define_term_meta_hooks() {

	$plugin_term_meta = new Monospace_Slides_Taxonomy_Term_Meta( $this->get_plugin_name(), $this->get_version() );

	if ( is_admin() ) {
		$this->loader->add_action( 'mnsp_slider_add_form_fields', $plugin_term_meta, 'create_fields', 10, 2 );
		$this->loader->add_action( 'mnsp_slider_edit_form_fields', $plugin_term_meta, 'edit_fields', 10, 2 );
		$this->loader->add_action( 'created_mnsp_slider', $plugin_term_meta, 'save_fields', 10, 1 );
		$this->loader->add_action( 'edited_mnsp_slider', $plugin_term_meta, 'save_fields', 10, 1 );
	}

}

As you can see, all those dynamic hooks we talked about earlier are used in this function.

This is all the code that we’ll be adding in this file.

Next, we’re moving on to add the code in the newly created /admin/class-monospace-slides-admin-taxonomy-term-meta.php file.

Here is the entire contents of the file which we’ll examine closely.

<?php

/**
 * The admin-specific functionality for the slider taxonomy term metadata.
 *
 * @link       https://www.mikeinmonospace.com/
 * @since      1.0.0
 *
 * @package    Monospace_Slides
 * @subpackage Monospace_Slides/admin
 */

/**
 * The admin-specific functionality for the slider taxonomy term metadata.
 *
 * Defines all the functionality related to the slide options metabox.
 *
 * @package    Monospace_Slides
 * @subpackage Monospace_Slides/admin
 * @author     Mike In Monospace <mikeinmonospace@gmail.com>
 */

class Monospace_Slides_Taxonomy_Term_Meta {

	/**
	 * The ID of this plugin.
	 *
	 * @since    1.0.0
	 * @access   private
	 * @var      string    $plugin_name    The ID of this plugin.
	 */
	private $plugin_name;

	/**
	 * The version of this plugin.
	 *
	 * @since    1.0.0
	 * @access   private
	 * @var      string    $version    The current version of this plugin.
	 */
	private $version;

	public function meta_fields() {

		return
			array(
				array(
					'label' => esc_html__( 'Transition Type', 'monospace-slides' ),
					'id' => 'mnsp-slider-transition-type',
					'default' => 'slide',
					'type' => 'select',
					'options' => array(
						'slide' => esc_html__( 'Slide', 'monospace-slides' ),
						'fade' => esc_html__( 'Fade', 'monospace-slides' ),
					),
				),
				array(
					'label' => esc_html__( 'Transition Duration', 'monospace-slides' ),
					'id' => 'mnsp-slider-transition-duration',
					'default' => 300,
					'type' => 'number',
				),
				array(
					'label' => esc_html__( 'Timeout Between Slides', 'monospace-slides' ),
					'id' => 'mnsp-slider-timeout',
					'default' => 3000,
					'type' => 'number',
				),
				array(
					'label' => esc_html__( 'Show Navigation Controls', 'monospace-slides' ),
					'id' => 'mnsp-slider-show-nav',
					'default' => '1',
					'type' => 'checkbox',
				),
				array(
					'label' => esc_html__( 'Pause Slider On Hover Over Slide', 'monospace-slides' ),
					'id' => 'mnsp-slider-pause-hover',
					'default' => '1',
					'type' => 'checkbox',
				),
				array(
					'label' => esc_html__( 'Autoplay', 'monospace-slides' ),
					'id' => 'mnsp-slider-autoplay',
					'default' => '1',
					'type' => 'checkbox',
				),
				array(
					'label' => esc_html__( 'Aspect Ratio', 'monospace-slides' ),
					'id' => 'mnsp-slider-aspect',
					'default' => 'wide',
					'type' => 'radio',
					'options' => array(
						'wide' => esc_html__( 'Wide 16:9', 'monospace-slides' ),
						'classic' => esc_html__( 'Classic 4:3', 'monospace-slides' ),
						'square' => esc_html__( 'Square 1:1', 'monospace-slides' ),
					),
				),
			);

	}

	public function __construct() {

		$this->plugin_name = $plugin_name;
		$this->version = $version;

	}

	public function create_fields( $taxonomy ) {

		$output = '';

		foreach ( $this->meta_fields() as $meta_field ) {

			$label = '<label for="' . $meta_field['id'] . '">' . $meta_field['label'] . '</label>';

			$meta_value = $meta_field['default'];			

			switch ( $meta_field['type'] ) {
				case 'checkbox':
					$input = sprintf(
						'<input %s id="%s" name="%s" type="checkbox" value="1">',
						$meta_value === '1' ? 'checked' : '',
						$meta_field['id'],
						$meta_field['id']
						);
					break;
				case 'radio':
					$input = '<fieldset>';
					$input .= '<legend class="screen-reader-text">' . $meta_field['label'] . '</legend>';
					$i = 0;
					foreach ( $meta_field['options'] as $key => $value ) {
						$meta_field_value = !is_numeric( $key ) ? $key : $value;
						$input .= sprintf(
							'<label><input %s id="%s" name="%s" type="radio" value="%s"> %s</label>%s',
							$meta_value === $meta_field_value ? 'checked' : '',
							$meta_field['id'],
							$meta_field['id'],
							$meta_field_value,
							$value,
							$i < count( $meta_field['options'] ) - 1 ? '<br>' : ''
						);
						$i++;
					}
					$input .= '</fieldset>';
					break;
				case 'select':
					$input = sprintf(
						'<select id="%s" name="%s">',
						$meta_field['id'],
						$meta_field['id']
					);
					foreach ( $meta_field['options'] as $key => $value ) {
						$meta_field_value = !is_numeric( $key ) ? $key : $value;
						$input .= sprintf(
							'<option %s value="%s">%s</option>',
							$meta_value === $meta_field_value ? 'selected' : '',
							$meta_field_value,
							$value
						);
					}
					$input .= '</select>';
					break;
				case 'number':
					$input = sprintf(
						'<input id="%s" name="%s" type="%s" value="%s">',
						$meta_field['id'],
						$meta_field['id'],
						$meta_field['type'],
						$meta_value
					);
					break;
				default:
					$input = sprintf(
						'<input id="%s" name="%s" type="%s" value="%s">',
						$meta_field['id'],
						$meta_field['id'],
						$meta_field['type'],
						$meta_value
					);
			}

			$output .= '<div class="form-field">'.$this->format_rows( $label, $input ).'</div>';

		}

		echo $output;
	}

	public function edit_fields( $term, $taxonomy ) {

		$output = '';

		foreach ( $this->meta_fields() as $meta_field ) {

			$label = '<label for="' . $meta_field['id'] . '">' . $meta_field['label'] . '</label>';

			$meta_value = get_term_meta( $term->term_id, $meta_field['id'], true );

			switch ( $meta_field['type'] ) {
				case 'checkbox':
					$input = sprintf(
						'<input %s id=" % s" name="% s" type="checkbox" value="1">',
						$meta_value === '1' ? 'checked' : '',
						$meta_field['id'],
						$meta_field['id']
						);
					break;
				case 'radio':
					$input = '<fieldset>';
					$input .= '<legend class="screen-reader-text">' . $meta_field['label'] . '</legend>';
					$i = 0;
					foreach ( $meta_field['options'] as $key => $value ) {
						$meta_field_value = !is_numeric( $key ) ? $key : $value;
						$input .= sprintf(
							'<label><input %s id=" % s" name="% s" type="radio" value="% s"> %s</label>%s',
							$meta_value === $meta_field_value ? 'checked' : '',
							$meta_field['id'],
							$meta_field['id'],
							$meta_field_value,
							$value,
							$i < count( $meta_field['options'] ) - 1 ? '<br>' : ''
						);
						$i++;
					}
					$input .= '</fieldset>';
					break;
				case 'select':
					$input = sprintf(
						'<select id="%s" name="%s">',
						$meta_field['id'],
						$meta_field['id']
					);
					foreach ( $meta_field['options'] as $key => $value ) {
						$meta_field_value = !is_numeric( $key ) ? $key : $value;
						$input .= sprintf(
							'<option %s value="%s">%s</option>',
							$meta_value === $meta_field_value ? 'selected' : '',
							$meta_field_value,
							$value
						);
					}
					$input .= '</select>';
					break;
				case 'number':
					$input = sprintf(
						'<input id="%s" name="%s" type="%s" value="%s">',
						$meta_field['id'],
						$meta_field['id'],
						$meta_field['type'],
						$meta_value
					);
					break;
				default:
					$input = sprintf(
						'<input id="%s" name="%s" type="%s" value="%s">',
						$meta_field['id'],
						$meta_field['id'],
						$meta_field['type'],
						$meta_value
					);
			}

			$output .= $this->format_rows( $label, $input );

		}

		echo '<div class="form-field">' . $output . '</div>';

	}

	public function format_rows( $label, $input ) {

		return '<tr class="form-field"><th>'.$label.'</th><td>'.$input.'</td></tr>';

	}

	public function save_fields( $term_id ) {

		foreach ( $this->meta_fields() as $meta_field ) {

			if ( isset( $_POST[ $meta_field['id'] ] ) ) {
				switch ( $meta_field['type'] ) {
					case 'email':
						$_POST[ $meta_field['id'] ] = sanitize_email( $_POST[ $meta_field['id'] ] );
						break;
					case 'text':
						$_POST[ $meta_field['id'] ] = sanitize_text_field( $_POST[ $meta_field['id'] ] );
						break;
				}

				update_term_meta( $term_id, $meta_field['id'], $_POST[ $meta_field['id']] );
			} else if ( $meta_field['type'] === 'checkbox' ) {
				update_term_meta( $term_id, $meta_field['id'], '0' );
			}

		}

	}

}

Taking a closer look at this file, we notice that it looks a lot like the file we created for the custom meta box in the previous post. The functionality is pretty much the same, it just applies to different content.

In the previous post we added metadata to the mnsp_slide custom content type. In this post we’re adding metadata to the mnsp_slider custom taxonomy of that custom content type.

So, let’s go through this file and break it down so we can better understand what’s going on.

Just like in the previous post, we’re creating a class to house of the functionality for the taxonomy term meta.

Next, the meta_fields() function defines all the fields that are added to every taxonomy term and then come the functions for creating, editing and saving the metadata fields.

Now, if you add these changes to the plugin in your WordPress installation and go to Slides > Sliders, you should see something like the first image in this post, that is all the new metadata fields in the term edit form.

At The End

There’s been a lot of code in this post, but it has been very familiar because it was very similar to the code in the previous post so you should not have any major issues.

In a future post we’ll use all these meta fields values to create a slider on the front facing side of our WordPress site by reading and outputting the values from the database.

While the next post is in the making, please feel free to share your thoughts regarding this post or the entire series in general as to what we’ve done so far or where you’re having trouble, if any.

Leave a Reply

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

This site uses Akismet to reduce spam. Learn how your comment data is processed.