Шаблоны для таксономий пользовательских типов записей

13 сент. 2013 г., 08:06:22
Просмотры: 19.3K
Голосов: 2

Я создал пользовательский тип записи "Ad" (Реклама), затем добавил таксономию "type" (Тип) с терминами "Radio" (Радио), "TV" (ТВ), "Print" (Печать). Мне нужно, чтобы WordPress использовал разные шаблоны single.php для каждого термина - отдельный шаблон для Radio, отличающийся от Print.

Я пробовал создавать файлы taxonomy-ad-type-radio.php и single-ad-type-radio.php, а также другие варианты, но ничего не сработало. Каков лучший способ реализовать это?

Также я добавлял фильтры в файл functions.php, но безрезультатно. Наверняка я упускаю что-то простое. Буду благодарен за помощь.

<?php 

/** Регистрация типа записи для рекламы **/

add_action( 'init', 'register_cpt_ad' );

function register_cpt_ad() {

    $labels = array( 
        'name' => _x( 'Реклама', 'ad' ),
        'singular_name' => _x( 'Реклама', 'ad' ),
        'add_new' => _x( 'Добавить новую', 'ad' ),
        'add_new_item' => _x( 'Добавить новую рекламу', 'ad' ),
        'edit_item' => _x( 'Редактировать рекламу', 'ad' ),
        'new_item' => _x( 'Новая реклама', 'ad' ),
        'view_item' => _x( 'Просмотр рекламы', 'ad' ),
        'search_items' => _x( 'Поиск рекламы', 'ad' ),
        'not_found' => _x( 'Реклама не найдена', 'ad' ),
        'not_found_in_trash' => _x( 'Реклама не найдена в корзине', 'ad' ),
        'parent_item_colon' => _x( 'Родительская реклама:', 'ad' ),
        'menu_name' => _x( 'Реклама', 'ad' ),
    );

    $args = array( 
        'labels' => $labels,
        'hierarchical' => false,
        'description' => 'Система рекламных баннеров',
        'supports' => array( 'title', 'excerpt', 'editor', 'thumbnail', 'custom-fields' ),
        'taxonomies' => array( 'category', 'type', 'campaign', 'post_tag' ),
        'public' => true,
        'show_ui' => true,
        'show_in_menu' => true,     
        'show_in_nav_menus' => true,
        'publicly_queryable' => true,
        'exclude_from_search' => false,
        'has_archive' => true,
        'query_var' => true,
    'menu_position' => 3,
        'can_export' => true,
        'rewrite' => true,
        'capability_type' => 'post'
    );

    register_post_type( 'ad', $args );
}

/**Регистрация таксономии для типов рекламы**/
add_action( 'init', 'register_taxonomy_type' );

function register_taxonomy_type() {

    $labels = array( 
        'name' => _x( 'Тип рекламы', 'type' ),
        'singular_name' => _x( 'Типы рекламы', 'type' ),
        'search_items' => _x( 'Поиск по типу рекламы', 'type' ),
        'popular_items' => _x( 'Популярные типы рекламы', 'type' ),
        'all_items' => _x( 'Все типы рекламы', 'type' ),
        'parent_item' => _x( 'Родительские типы рекламы', 'type' ),
        'parent_item_colon' => _x( 'Родительские типы рекламы:', 'type' ),
        'edit_item' => _x( 'Редактировать тип рекламы', 'type' ),
        'update_item' => _x( 'Обновить тип рекламы', 'type' ),
        'add_new_item' => _x( 'Добавить новый тип рекламы', 'type' ),
        'new_item_name' => _x( 'Новый тип рекламы', 'type' ),
        'separate_items_with_commas' => _x( 'Разделяйте типы рекламы запятыми', 'type' ),
        'add_or_remove_items' => _x( 'Добавить или удалить тип рекламы', 'type' ),
        'choose_from_most_used' => _x( 'Выбрать из наиболее используемых типов рекламы', 'type' ),
        'menu_name' => _x( 'Тип рекламы', 'type' ),
    );

    $args = array( 
        'labels' => $labels,
        'public' => true,
        'show_in_nav_menus' => true,
        'show_ui' => true,
        'show_tagcloud' => true,
        'hierarchical' => true,
        'rewrite' => true,
        'query_var' => true
    );

    register_taxonomy( 'type', array('ad'), $args );
}

