Strange that stickies aren't completely unset from the main loop on paged pages but only on the first page. If we look at the source, we will see that stickies are only unset from the main loop if they are on the first page. So we have two options here depending on what you exactly need
OPTION 1
If you need to keep your stickies in the loop on paged pages and just remove the styling, you can make use of the is_paged()
condition in conjuction with your condition
if ( is_sticky()
&& !is_paged()
) {
// Add your styling here
}
OPTION 2.1
Completely remove stickies from paged pages
add_action( 'pre_get_posts', function ( $q )
{
if ( $q->is_home() // Only target the home page
&& $q->is_main_query() // Only target the main query
&& $q->is_paged() // Only target paged pages
) {
// Remove stickies
$q->set( 'post__not_in', get_option( 'sticky_posts' ) );
}
});
I'm just thinking that if we use this option that we will need to adjust $found_posts
to compensate for pagination on the first page. WP_Query
throws us a curveball here as we cannot set post__not_in
on page one as this will explicitely remove any sticky post from the sticky posts array if these specific posts aren't on the first page.
I will investigate this and post anything extra that would be relevant to this issue
EDIT
There is an issue with pagination, so we will need to adjust the $found_posts
property to adjust for pagination
add_filter( 'found_posts', function( $found_posts, \WP_Query $q )
{
if ( $q->is_home()
&& $q->is_main_query()
&& !$q->is_paged()
) {
// Get the sticky posts array
$stickies = get_option( 'sticky_posts' );
// Get all the post ID's from the first page
$ids = $q->posts;
// Remove all the current ids from the current sticky posts array
$stickies = array_diff( $stickies, $ids );
$found_posts = $found_posts - count( $stickies );
}
return $found_posts;
}, 10, 2 );
OPTION 2.2
I always tend to use the following right off the back to handle my sticky posts. This completely removes sticky posts from the main query and then it gets added back to via the the_posts
filter
add_action( 'pre_get_posts', function ( $q )
{
if ( $q->is_home()
&& $q->is_main_query()
) {
$q->set( 'ignore_sticky_posts', 1 );
$q->set( 'post__not_in', get_option( 'sticky_posts' ) );
add_filter( 'the_posts', function( $posts, \WP_Query $q )
{
// Only do this for the first page
if ( $q->is_paged() )
return $posts;
$stickies = get_option( 'sticky_posts' );
// Check if we have stickies
if ( !$stickies )
return $posts;
$args = [
'posts_per_page' => count( $stickies ),
'post__in' => $stickies,
];
$sticky_posts = get_posts( $args );
// Merge the array
$posts = array_merge( $sticky_posts, $posts );
return $posts;
}, 10, 2 );
}
});