WordPress. Создание виджета

30.03.2019

Теги: CMSWeb-разработкаWordPressВиджетКласс

Чтобы создать виджет, для начала нужно подключить хотя бы один сайдбар. После этого в панели управления «Внешний вид • Виджеты» можно будет добавлять виджеты в сайдбары. Когда виджет будет добавлен, станут доступны его настройки. Для удаления виджета из сайдбара предназначена ссылка «Удалить». Если нужно лишь временно отключить виджет, сохранив его настройки, нужно его перетащить в область «Неактивные виджеты».

Создание собственного виджета

Давайте создадим виджет популярных постов — который будет выводить записи через WP_Query, отсортированные по количеству комментариев. По своей структуре он будет похож на стандартный виджет WordPress «Свежие записи», т.е. он будет иметь похожие параметры (заголовок и количество постов) и похожий HTML-шаблон для вывода постов.

Для виджетов существует специальный класс WP_Widget, использование которого позволит нам создать новый виджет. Класс содержит около двадцати методов, однако нам потребуются лишь четыре из них:

  • __construct() — регистрация базовой информации о виджете;
  • widget() — вывод виджета внутри сайдбара публичной части сайта;
  • form() — параметры виджета, отображаемые в панели управления;
  • update() — обновление настроек виджета в панели управления.
<?php
/**
 * Класс виджета, который позволяет вывести записи,
 * отсортированные по количеству комментариев
 */
class Popular_Posts_Widget extends WP_Widget {

    /**
     * Cоздание виджета
     */
    function __construct() {
        parent::__construct(
            'popular_posts_widget',
            'Популярные посты', // заголовок виджета
            ['description' => 'Записи, отсортированные по количеству комментариев'] // описание
        );
    }

    /**
     * Метод выводит популярные записи в общедоступной части сайта
     */
    public function widget($args, $instance) {

        // к заголовку применяем фильтр
        $title = apply_filters('widget_title', $instance['title']);
        // количество записей из настроек
        $posts_per_page = $instance['posts_per_page'];

        echo $args['before_widget'];

        // выводим заголовок виджета
        if ( ! empty($title)) {
            echo $args['before_title'] . $title . $args['after_title'];
        }

        // выводим популярные записи
        $query = new WP_Query([
            'posts_per_page' => $posts_per_page,
            'orderby' => 'comment_count',
            'order' => 'DESC'
        ]);
        if ($query->have_posts()) {
            ?>
            <ul>
            <?php
            while ($query->have_posts()) {
                $query->the_post();
                $link = get_permalink();
                $title = get_the_title();
                $comments = get_comments_number();
                ?>
                <li><a href="<?= $link; ?>"><?= $title; ?></a> (<?= $comments; ?>)</li>
                <?php
            }
            ?>
            </ul>
            <?php
        }
        wp_reset_postdata();

        echo $args['after_widget'];
    }

    /*
     * Форма настроек виджета в панели управления
     */
    public function form($instance) {

        $title = '';
        if (isset($instance['title'])) {
            $title = $instance['title'];
        }
        $posts_per_page = 5;
        if (isset($instance['posts_per_page'])) {
            $posts_per_page = $instance['posts_per_page'];
        }
        ?>

        <p>
        <label for="<?= $this->get_field_id('title'); ?>">Заголовок</label>
        <input type="text" class="widefat"
               id="<?= $this->get_field_id('title'); ?>"
               name="<?= $this->get_field_name('title'); ?>'"
               value="<?= esc_attr($title); ?>" />
        </p>

        <p>
        <label for="<?= $this->get_field_id('title'); ?>">Количество</label>
        <input type="text"
               id="<?= $this->get_field_id('posts_per_page'); ?>"
               name="<?= $this->get_field_name('posts_per_page'); ?>"
               value="<?= esc_attr($posts_per_page); ?>" />
        </p>
        <?php
    }

    /*
     * Сохранение настроек виджета в панели управления
     */
    public function update($new_instance, $old_instance) {
        $instance = array();
        $instance['title'] =
            ! empty($new_instance['title']) ? strip_tags($new_instance['title']) : '';
        $instance['posts_per_page'] =
            ctype_digit($new_instance['posts_per_page']) ? $new_instance['posts_per_page'] : 5;
        if ($instance['posts_per_page'] > 30 || $instance['posts_per_page'] < 1) {
            $instance['posts_per_page'] = 5;
        }
        return $instance;
    }
}

Теперь осталось только подключить файл с классом виджета в functions.php:

require_once __DIR__ . '/Popular_Posts_Widget.php';

И зарегистрировать виджет, чтобы он появился на странице «Внешний вид • Виджеты»:

/*
 * Регистрируем виджет «Популярные записи блога»
 */
add_action(
    'widgets_init',
    function () {
        register_widget('Popular_Posts_Widget');
    }
);

Как вывести сайдбар в шаблоне

Для этого предназначены функции is_active_sidebar() и dynamic_sidebar():

  • функция is_active_sidebar() — проверяет, есть ли в сайдбаре виджеты;
  • функция dynamic_sidebar() — собственно, выводит сайдбар.

Выводим сайдбар в правой колонке:

<aside class="col-md-3">
    <?php if (is_active_sidebar('sidebar_right')): ?>
        <div id="sidebar_right" class="sidebar">
            <?php dynamic_sidebar('sidebar_right'); ?>
        </div>
    <?php endif; ?>
</aside>

Отключение стандартных виджетов

Если не планируется использовать какой-либо из стандартных виджетов, можно его полностью отключить его при помощи функции unregister_widget(), после чего виджет перестанет отображаться в админке на странице «Внешний вид • Виджеты».

add_action(
    'widgets_init',
    function() {
        unregister_widget('WP_Widget_Archives'); // архивы
        unregister_widget('WP_Widget_Calendar'); // календарь
        unregister_widget('WP_Widget_Categories'); // рубрики
        unregister_widget('WP_Widget_Meta'); // мета
        unregister_widget('WP_Widget_Pages'); // страницы
        unregister_widget('WP_Widget_Recent_Comments'); // свежие комментарии
        unregister_widget('WP_Widget_Recent_Posts'); // свежие записи
        unregister_widget('WP_Widget_RSS'); // RSS
        unregister_widget('WP_Widget_Search'); // поиск
        unregister_widget('WP_Widget_Tag_Cloud'); // облако меток
        unregister_widget('WP_Widget_Text'); // текст
        unregister_widget('WP_Nav_Menu_Widget'); // произвольное меню
    },
    20
);

Эта функция позволяет удалять не только стандартные виджеты. В качестве параметра функции можно указать название класса любого виджета.

Поиск: CMS • PHP • Web-разработка • WordPress • Класс • Widget • Виджет • widgets_init • register_widget • unregister_widget • WP_Widget • WP_Query

Каталог оборудования
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
Производители
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
Функциональные группы
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.