Reputation: 33
I'm using this method to load more posts with Ajax.
I'm also using Masonry for the posts layout.
Masonry works fine for the first set of posts, but not for the next set of posts that are appended after clicking load more posts.
How can I make Masonry work after loading more posts?
index.php
<!-- Post Layout -->
<div class="posts <?php echo $home_style; ?>">
<!-- Normal Post -->
<?php
if (have_posts()) :
/* Start the Loop */
while (have_posts()) : the_post();
/* Home Layout */
if ($home_style === 'standard') {
get_template_part('inc/posts/content');
} else {
get_template_part('inc/posts/content', 'grid');
}
endwhile;
else :
get_template_part('template-parts/content', 'none');
endif;
?>
<?php
global $wp_query; // you can remove this line if everything works for you
// don't display the button if there are not enough posts
if ($wp_query->max_num_pages > 1)
// you can use <a> as well
echo '<div class="misha_loadmore grid-post">More posts</div>';
?>
</div>
<!-- Post Layout / END -->
Ajax Code
jQuery(function ($) {
$('.misha_loadmore').click(function () {
var button = $(this),
data = {
'action': 'loadmore',
'query': misha_loadmore_params.posts,
'page': misha_loadmore_params.current_page
};
$.ajax({
url: misha_loadmore_params.ajaxurl, // AJAX handler
data: data,
type: 'POST',
beforeSend: function (xhr) {
// change the button text, you can also add a preloader image
button.text('Loading...');
},
success: function (data) {
if (data) {
button.text('More posts').prev().before(data); // insert new posts
misha_loadmore_params.current_page++;
if (misha_loadmore_params.current_page == misha_loadmore_params.max_page)
button.remove(); // if last page, remove the button
// you can also fire the "post-load" event here
// if you use a plugin that requires it
// $( document.body ).trigger( 'post-load' );
} else {
button.remove(); // if no data, remove the button as well
}
}
});
});
});
Masonry script.js
/* Masonary Grid */
$('.home-grid').masonry({
itemSelector: '.grid-post',
percentPosition: true,
gutter: 33
});
Upvotes: 3
Views: 2650
Reputation: 6778
In most javascript libraries, if you change the DOM (HTML) after initializing the plugin, you will have to tell the library that changes have been made. Most libraries will include a function or listen to an event that tells it to update. In the case of Masonry, it looks like this function is reloadItems.
In your case, it looks like you will have to call $('.home-grid').masonry('reloadItems');
directly after you do button.text( 'More posts' ).prev().before(data);
.
Full code:
jQuery(function ($) {
$('.misha_loadmore').click(function () {
var button = $(this),
data = {
'action': 'loadmore',
'query': misha_loadmore_params.posts,
'page': misha_loadmore_params.current_page
};
$.ajax({
url: misha_loadmore_params.ajaxurl, // AJAX handler
data: data,
type: 'POST',
beforeSend: function (xhr) {
button.text('Loading...');
},
success: function (data) {
if (data) {
button.text('More posts').prev().before(data); // insert new posts
$('.home-grid').masonry('reloadItems');
misha_loadmore_params.current_page++;
if (misha_loadmore_params.current_page == misha_loadmore_params.max_page)
button.remove(); // if last page, remove the button
} else {
button.remove(); // if no data, remove the button as well
}
}
});
});
});
Upvotes: 3