web-dev-qa-db-fra.com

Les résultats de recherche classés par types de publication personnalisés ne sont pas groupés.

Pour un site Web WordPress, j'ai deux types de publication personnalisés, nommés cities et books, ainsi que les publications de blog classiques. J'ai personnalisé la page de résultats de recherche (recherche uniquement dans le titre du message) afin que les résultats soient classés par type de message personnalisé.

Le problème est que les résultats de la recherche dans un type de publication personnalisé ne sont pas vraiment regroupés.

Exemple:

Lorsque je recherche les lettres am, les résultats suivants apparaissent dans la page de résultats de recherche:

BOOKS
-----
Book 1

CITIES
------
City 1

BOOKS
-----
Book 2
Book 3

CITIES
------
City 2
City 3
City 4

BLOGPOSTS
---------
Post 1
Post 2
Post 3
etc.

Ce que je voudrais:

BOOKS
-----
Book 1
Book 2
Book 3

CITIES
------
City 1
City 2
City 3
City 4

BLOGPOSTS
---------
Post 1
Post 2
Post 3
etc.

Ceci est ma boucle:

<?php if(have_posts()) : ?>

    <?php   
        $last_type = "";
        $typecount = 0;
        while ( have_posts() ) : the_post();
    ?>

        <?php
            if ($last_type != $post->post_type){
                $typecount = $typecount + 1;
                if ($typecount > 1){
                    echo '</div><!-- close type-container -->'; //close type container
                }

                // save the post type.
                $last_type = $post->post_type;

                //open type container
                switch ($post->post_type) {
                    case 'books':
                        echo "<div class=\"books-container\"><h2>";
                        _e('Books', 'qode');
                        echo "</h2>";
                    break;

                    case 'cities':
                        echo "<div class=\"cities-container\"><h2>";
                        _e('Destinations', 'qode');
                        echo "</h2>";
                    break;

                    case 'post':
                        echo "<div class=\"blog-container\"><h2>";
                        _e('Blogposts', 'qode');
                        echo "</h2>";
                    break;
                }
            }
        ?>

        <?php if('books' == get_post_type()) : ?>

             <?php get_template_part('templates/books_search', 'loop'); ?>

        <?php elseif('cities' == get_post_type()) : ?>

            <?php get_template_part('templates/cities_search', 'loop'); ?>

        <?php elseif('post' == get_post_type()) : ?>

            <?php get_template_part('templates/blog_search', 'loop'); ?>

        <?php endif; ?>                     

    <?php endwhile; // endwhile have_posts ?>

    <?php // Pagination ?>
    <?php if($qode_options_proya['pagination'] != "0") : ?>
        <?php pagination($wp_query->max_num_pages, $blog_page_range, $paged); ?>
    <?php endif; ?>

    <?php else: //If no posts are present ?>
        <div class="entry nothing-found">                        
            <h3><?php _e('Sorry, there is no 100% ', 'qode') . " " . the_search_query() . " " . _e(' yet.') ?></h3>
            <p><?php _e('But there are loads of other 100% destinations available. Try again in the searchfield below.', 'qode'); ?> 
        </div>
<?php endif; // endif have_posts ?>

Et voici un exemple de fichier modèle pour un CPT en cours d’inclusion:

<div <?php post_class('vc_span4 wpb_column column_container'); ?> style="padding-bottom: 60px;">

<div class="wpb_wrapper book">

    <?php // Get the post thumbnail ?>
    <div class="wpb_single_image wpb_content_element element_from_fade element_from_fade_on">
        <div class="wpb_wrapper">
            <?php 
                if ( has_post_thumbnail() ) {
                    echo '<a href="' . get_permalink( $thumbnail->ID ) . '" title="' . the_title_attribute( 'echo=0' ) . '" class="book-holder" ><span class="book-thumb">';
                    echo get_the_post_thumbnail( $post->ID, 'book-thumbnail' ); 
                    echo '</span></a>';
                }
            ?>
        </div> 
    </div>

</div>

<div class="wpb_text_column wpb_content_element text-align-center" style="margin: 20px 0px 0px 0px; ">

    <div class="wpb_wrapper">
        <h5><?php the_title(); ?></h5>
    </div>
    <a href="<?php the_permalink(); ?>" target="_blank" class="qbutton  small" style="margin: 20px 0px 0px 0px; "><?php _e('More Info', 'qode'); ?></a>

</div>
</div>

Je dois faire quelque chose de mal ici, mais je ne peux pas comprendre quoi.

Quelqu'un peut-il me suggérer où je me trompe ici?

1
Justin Picard

Ce type de commande n'est pas disponible par défaut. Vous avez cependant deux options de base ici

  • rewind_posts() -> Réexécutez la boucle plusieurs fois et utilisez rewind_posts() pour rembobiner la boucle afin de pouvoir la réexécuter.

EXEMPLE

if ( have_posts() ) {
    while( have_posts() ) {
        the_post();

        if ( $post->post_type == 'books' ) {
            // Output books posts
        }

    } // end first while loop

    rewind_posts(); // rewind loop so we can rerun it

    while( have_posts() ) { // Start second while loop
        the_post();

        if ( $post->post_type == 'cities' ) {
            // Output cities posts
        }

    } // end second while loop

    rewind_posts(); // rewind loop so we can rerun it

    // Run your third while loop for blog posts

} // End your if statement
  • La deuxième méthode consiste à utiliser usort et le filtre the_posts pour trier vos publications en fonction de la boucle exécutée.

EXEMPLE

( Ceci va dans votre functions.php )

add_filter( 'the_posts', function( $posts, $q ) 
{
    if(     $q->is_main_query()  // Targets the main query only
         && $q->is_search() // Only targets the search page
    ) {

        usort( $posts, function( $a, $b )
      {
            $post_types = array ( // Set your post type order here
                'books' => 1,
                'cities' => 2,
                'post' => 3
            );

            $posts = $post_types[$a->post_type] - $post_types[$b->post_type];

            if ($posts === 0) {
                //same post_type, compare by post_date.
                return $a->post_date < $b->post_date;
            }else{
                //different post_type, save to ignore the post_date.
                return $posts;
            }
        } );
    } 
    return $posts;  
}, 
10, 2 );
3
Pieter Goosen