Не так давно один из моих клиентов заказал такое задание: клиенту требовалось добавить в архивы категорий и в отдельную запись блоки навигации по меткам (тегам). Ничего сложного в этом как бы нет, однако, заказчику требовалось организовать вывод меток таким образом, чтобы в архивах конкретных рубрик выводились только соответствующие текущей рубрике метки! т.е чтобы «облако меток» выводилось не всё скопом, а только те метки, которые принадлежат конкретной категории. Такой же принцип вывода и для отдельной записи, чтобы метки выводились только из той категории, к которой относится запись…
Просил подобную фичу организовать без плагина.
Как известно, в стандартном виджете WordPress «Облако меток» возможности вывода меток для отдельной категории нет.
Короче, решение было найдено — им и делюсь с читателями:
своё облако меток для каждой отдельной категории записей
Вот, например, у меня на тестовом сайте получилось так (скриншот ниже): в разделе сайта (в категории/рубрике) «Шаблоны — описания» выведены метки, принадлежащие записям только этой категории. Т.е. все имеющиеся на сайте теги — всё их общее количество выводиться не будут — а будут отображены только те метки (теги) которые относятся к данной конкретной категории — в любой другой рубрике, будут выводиться только соответствующие ЕЙ метки!
Как и говорил выше, точно таким же образом возможно и в отдельной статье показывать только соответствующие категории статьи метки.
В принципе — это удобно для требовательного администратора.
Что нам и требовалось.
к оглавлению
функция — код вывода меток для определённой категории
Для начала, требуется добавить в файл functions.php активного шаблона код показанный ниже (либо организуем — создадим свой плагин):
/* Выводим теги для конкретной рубрики/записи */
function get_category_tags($cats) {
// формируем запрос к базе данных
global $wpdb;
$tags = $wpdb->get_results
("
SELECT DISTINCT terms2.term_id as tag_id, terms2.name as
tag_name, t2.count as posts_count, null as tag_link
FROM
wp_posts as p1
LEFT JOIN wp_term_relationships as r1 ON
p1.ID = r1.object_ID
LEFT JOIN wp_term_taxonomy as t1 ON
r1.term_taxonomy_id = t1.term_taxonomy_id
LEFT JOIN wp_terms as terms1 ON
t1.term_id = terms1.term_id,
wp_posts as p2
LEFT JOIN wp_term_relationships as r2 ON
p2.ID = r2.object_ID
LEFT JOIN wp_term_taxonomy as t2 ON
r2.term_taxonomy_id = t2.term_taxonomy_id
LEFT JOIN wp_terms as terms2 ON
t2.term_id = terms2.term_id
WHERE
t1.taxonomy = 'category' AND
p1.post_status = 'publish' AND
terms1.term_id IN (". $cats .") AND
t2.taxonomy = 'post_tag' AND
p2.post_status = 'publish'
AND p1.ID = p2.ID
ORDER by tag_name
");
$min_size = 13; // Минимальный размер шрифта тегов
$i = 0;
/* Перебираем результаты запроса к БД в массив *
* $keys сохраняем количество статей данной рубрики, помеченных каждым из тегов
*/
foreach( $tags as $tag ) {
$keys[$i] = $tag->posts_count; // количество статей
//$i += 1; // изменение размера в зависимости от кол записей
}
/*
* Сортируем элементы массива по возрастанию. В конце самые популярные теги
*/
if ( $keys ) {
sort( $keys );
/* Перебираем все теги, используя отсортированный массив, $keys - ключи. Добьёмся при смене количества статей,
* в массиве $sizes СНОВА изменение (перезаписанного) размера шрифта. Чем больше статей - тем крупнее ШРИФТ. Шаг увеличения шрифта = 1px
*/
$i = 0;
foreach ( $keys as $key ) {
if ($i==0) { $curr_size = $min_size; $prev_key = $key; }
if ( $prev_key > $key) { $curr_size += 1; }
$sizes[$i] = $curr_size;
$prev_key = $key;
// $i += 1; // закомментить, если нужно чтоб величина тега равнялась кол. записей
}
/* Подготовка выборки окончена, теперь формируем список тегов: чем больше статей
* помеченных тем или иным тегом, тем он выводится крупнее, сортируем теги
* по алфавиту
*/
foreach($tags as $tag) {
$i = 0;
foreach ( $keys as $key ) {
if ( $tag->posts_count == $key ) {
$stil = 'style="font-size: ' . $sizes[$i] . 'px;"';
}
// $i += 1; // исключим повтор ссылки (например, статьи) - закомментировать!
}
//echo "<div class='tag-link-styles22'>"; // дополнительные стили
$out .= '<span class="tag-link-styles"><a href="'. get_tag_link($tag->tag_id) .'" // если ДИВ о будет в столбик вывод
class="tag-link-'.$tag->tag_id.'" ' .
$stil . '>'. $tag->tag_name .' </a></span>'; // разделитель - ( отделить знак запись ,) показать количество записей ('. $tag->posts_count .')
//echo "</div>"; // дополнительные стили
}
}
return rtrim($out, ', ');
}
/* Выводим теги для конкретной рубрики/записи */
Код я немного подработал и дополнил понятности ради комментариями…
1 — например, возможно сделать так, чтобы в скобках после каждого имени метки отображалось количество записей…
В финальной части кода — там, где формируется ссылка меток — можно добавить ('. $tag->posts_count .')
— в этом случае будет показано (в скобках) количество записей…
2 — …чтобы в зависимости от количества записей в разделе МЕТКИ, шрифт тега увеличивался/уменьшался… Отработка данных переменной $i += 1;
— в коде комментарии.
Код возможно сократить… однако, я его сильно кастрировать не стал, потому как у всех у нас разные потребности… Пусть каждый решает сам, что ему требуется, а что нет…
к оглавлению
выводим метки только конкретной категории
Для того, чтобы вывести на сайте (фронтенд) СВОИ метки для каждой конкретной рубрики сайта, всего-то потребуется запросить в файлах (либо в сайдбаре) отработку функции данной выше.
Как это делается?
В то место, в котором требуется вывести, скажем так, облако меток — навигацию по тегам, следует прописать код вызова, показанный ниже:
Код прописывать в сайдбар (виджет), либо напрямую в соответствующий файл активного шаблона.
<?php
// Выводим теги конкретного раздела (рубрики), если они есть
$cat = get_the_category();
$tags = get_category_tags( $cat[0]->cat_ID );
if ( $tags != '' )
echo '' . $tags . '';
?>
Для того, чтобы вывести метки по конкретной категории (записи), к примеру, в сайдбаре, потребуется воспользоваться выджетом, который умеет работать с PHP кодом (стандартные виджеты WP такой возможности не имеют) — а посему смею предложить свой плагин Плагин widget text class ats — текстовый виджет для работы с php и шорткодами — скачивать или прямо у меня на сайте, либо — стандартно — через админку своего сайта установка плагинов «Добавить новый».
Плагин очень простой — никаких настроек — после установки и активации, в админке, в разделе «Виджеты», появится новый виджет, который умеет работать с PHP и шорткодами..
Что ещё… …если нам требуется дать имя блоку меток по рубрикам, то возможно при помощи оператора echo
— в коде вызова функции (данном чуть выше) организовать примерно такую строку:
как видите, пример — имя раздела «Теги».
echo '<div class="tagCloud"><h3>Теги</h3></div>';
Возможно, будет кому-то полезна статья о том, как закрыть метки (теги) от роботов — либо nofollow либо AJAX.
Либо же — к вашим услугам плагин «Закрытых меток» по метОде AJAX…
Тем, которые не знают:
вывод блоков меток для конкретной рубрики возможно организовать и ещё более тонко (или в сайдбаре/виджете, либо в коде) — например, запретить вывод блока меток на главной странице, в конкретном архиве рубрик/меток и пр. или статье, а в каких-то иных архивах напротив — разрешить…
Если изучите статью Условные теги WordPress — полная подборка, пояснения то у вас всё получится так, как требуется для вашего бизнеса.
к оглавлению
css для вывода меток привязанных к конкретной категории
Вот примерный CSS код для описанного в статье вывода блока меток для отдельных рубрик: код дан для примера, так что можете его смело редактировать в соответствии со стилистикой своего сайта.
.tag-link-styles a{background-color:#e9f6fc;text-decoration:none;padding:2px 2px 2px 7px;border:1px solid #CFCECE;border-radius:6px;line-height:1.8;margin-right:3px;color:#007205;
}
.tag-link-styles a:hover{color:#a43900;}
.tag-link-{display:none;}
вариант 2:
к оглавлению
выводим метки только для конкретной рубрики
Код, показанный ниже, призван выводить метки только для текущей рубрики (раздела сайта). Таким образом функция отработает для каждой категории свои собственные метки (теги)!
Помещать в файл функций functions.php
активного шаблона и выводить в том месте, где следует… В сайдбаре или в файлах шаблона.
Внимание! в записях — код правильно работать не будет — в записях метки будут отображены все, которые имеются на сайте. Поэтому, если нужно чтобы в записях были показаны метки текущей категории, к которой относится запись, используйте код выше — ПЕРВЫЙ вариант!
/* Выводим теги ТОЛЬКО для конкретной рубрики (только в архивах) */
function get_tags_in_cat($cat_id){
$posts = get_posts( array('category' => $cat_id, 'numberposts' => -1) );//
$tags = array();
foreach($posts as $post)
{
$post_tags = get_the_tags($post->ID);
if( !empty($post_tags) )
foreach($post_tags as $tag)
$tags[$tag->term_id] = $tag->name;
}
asort($tags);
return $tags;
}
/* Выводим теги ТОЛЬКО для конкретной рубрики (только в архивах) */
…далее… вызываем функцию там, где требуется кодом, показанным ниже: (со ссылкой возможно работать по своим усмотрениям — закрыть ссылки в либо nofollow
либо AJAX — как это делается, ссылки ВЫШЕ)
<?php
$cat_id = get_query_var('cat'); // получим ID-дентификатор текущей категории
$tags = get_tags_in_cat($cat_id);
foreach($tags as $tag_id => $tag_name)
$tags_print[] = '<span class="tag-link-styles"><a title="' .$tag_name. '" href="' .get_tag_link($tag_id). '">' .$tag_name. '</a></span>';
echo implode(' ', $tags_print); // разделитель: ', ' если требуется (запятая)
?>
Код CSS использован что и для первого кода: span class="tag-link-styles"
Вот в принципе и всё, что хотелось сегодня рассказать…
Если что-то не ясно…
mihalica.ru !
Код отлично работает, спасибо!
Хотелось бы немного разгрузить сайт, ограничившись выводом облаков тэгов только в архивах категорий, не выводя их в постах. Не подскажете — что для этого нужно изменить в выводе?
Привет!
Это вам, насколько я понял из вопроса, нужно как-то использовать условные теги WP и все получится.
Спасибо! Благодаря вам, впервые воспользовался кондишенами и всё получилось. Облако теперь не перегружает своим присутствием посты, но отображается там, где ему место — в архивах.
Возник ещё один вопрос, если позволите. Подскажите пожалуйста конструкцию для отображения виджетов только в том случае, если они содержат данные. То есть, если им есть что показать. А то бывает, что заголовок висит на фронтэнде и скучает в одиночестве. С php-виджетом я это решил теми же условными операторами, отказавшись от заголовка виджета и добавив операторы присутствия/отсутствия заголовка в php-коде. А вот то, как глобально решить проблему — докопаться сам не смог.
На здоровье)
В вашей задаче, насколько я понял, нужно определиться — как убирать (скажем так) виджет — php либо display: none …
А вообще, как вы говорите — глобально, решать целесообразно кастомно, перестраивая ядро шаблона по выводу виджетов (некоторые юзают и полный сайдбар) — в том или ином месте… В этом случае решается и задача легкости кода (скорости загрузки стр.).
Задача решаема. Главное определиться с целями и более логичным индивидуальным решением. ЛИБО по ID-виджета скрываете виджет полностью!..
Это, если вас правильно понял…
Да, нужно скрывать виджет. Но по условию: тогда, когда ему нечего выводить. Учитывая же то, что заголовок виджета будет виден постоянно, есть вывод данных или их нет, заголовок будет висеть в одиночестве. Если делать в CSS через «display:none», то виджет закроется навсегда — даже если наворотить логики: CSS не понимает — есть данные виджета или нет. А вот php другое дело. Поэтому подошла бы конструкция, проверяющая наличие у виджета данных для вывода или их отсутствие. Таким образом, при отсутствии данных, виджет просто не выводился бы. Я перерыл массу плагинов для виджета, но они в основном предлагают стилизацию, но не выключение виджета по условиям.
Я вам уже описал в предыдущем комменте… вы, вероятно, не поняли. Либо я не ясно пояснил)
Так же и мне не ясно, чтобы помочь, — как это у вас остается Title виджета, если его вывод запрещен условием.?. (так может получится только в том случае, если условия отрабатываются внутри виджета)
Во-первых, каким именно виджетом у вас выводится облако меток?
В том-то и дело, что виджеты не предусматривают — ни «самоотключения» в отсутствие данных для вывода, ни php-кода в своих заголовках для условных операторов. На это способен лишь виджет предназначенный специально для кода.
А мне нужно, чтобы была возможность проверить виджет на сам факт вывода данных. И если данные не выводятся («пусто»), то виджет должен отключиться.
Ну, об этом я вам говорил — узнать логику вывода виджетов, тогда и решение само-собой придет.
…
Тогда нужно что-нить с кодом придумывать — код писать для ваших условий и задач.
Но в любом случае, со слов ясно только приблизительно… без визуального осмотра не вполне ясна логика вывода виджетов в шаблоне. А значит и помочь конкретным решением сложно..
Божественная статья» Спасибо огромное
На здоровье, Павел!
Подскажите, а как на странице тега вывести список рубрик относящихся к этому тегу.
Спасибо, буду очень благодарен!
Привет.
Это нужно код писать…
Сиюминутного решения нет.
В общем, это задача. Потому что обычно поступают от обратного.
Здравствуйте,а как вывести метки так:7-8 отображаются ,а остальные скрыты «сполером» и рядом кнопка «показать все метки»
Тоже интересно, не нашли информацию про сполер для меток?
это нужно в конкретном шаблоне смотреть…
в принципе не сложно скрыть в спойлер контент, но нужно решать по обстоятельствам подключения JS и прочего для конкретного шаблона…