Using WordPress Plugin Boilerplate

Chris Wilcoxson

WordCamp Dayton 2015

slushman

DCC Marketing

Decatur, IL

dccmarketing.com

Let's Jump In!

 

 

 

 

 

 

WordPress Plugin Boilerplate

Tom McFarlin

Devin Vinson

Why Use It?

Keeps files organized

WordPress Coding Standards

WordPress Documentation Standards

WordPress APIs

Translatable

What's New?

Completely rewritten

No more singleton

New Structure

http://wppb.io

Structure

Admin & Public

Includes

Use a Generator

http://wppb.me

plugin-name.php

/**
 * @link              http://example.com
 * @since             1.0.0
 * @package           Plugin_Name
 *
 * @wordpress-plugin
 * Plugin Name:       WordPress Plugin Boilerplate
 * Plugin URI:        http://example.com/plugin-name-uri/
 * Description:       This is a short description of what the plugin does.
 * Version:           1.0.0
 * Author:            Your Name or Your Company
 * Author URI:        http://example.com/
 * License:           GPL-2.0+
 * License URI:       http://www.gnu.org/licenses/gpl-2.0.txt
 * Text Domain:       plugin-name
 * Domain Path:       /languages
 */
See Full Code

plugin-name.php

if ( ! defined( 'WPINC' ) ) { die; }

function activate_plugin_name() {
    require_once plugin_dir_path( __FILE__ ) . 'includes/class-plugin-name-activator.php';
    Plugin_Name_Activator::activate();
}

function deactivate_plugin_name() {
    require_once plugin_dir_path( __FILE__ ) . 'includes/class-plugin-name-deactivator.php';
    Plugin_Name_Deactivator::deactivate();
}

register_activation_hook( __FILE__, 'activate_plugin_name' );
register_deactivation_hook( __FILE__, 'deactivate_plugin_name' );
See Full Code

plugin-name.php

require plugin_dir_path( __FILE__ ) . 'includes/class-plugin-name.php';

function run_plugin_name() {

    $plugin = new Plugin_Name();
    $plugin->run();

}
run_plugin_name();
See Full Code

Plugin Class

Plugin Class

Constructor

public function __construct() {

    $this->plugin_name = 'plugin-name';
    $this->version = '1.0.0';

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

}
See Full Code

Plugin Class

Load Dependencies

private function load_dependencies() {

    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-plugin-name-loader.php';
    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-plugin-name-i18n.php';
    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'admin/class-plugin-name-admin.php';
    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'public/class-plugin-name-public.php';

    $this->loader = new Plugin_Name_Loader();

}
See Full Code

Plugin Class

i18n

private function set_locale() {

    $plugin_i18n = new Plugin_Name_i18n();
    $plugin_i18n->set_domain( $this->get_plugin_name() );

    $this->loader->add_action( 'plugins_loaded', $plugin_i18n, 'load_plugin_textdomain' );

}
See Full Code

Plugin Class

Hooks

private function define_admin_hooks() {

    $plugin_admin = new Plugin_Name_Admin(
        $this->get_plugin_name(), $this->get_version() );

    $this->loader->add_action(
        'admin_enqueue_scripts', $plugin_admin, 'enqueue_styles'
    );

    $this->loader->add_action(
        'admin_enqueue_scripts', $plugin_admin, 'enqueue_scripts'
    );

}
See Full Code

Loader Class

Constructor

public function __construct() {

    $this->actions = array();
    $this->filters = array();

}
See Full Code

Loader Class

Add Action

public function add_action(
    $hook, $component, $callback, $priority = 10, $accepted_args = 1 ) {

    $this->actions = $this->add(
        $this->actions,
        $hook,
        $component,
        $callback,
        $priority,
        $accepted_args
    );

}
See Full Code

Loader Class

Run Method

public function run() {

    foreach ( $this->actions as $hook ) {
        add_action(
            $hook['hook'],
            array( $hook['component'], $hook['callback'] ),
            $hook['priority'],
            $hook['accepted_args']
        );
    }
}
See Full Code

Admin & Public Classes

Constructor

public function __construct( $plugin_name, $version ) {

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

}
See Full Code - Admin See Full Code - Public

Admin & Public Classes

Enqueue Styles

public function enqueue_styles() {

    wp_enqueue_style(
        $this->plugin_name,
        plugin_dir_url( __FILE__ ) . 'css/plugin-name-admin.css',
        array(),
        $this->version,
        'all'
    );

}
See Full Code - Admin See Full Code - Public

Admin & Public Classes

Enqueue Scripts

public function enqueue_scripts() {

    wp_enqueue_script(
        $this->plugin_name,
        plugin_dir_url( __FILE__ ) . 'js/plugin-name-admin.js',
        array( 'jquery' ),
        $this->version,
        false
    );

}
See Full Code - Admin See Full Code - Public

Other Files

  • index.php files
  • Languages Folder & blank .pot file
  • license.txt
  • README.txt
  • uninstall.php

