Show latest posts from each custom post type with pre_get_posts

What I have


On my front page I have managed to alter the main query on the front page to show my custom post types with “pre_get_posts” like this:

Read More
function custom_post_types_in_home_loop( $query ) {

    if ( ! is_admin() && is_home() && $query->is_main_query() ) {
        $query->set( 'post_type', array( 'member',  'press', 'calendar_event' ) );
    }

    return $query;

}

add_filter( 'pre_get_posts', 'custom_post_types_in_home_loop' );

What I want


The problem is that some post types have way more posts than others, so I want to show only 3 posts per post type to get a little variation in the loop.

What I’ve tried


With some help from this and this answer ive managed to do this but nothing’s happening, what am I doing wrong?

function custom_post_types_in_home_loop( $query ) {

    if ( ! is_admin() && is_home() && $query->is_main_query() ) {
        $query->set( 'post_type', array( 'member',  'press', 'calendar_event' ) );

        if ( $query->get( 'post_type' ) == 'member' ) {
            $query->set('posts_per_page',  3);
        }

        /* And the same 'if' statement for 'press' and 'calendar_event' */
    }

    return $query;

}

add_filter( 'pre_get_posts', 'custom_post_types_in_home_loop' );

Related posts

Leave a Reply

1 comment

  1. You are setting post_type on the main query to an array. And then comparing it against a string. None of these conditionals are true and hence aren’t executing.

    If you simply want to limit the number of queries and pick a random order you can do so with,

    $query->set('posts_per_page', 9);
    $query->set('orderby', 'rand);
    

    This will give you 9 posts, 3 each, randomly choosen between the different Custom Post Types.

    To keep the different types together, you’ll need to build a more complex and resource intensive groupby query. If you need this, I’d suggest building 3 different Custom Loops for each post_type instead.