/**Регистрация таксономии для кампаний**/
add_action( 'init', 'register_taxonomy_campaign' );

function register_taxonomy_campaign() {

    $labels = array( 
        'name' => _x( 'Кампании', 'campaign' ),
        'singular_name' => _x( 'Кампания', 'campaign' ),
        'search_items' => _x( 'Поиск кампаний', 'campaign' ),
        'popular_items' => _x( 'Популярные кампании', 'campaign' ),
        'all_items' => _x( 'Все кампании', 'campaign' ),
        'parent_item' => _x( 'Родительская кампания', 'campaign' ),
        'parent_item_colon' => _x( 'Родительская кампания:', 'campaign' ),
        'edit_item' => _x( 'Редактировать кампанию', 'campaign' ),
        'update_item' => _x( 'Обновить кампанию', 'campaign' ),
        'add_new_item' => _x( 'Добавить новую кампанию', 'campaign' ),
        'new_item_name' => _x( 'Новая кампания', 'campaign' ),
        'separate_items_with_commas' => _x( 'Разделяйте кампании запятыми', 'campaign' ),
        'add_or_remove_items' => _x( 'Добавить или удалить кампании', 'campaign' ),
        'choose_from_most_used' => _x( 'Выбрать из наиболее используемых кампаний', 'campaign' ),
        'menu_name' => _x( 'Кампании', 'campaign' ),
    );

    $args = array( 
        'labels' => $labels,
        'public' => true,
        'show_in_nav_menus' => true,
        'show_ui' => true,
        'show_tagcloud' => true,
        'hierarchical' => true,
        'rewrite' => true,
        'query_var' => true
    );

    register_taxonomy( 'campaign', array('ad'), $args );
}

function query_post_type($query) {
    $post_types = get_post_types();

    if ( is_category() || is_tag()) {

        $post_type = get_query_var('ad');

        if ( $post_type ) {
            $post_type = $post_type;
        } else {
            $post_type = $post_types;
        }

        $query->set('post_type', $post_type);

        return $query;
    }
}

add_filter('pre_get_posts', 'query_post_type');

/* НОВЫЕ ФУНКЦИОНАЛЬНОСТИ */

// Добавление колонки
function price_column_register( $columns ) {
$columns['level'] = __( 'Уровень пользователя', 'my-plugin' );

return $columns;
}
add_filter( 'manage_edit-ad_columns', 'price_column_register' );

// Отображение содержимого колонки
function price_column_display( $column_name, $post_id ) {
if ( 'level' != $column_name )
    return;
$roles = get_post_meta( $post->ID, '_members_access_role', true );
if ($roles == 'level1') echo 'level1';
echo 'привет';
}
add_action( 'manage_posts_custom_column', 'price_column_display', 10, 2 );

/**
 * Добавление терминов нескольких таксономий к списку
 * классов, генерируемых post_class().
 *
 * @since 2010-07-10
 * @alter 2012-01-06
 */
function mysite_post_class( $classes, $class, $ID ) {

    $taxonomies = array(
        'type',
        'campaign',

    );

    $terms = get_the_terms( (int) $ID, $taxonomies );

    if ( is_wp_error( $terms ) || empty( $terms ) )
        return $classes;

    foreach ( (array) $terms as $term ) {
        if ( ! in_array( $term->slug, $classes ) )
            $classes[] = $term->slug;
    }

    return $classes;
}

add_filter( 'post_class', 'mysite_post_class', 10, 3 );
add_filter( 'tpicker_taxonomies', 'my_tpicker_taxonomies' );
function my_tpicker_taxonomies( $old_taxies) { // Фильтр порядка таксономий

    foreach( array("Категории", "Кампании", "Тип рекламы" ) as $tax_label) {
        $new_taxies[$tax_label] = $old_taxies[$tax_label];
    }

    return $new_taxies;
}
0
Все ответы на вопрос 1
10

Думаю, вы упускаете некоторые концепции или не до конца понимаете.

  1. Таксономия — это способ группировки сущностей, например, записей. Одна и та же таксономия может использоваться для нескольких типов записей, поэтому таксономия не принадлежит конкретной записи.
  2. Шаблоны single используются для отображения отдельной записи. Вы можете создавать разные шаблоны single для каждого типа записи и даже для каждой конкретной записи.
  3. Специфичный шаблон для элемента таксономии — это taxonomy-{ваша_таксономия}-{термин}.php, в вашем случае, например, taxonomy-type-radio.php. Этот шаблон будет отображать все записи, принадлежащие термину 'radio' таксономии 'type'.