Examples

Enqueue styles and scripts

Custom Post Type

Taxonomy

Plugin Settings

Metaboxes

Shortcode

Displays/Views

Widgets

Custom Post Type

Plugin Class

private function define_admin_hooks() {

    $plugin_admin = new Now_Hiring_Admin(
        $this->get_i18n(),
        $this->get_version()
    );

    $this->loader->add_action( 'init', $plugin_admin, 'new_cpt_jobs' );

}
See Full Code

Custom Post Type

Admin Class

public function new_cpt_jobs() {

    $cap_type 	= 'post';
    $plural 	= 'Jobs';
    $single 	= 'Job';

    $opts['show_ui'] = TRUE;
    $opts['supports'] = array( 'title', 'editor', 'thumbnail' );
    $opts['capabilities']['edit_post'] = "edit_{$cap_type}";
    $opts['labels']['add_new'] =
        __( "Add New {$single}", $this->i18n );

    ...

    register_post_type( strtolower( $plural ), $opts );

}
See Full Code

Taxonomy

Plugin Class

private function define_admin_hooks() {

    $plugin_admin = new Now_Hiring_Admin(
        $this->get_i18n(),
        $this->get_version() );

    $this->loader->add_action( 'init', $plugin_admin, 'new_tax_type' );

}
See Full Code

Taxonomy

Admin Class

public function new_taxonomy_type() {

    $plural 	= 'Types';
    $single 	= 'Type';
    $tax_name 	= 'job_type';

    $opts['query_var'] = $tax_name;
    $opts['capabilities']['assign_terms'] = 'edit_posts';
    $opts['labels']['add_new_item'] =
        __( "Add New {$single}", $this->i18n );

    ...

    register_taxonomy( $tax_name, 'jobs', $opts );

}
See Full Code

Plugin Settings

Plugin Class

private function define_admin_hooks() {

    $plugin_admin = new Now_Hiring_Admin(
        $this->get_i18n(),
        $this->get_version()
    );

    $this->loader->add_action( 'admin_menu', $plugin_admin, 'add_menu' );
    $this->loader->add_action( 'admin_init', $plugin_admin, 'register_settings' );

}
See Full Code

Plugin Settings

Admin Class - Register Settings

public function register_settings() {

    register_setting( 'now_hiring_options', 'now_hiring_options',
        array( $this, 'validate_options' ) );

    add_settings_section( 'now_hiring_display_options',
        'Display Options',
        array( $this, 'display_options_section' ), 'now-hiring' );

    add_settings_field( 'display_salary', 'Display Salary',
        array( $this, 'display_options_field' ),
        'now-hiring', 'now_hiring_display_options' );

}
See Full Code

Plugin Settings

Admin Class - Options Page

