Problem with multiple loops

HI All,

I’m hoping someone might be able to help me with multiple loops problems I’m having. I am trying to do a magazine style layout with a featured post in a hero style which is the latest blog post. I am then trying to get the rest of the blog posts (10 to page ) in a second loop.

I have put the featured blog post loop in my header for the blog home and get the right post.

In my blog posts home page blade I have the second loop getting the rest of the posts.

Both work but I have the following issues:

  • when using the offset in the second loop it screws up the pagination and just shows pages of duplicate posts ignoring the post per page setting

  • when trying the code in the wordpress codex where they use the $do_not_duplicate method - https://codex.wordpress.org/The_Loop#Multiple_Loops_in_Action. the second loop displays no posts. I have discovered that the $do_not_duplicate method is correctly getting the id of the featured post first loop, but when it comes to the second loop, the $do_not_duplicate variable is empty, the value is not being passed from partial to partial.

I am very new to Sage and I really don’t know how to pass that value from one blade to the next, or have the value be saved. Or indeed if there is another way to do it.

I read about the right way to run multiple WordPress loops forum post with the logic in the controller file but I haven’t a clue how to start with that with two loops and then getting the $do_not_duplicate value in there.

This is my first loop code:

@php $my_query = new WP_Query( 'posts_per_page=1' );
    while ( $my_query->have_posts() ) : $my_query->the_post();
    $do_not_duplicate = $post->ID;
    @endphp `

And my second loop:

<?php if ( have_posts() ) : while ( have_posts() ) : the_post(); 
if ( $post->ID == $do_not_duplicate ) continue; ?>
	<div>
    <div class="uk-card uk-card-default uk-text-center">
      <div class="uk-card-media-top">
        <img src="<?php the_post_thumbnail_url(); ?>" data-src="" alt="" data-uk-img />
      </div>
      <div class="uk-card-body">

        <h3><a class="uk-link-reset" rel="bookmark" href="<?php the_permalink(); ?>">
            <?php the_title(); ?></a></h3>
            @include('partials/entry-meta-main')
            <div class="uk-margin-small-top">
              <?php the_excerpt(); ?>
            </div>
          <p><a class="uk-button red-button uk-border-rounded" href="<?php the_permalink(); ?>">Read more &raquo;</a></p>
      </div>
    </div>
  </div>
@php endwhile; endif; @endphp

Would really appreciate any help anybody can offer.

This seems a little over-complicated. This is my understanding of what you’re trying to do:

  • On Blog landing page:
  • Show latest post in the header (on its own)
  • Show the rest of the posts, and paginate them correctly

If I understand correctly, I think you can do it this way:

(I’m using @Log1x cool Sage Directives package here)

// In functions.php or something (i.e. not in a template file)
add_action('pre_get_posts', function ($query) {
   if ($query->is_main_query() && !is_admin()) :
       if($query->is_paged) :
           $query->set('offset', 1 + ( ($query->query_vars['paged']-1) * 10 );
           $query->set('posts_per_page', 10);
       else :
           $query->set('posts_per_page', 11);
       endif;
   endif;
}, 10, 1);

// This is your template
@global($wp_the_query)

// only do this on the first page of the blog
@if(!is_paged()) 
  // limit this `while` to only the very first post in the query
  @while(have_posts() && $wp_the_query->current_post < 0) @php(the_post())
     <article class="featured">
        <h2>@title</h2>
     </article>
  @endwhile
@endif

// On to the rest of your posts
@while(have_posts()) @php(the_post())
  <article class="post">
     <h2>@title</h2>
  </article>
@endwhile
2 Likes

Hi @alwaysblank ,

Thanks for your solution. I have installed the Sage Directives and tried to implement the solution but I am getting a problem where when loading the blog page now it just spins unresponsively doing nothing and then my CPU usage hits 100%. I use flywheel for local development. Only way to stop it is to restart the local site.

I’m not quite sure what is going on so hoping you might be able to help?

Thanks

Sounds like you’ve got an infinite loop, or something similar. The code I posted is meant to be a suggestion, not a solution—I haven’t tested it. There are plenty of other ways to achieve this effect if this one doesn’t work for you. If you want to debug it, I’d probably start by removing parts until the problem goes away to figure out what part is causing the issue. As always, it’s also a good idea to check the logs for your VM.

This topic was automatically closed after 42 days. New replies are no longer allowed.