Полагаю, что на самом деле вам нужно использовать разные шаблоны single в зависимости от термина таксономии "type", связанного с записью типа 'Ad'. Предполагаю, что для каждой записи может быть выбран только один термин таксономии 'type'. Вы можете использовать фильтр template_include или, более конкретно, фильтр single_template:

<?php
function get_custom_single_template($single_template) {
    global $post;

    if ($post->post_type == 'ad') {
        $terms = get_the_terms($post->ID, 'type');
        if($terms && !is_wp_error( $terms )) {
            //Цикл foreach, потому что $terms — это массив, но предполагается только один термин
            foreach($terms as $term){
                $single_template = dirname( __FILE__ ) . '/single-'.$term->slug.'.php';
            }
        }
     }
     return $single_template;
}

add_filter( "single_template", "get_custom_single_template" ) ;
?>

Поместите этот код в файл functions.php вашей темы. Не забудьте создать файлы single-*.php для каждого термина (single-radio.php, single-tv.php и т.д.).

Если вам не нужен отдельный файл шаблона, а требуются лишь небольшие изменения, например, разные CSS-классы, вы можете проверить, имеет ли запись указанный термин, и назначить другой класс. Например, в общем шаблоне single:

 <div class="<?php echo class="<?php echo has_term( 'radio', 'type' ) ? 'radio' : ''; ?>">
   <?php the_cotent();?>
</div>

Или

<?php
$terms = get_the_terms($post->ID, 'type');
$class = '';
//Цикл foreach, потому что $terms — это массив, но предполагается только один термин
foreach($terms as $term){
    $class = $term->slug;
}
?>
<div class="<?php echo $class; ?>">
   <?php the_cotent();?>
</div>
13 сент. 2013 г. 08:39:58
Комментарии

Да! Я хочу, чтобы для каждого "типа" был свой шаблон. То есть, если запись относится к категории radio, то должен использоваться шаблон single radio. Простите за незнание, но куда вставить ваш код? В файл functions?

Ben Ben
13 сент. 2013 г. 09:20:01

Да, в файл functions.php. Также вам нужно создать single-radio.php, single-tv.php и так далее... в папке вашей темы.

cybmeta cybmeta
13 сент. 2013 г. 13:01:47

Я так и подумал, и сделал всё это, но почему-то используется только single-ad.php, он отказывается смотреть на другие single-шаблоны. Даже если я удалю single-ad.php, он не переключится на другие файлы. Возможно, разработчик темы где-то прописал использование только этого файла. Но я не могу найти это место ;-(

Ben Ben
13 сент. 2013 г. 17:04:11

Чтобы помочь вам дальше, мне нужно увидеть код, который вы используете для регистрации пользовательского типа записи и пользовательской таксономии. Можете ли вы отредактировать свой вопрос и добавить код?

cybmeta cybmeta
13 сент. 2013 г. 18:13:41

Не могли бы вы также попробовать снова код из моего ответа? Я его отредактировал.

cybmeta cybmeta
13 сент. 2013 г. 18:22:50

Я только что добавил весь код, но из-за фигурных скобок {} он сломался в странных местах. Надеюсь, вы сможете его прочитать нормально. Прочитайте все как один длинный functions.php. Огромное спасибо... если вы сможете разобраться в этом, вы станете моим героем!!

Ben Ben
13 сент. 2013 г. 19:13:41

Вы снова пробовали код из моего ответа? Я его отредактировал и просил вас попробовать снова, но вы не сказали, пробовали или нет.

cybmeta cybmeta
13 сент. 2013 г. 19:50:55

По какой-то причине этот код просто выдает мне пустую белую страницу без какого-либо содержимого. Он ломает все одиночные записи, не только радио.

Ben Ben
14 сент. 2013 г. 00:07:36

Извините, у меня была опечатка. Попробуйте снова, я протестировал и у меня это работает.

cybmeta cybmeta
14 сент. 2013 г. 00:19:16

Ян, ты мой новый лучший друг!!! Теперь всё работает отлично!!

Ben Ben
14 сент. 2013 г. 02:25:41
Показать остальные 5 комментариев