Ограничьте get_categories, чтобы показать каждую категорию один раз
-
16-10-2019 - |
Вопрос
Я пытаюсь создать домашнюю страницу, где это список категорий с соответствующей миниатюрой для каждого. Мне бы хотелось, чтобы это возвращает каждую категорию один раз и возвращает соответствующую миниатюру из последнего поста, или даже лучше не требует, чтобы я добавлял изображение в каждый пост, а скорее захватывает миниатюру от изображения поста, используя post_mime_type ? Я все еще ухожу с пути, так как он возвращает категорию для каждого поста, который находится в этой категории, а затем связывает изображение с каждой категорией.
Вот функция, с которой я работаю:
function home_filter() {
if ( is_home() )
{
add_filter( 'the_content', 'home_cats' );
}
}
add_action('template_redirect', 'home_filter');
function home_cats(){
$args=array(
'orderby' => 'name',
'order' => 'ASC',
);
$categories=get_categories($args);
foreach($categories as $category) {
echo '<li><a href="' . get_category_link( $category->term_id ) . '" title="' . sprintf( __( "View all posts in %s" ), $category->name ) . '" ' . '>' . get_the_post_thumbnail($page->ID, 'thumbnail') . $category->name.'</a></li> ';
}
}
Домашняя страница просто:
<ul>
<?php while ( have_posts() ) : the_post(); ?>
<?php the_content();?>
<?php endwhile; ?>
</ul>
Вывод - что -то вроде:
<ul>
<li><a href="../?cat=1" title="View all posts in Cat A" ><img src="..image-A.jpg" />Cat A</a></li>
<li><a href="../?cat=3" title="View all posts in Cat B" ><img src="..image-A.jpg" />Cat B</a></li>
<li><a href="../?cat=1" title="View all posts in Cat A" ><img src="..image-B.jpg" />Cat A</a></li>
<li><a href="../?cat=3" title="View all posts in Cat B" ><img src="..image-B.jpg" />Cat B</a></li>
<li><a href="../?cat=1" title="View all posts in Cat A" ><img src="..image-C.jpg" />Cat A</a></li>
<li><a href="../?cat=3" title="View all posts in Cat B" ><img src="..image-C.jpg" />Cat B</a></li>
</ul>
Может ли кто -нибудь, пожалуйста, помочь мне понять, как вернуть каждую категорию только один раз, и включить большой палец из последнего поста в этой категории? И еще лучше может кто -нибудь придумать способ сделать это без необходимости устанавливать изображение функции каждый раз?
Решение
Обычно Мне нравится уклоняться от рекомендации Direct SQL, но в вашем случае использования я думаю, что это оправдано.
Я закодировал это как прямой запрос SQL; Как вы можете заметить, немного сложно. Вы можете скопировать следующий код в свою тему functions.php
файл или добавьте его в .php
Файл плагина, который вы можете писать:
function home_cats($max_image_height=150){
$categories= get_taxonomy_latest_posts_with_attachment('category');
echo '<h1>Categories</h1>';
foreach($categories as $category) {
$category_link = get_category_link( $category->term_id );
$category_title = sprintf( __( "View all posts with category: '%s'" ),$category->term_name );
$post_title = get_the_title($category->post_id);
$post_link = get_permalink($category->post_id);
$img_html = wp_get_attachment_image( $category->attachment_id, array( 'thumbnail',$max_image_height ) );
$html = <<<HTML
<div id="category-{$category->term_slug}" class="category">
<span style="float:right;">{$img_html}</span>
<span style="float:left;">
<h2><a href="{$category_link}" title="{$category_title}">{$category->term_name}</a></h2>
<p style="float:left;">Latest post: <a href="{$post_link}" title="{$post_title}">$post_title</a></p>
</span>
</div>
<br clear="both" />
HTML;
echo $html;
}
}
function get_taxonomy_latest_posts_with_attachment($taxonomy) {
global $wpdb;
$sql =<<<SQL
SELECT
categorized_posts.rownum,
categorized_posts.term_id,
categorized_posts.term_name,
categorized_posts.term_slug,
categorized_posts.post_id,
categorized_posts.post_date,
categorized_posts.post_title,
attachments.ID AS attachment_id,
attachments.post_title AS attachment_title,
attachments.post_mime_type AS attachment_mime_type,
attachments.guid AS attachment_guid
FROM
(
SELECT
rownum,
term_id,
term_name,
term_slug,
post_id,
post_date,
post_title,
post_parent,
post_name,
post_type
FROM (
SELECT
IF( @prev <> {$wpdb->terms}.term_id, @rownum := 1, @rownum := @rownum+1 ) AS rownum,
@prev := {$wpdb->terms}.term_id,
{$wpdb->terms}.term_id,
{$wpdb->terms}.name AS term_name,
{$wpdb->terms}.slug AS term_slug,
{$wpdb->posts}.ID as post_id,
{$wpdb->posts}.post_date,
{$wpdb->posts}.post_title,
{$wpdb->posts}.post_parent,
{$wpdb->posts}.post_name,
{$wpdb->posts}.post_type
FROM
{$wpdb->term_taxonomy}
INNER JOIN {$wpdb->terms} ON {$wpdb->term_taxonomy}.term_id={$wpdb->terms}.term_id
INNER JOIN {$wpdb->term_relationships} ON {$wpdb->term_relationships}.term_taxonomy_id={$wpdb->term_taxonomy}.term_taxonomy_id
INNER JOIN {$wpdb->posts} ON {$wpdb->posts}.ID={$wpdb->term_relationships}.object_id
INNER JOIN (SELECT @rownum := NULL, @prev := 0) AS rownum_initializer ON 1=1
WHERE 1=1
AND {$wpdb->posts}.post_type='post'
AND {$wpdb->posts}.post_status='publish'
AND {$wpdb->term_taxonomy}.taxonomy='%s'
ORDER BY {$wpdb->posts}.post_parent DESC, {$wpdb->posts}.post_date DESC
) x
) categorized_posts
INNER JOIN (SELECT MAX(ID) AS post_id,post_parent FROM {$wpdb->posts} WHERE post_type='attachment' GROUP BY post_parent) attachment_join ON attachment_join.post_parent=categorized_posts.post_id
INNER JOIN {$wpdb->posts} attachments ON attachments.ID=attachment_join.post_id
WHERE
categorized_posts.rownum=1
GROUP BY
categorized_posts.term_id
ORDER BY
categorized_posts.term_name
SQL;
return $wpdb->get_results($wpdb->prepare($sql,$taxonomy));
}
Вы заметите, что я отделил логику, чтобы вы могли получить список любых терминов таксономии и их последних сообщений с фотографией, позвонив в get_taxonomy_latest_posts_with_attachment()
функционируйте и передавая его идентификатор таксономии, как это:
$post_tags = get_taxonomy_latest_posts_with_attachment('post_tags');
Из -за сложности SQL в этой функции я не собираюсь пытаться это объяснить (или я буду здесь всю ночь) Но если у вас есть конкретные последующие вопросы, просто спросите. В любом случае, вот как выглядит код на моей тестовой стороне с помощью тестовых данных:
(источник: mikeschinkel.com)
PS люди на фотографиях - мои друзья, и все так или иначе работают с WordPress. Надеюсь, они не возражают против того, чтобы я использовал их сходство. :)
Другие советы
Эта хитрость крюка довольно грязно, почему бы просто не позвонить home_cats()
в шаблоне?
Попробуйте это (обратите внимание, что это запрос на категорию и может стать уродливым для производительности):
function home_cats() {
$args = array(
'orderby' => 'name',
'order' => 'ASC',
);
$categories = get_categories($args);
echo '<ul>';
foreach ( $categories as $category ) {
$link = get_category_link($category->term_id);
$title = sprintf(__("View all posts in %s"), $category->name);
$posts = get_posts( array(
'cat' => $category->term_id,
'numberposts' => 1,
) );
$post = $posts[0];
$thumbnail = get_the_post_thumbnail($post->ID);
echo "<li><a href='{$link}' title='{$title}'>{$thumbnail}{$category->name}</a></li>";
}
echo '</ul>';
}
Есть разные способы для моих для изображений, я обычно иду с Получите изображение.