public function options_page() {

    echo '

Now Hiring Settings

'; echo '
'; settings_fields( 'now_hiring_options' ); do_settings_sections( 'now-hiring' ); submit_button( 'Save Settings' ); echo '
'; }
See Full Code

Plugin Settings

Admin Class - Add Menu

public function add_menu() {

    add_options_page(
        __( 'Now Hiring Settings', $this->i18n ),
        __( 'Now Hiring', $this->i18n ),
        'manage_options',
        'now-hiring',
        array( $this, 'options_page' )
    );

}
See Full Code

Plugin Settings

Admin Class - Display Section

public function display_options_section( $params ) {

    echo '

' . $params['title'] . '

'; }
See Full Code

Plugin Settings

Admin Class - Display Field

public function display_options_field() {

    $options = get_option( 'now_hiring_options' );

    ?><input type="checkbox" id="now_hiring_options[display_salary]" name="now_hiring_options[display_salary]" value="1" <?php checked( 1, $options['display_salary'], false ); ?> /><?php

}
See Full Code

Plugin Settings

Admin Class - Validate Options

public function validate_options( $input ) {

    $display_salary = trim( $input['display_salary'] );
    $valid['display_salary'] = isset( $display_salary ) ? 1 : 0;

    if ( $valid['display_salary'] != $input['display_salary'] ) {
        add_settings_error(
            'display_salary',
            'display_salary_error',
            'Display salary error.',
            'error'
        );
    }

    return $valid;

} // validate_options()
See Full Code

Metaboxes

Plugin Class

private function define_admin_hooks() {

    $plugin_admin = new Now_Hiring_Admin( $this->get_i18n(), $this->get_version() );

    $this->loader->add_action( 'add_meta_boxes', $plugin_admin, 'add_metaboxes' );

    $this->loader->add_action( 'save_post_jobs', $plugin_admin, 'save_meta', 10, 2 );

}
See Full Code

Metaboxes

Admin Class - Add Metaboxes

public function add_metaboxes() {

    add_meta_box(
        'now_hiring_job_location',
        __( 'Job Location', $this->i18n ),
        array( $this, 'callback_metabox_job_location' ),
        'jobs',
        'normal',
        'default'
    );

}
See Full Code

Metaboxes

Admin Class - Metabox Method

public function callback_metabox_job_location( $object, $box ) {

    include( plugin_dir_path( __FILE__ ) . 'partials/now-hiring-admin-display-metabox-job-location.php' );

}
See Full Code

Metaboxes

Admin Class - Save Meta

public function save_meta( $post_id, $object ) {

    // check for autosave, post type, capability, & set nonce

    if ( ! wp_verify_nonce( $_POST['job_location_nonce'], NOW_HIRING_BASENAME ) ) { return $post_id; }

    $custom = get_post_custom( $post_id );
    $metas = array( 'job-location' );

    foreach ( $metas as $meta ) {

        // sanitize data
        // update meta

    }

}
See Full Code

Shortcode

Plugin Class

private function define_public_hooks() {

    $plugin_public = new Now_Hiring_Public(
        $this->get_i18n(),
        $this->get_version()
    );

    $this->loader->add_action(
        'init',
        $plugin_public,
        'register_shortcodes'
    );

}
See Full Code

Shortcode

Public Class - Register Shortcodes

public function register_shortcodes() {

    add_shortcode( 'nowhiring', array( $this, 'shortcode' ) );

}
See Full Code

Shortcode

Public Class - Shortcode Method

public function shortcode( $atts ) {

    ob_start();

    $defaults['order'] = 'date';
    $defaults['quantity'] = -1;
    $args = shortcode_atts( $defaults, $atts, 'nowhiring' );
    $items = $this->get_job_posts( $args );

    ...

    $output = ob_get_contents();

    ob_end_clean();

    return $output;

}
See Full Code

Displays, Partials, Views, Oh My!

Shortcode Method

if ( is_array( $items ) || is_object( $items ) ) {

    include( plugin_dir_path( __FILE__ ) . 'partials/now-hiring-public-display.php' );

}
See Full Code

Displays, Partials, Views, Oh My!

Public Class - Display Loop

foreach ( $items->posts as $item ) {

    include( plugin_dir_path( __FILE__ ) . 'now-hiring-public-display-single.php' );

}
See Full Code

Displays, Partials, Views, Oh My!

Public Class - Display Loop

foreach ( $items->posts as $item ) {

    include( plugin_dir_path( __FILE__ ) . 'now-hiring-public-display-single-' .    esc_attr( $options['layout'] ) . '.php' );

}
See Full Code

Displays, Partials, Views, Oh My!

Public Class - Display Single

?><div class="job-wrap">
    <h1 class="job-title"><a href="<?php echo get_permalink( $item->ID ); ?>"><?php echo esc_attr( $item->post_title ); ?></a></h1>
    <div class="job-content"><?php echo $item->post_content; ?></h1>
</div>
See Full Code

Widgets

Where?

Plugin Class

Load Dependencies

private function load_dependencies() {

    ...
    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-now-hiring-widget.php';

}
See Full Code

Init Widgets

public function widgets_init() {

    register_widget( 'now_hiring_widget' );

}
See Full Code

Flush Widget Cache

public function flush_widget_cache( $post_id ) {

    if ( wp_is_post_revision( $post_id ) ) { return; }

    $post = get_post( $post_id );

    if ( $post->post_type == 'jobs' ) {

        wp_cache_delete( $this->i18n, 'widget' );

    }

}
See Full Code

Method One

Plugin Class

Constructor

public function __construct( $plugin_name, $version ) {

    ...
    $this->define_widget_hooks();

}
See Full Code

Plugin Class

Define Widget Hooks

private function define_widget_hooks() {

    $this->loader->add_action( 'widgets_init', $this, 'widgets_init' );
    $this->loader->add_action( 'save_post_jobs', $this, 'flush_widget_cache' );
    $this->loader->add_action( 'deleted_post', $this, 'flush_widget_cache' );
    $this->loader->add_action( 'switch_theme', $this, 'flush_widget_cache' );

}
See Full Code

Method Two

Shared Class

Constructor

public function __construct( $plugin_name, $version ) {

    ...
    $this->define_shared_hooks();

}
See Full Code

Shared Class

Load Dependencies

private function load_dependencies() {

    ...
    require_once plugin_dir_path( dirname( __FILE__ ) ) . 'includes/class-now-hiring-shared.php';

}
See Full Code

Shared Class

Define Widget Hooks

private function define_shared_hooks() {

    $plugin_shared = new Now_Hiring_Shared( $this->get_i18n(), $this->get_version() );

    $this->loader->add_action( 'widgets_init', $plugin_shared, 'widgets_init' );
    $this->loader->add_action( 'save_post_jobs', $plugin_shared, 'flush_widget_cache' );
    $this->loader->add_action( 'deleted_post', $plugin_shared, 'flush_widget_cache' );
    $this->loader->add_action( 'switch_theme', $plugin_shared, 'flush_widget_cache' );

}
See Full Code

Review

Questions?