This article describes how to create multiple post loops with pagination using a shortcode. You might already know how to create a post list with a shortcode, here I am extending that with multiple occurrences and pagination.
Multiple Post Type Loop & Pagination by Shortcode – Code
function w4dev_custom_loop_shortcode( $attrs ) {
static $w4dev_custom_loop;
if ( ! isset ( $w4dev_custom_loop ) ) {
$w4dev_custom_loop = 1;
} else {
$w4dev_custom_loop ++;
}
$attrs = shortcode_atts( array(
'paging' => 'pg'. $w4dev_custom_loop,
'post_type' => 'post',
'posts_per_page' => '5',
'post_status' => 'publish'
), $attrs );
$paging = $attrs['paging'];
unset( $attrs['paging'] );
if ( isset( $_GET[ $paging ] ) ) {
$attrs['paged'] = max( 1, absint( $_GET[ $paging ] ) );
} else {
$attrs['paged'] = 1;
}
$html = '';
$custom_query = new WP_Query( $attrs );
$pagination_base = add_query_arg( $paging, '%#%' );
if ( $custom_query->have_posts() ) :
$html .= '<ul>';
while( $custom_query->have_posts()) : $custom_query->the_post();
$html .= sprintf(
'<li><a href="%1$s">%2$s</a></li>',
get_permalink(),
get_the_title()
);
endwhile;
$html .= '</ul>';
wp_reset_postdata();
endif;
$html .= paginate_links( array(
'type' => '',
'base' => $pagination_base,
'format' => '?'. $paging .'=%#%',
'current' => max( 1, $custom_query->get('paged') ),
'total' => $custom_query->max_num_pages
));
return $html;
}
add_shortcode( 'w4dev_custom_loop', 'w4dev_custom_loop_shortcode' );
For pagination, we are using a custom query argument pg rather than the default page, so it won’t affect any other pagination on the page. The shortcode can be used multiple times and pg gets an increasing number, ex: pg1, pg2 etc. You can of course define your own variable name, ex: paginate_page, paginate_product or anything else, as long as it isn’t a WordPress reserved query variable.
Usage
The shortcode can be used with [w4dev_custom_loop] in your page or post content. Try copying the code into your theme’s functions.php or plugin file, then use the two shortcodes [w4dev_custom_loop] and [w4dev_custom_loop post_type="page"]. This will output a list of posts and a list of pages. You can paginate both lists without losing the other list’s pagination. That means, if you are on level 3 of the post list, and then navigate the page list to level 2, both lists will keep their offset correct.

Leave a Reply