Last active
May 5, 2023 17:09
-
-
Save kbcarte/619dd225aeea78db3f7ef2df4c101771 to your computer and use it in GitHub Desktop.
Page Template custom WP_Query with ajax and pagination
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/* | |
Template Name: Blog Archive | |
Author: kbcarte | |
*/ | |
get_header(); | |
?> | |
<section class="article-list"> | |
<div id="cat-list" class="cat-list"> | |
<a data-topic="all" href="/blog/?topic=all" class="topic all current">All</a> | |
<a data-topic="cat-a" href="/blog/?topic=cat-a" class="topic cat-a">Topic A</a> | |
<a data-topic="cat-b" href="/blog/?topic=cat-b" class="topic cat-b">Topic B</a> | |
<a data-topic="cat-c" href="/blog/?topic=cat-c" class="topic cat-c">Topic C</a> | |
<a data-topic="cat-d" href="/blog/?topic=cat-d" class="topic cat-d">Topic D</a> | |
</div> | |
<div id="ajax-results"></div> | |
</section> | |
<script> | |
const clear_current_topics = (topic_links) => { | |
topic_links.forEach( (topic) => { | |
topic.classList.remove('current'); | |
} ); | |
} | |
const get_posts = (topic, paged) => { | |
jQuery.ajax({ | |
type: 'POST', | |
url: '<?php echo admin_url("admin-ajax.php"); ?>', | |
data: { | |
action: 'blog_archive_ajax_pagination', | |
topic: topic, | |
paged: paged | |
}, | |
success: function(data, textStatus, XMLHttpRequest){ | |
jQuery("#ajax-results").html(data['data']['html']); | |
const current_topic = document.querySelector(".article-list .cat-list .topic.current").getAttribute('data-topic'); | |
// another ajax call for when page numbers are clicked | |
const paged_nav_list = document.querySelectorAll("#ajax-results .pagination .page-numbers a.page-numbers"); | |
if( paged_nav_list ){ | |
paged_nav_list.forEach((p)=> { | |
const urlParams = new URLSearchParams(p.href.split('?')[1]); | |
// bug with pagination and `add_fragment` for the first page of pagination | |
if( p.text === "1" ){ | |
p.href = "?paged=1&topic=" + current_topic; | |
} | |
p.addEventListener('click', (e) => { | |
e.preventDefault(); | |
get_posts(urlParams.get('topic'), urlParams.get('paged')); | |
}); | |
}); | |
} | |
// another ajax call for when the category filter is clicked | |
const cat_nav_list = document.querySelectorAll(".article-list .cat-list .topic"); | |
if( cat_nav_list ){ | |
cat_nav_list.forEach((c)=> { | |
const urlParams = new URLSearchParams(c.href.split('?')[1]); | |
c.addEventListener('click', (e) => { | |
e.preventDefault(); | |
clear_current_topics(cat_nav_list); | |
c.classList.add('current'); | |
get_posts(urlParams.get('topic'), urlParams.get('paged')); | |
}); | |
}); | |
} | |
}, | |
error: function(MLHttpRequest, textStatus, errorThrown){ | |
console.log(errorThrown); | |
} | |
}); | |
} | |
// get the list of posts initially on page load | |
get_posts('<?php echo $cat; ?>', '<?php echo $paged; ?>'); | |
</script> | |
<?php | |
get_footer(); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
// Yoink: https://ourcodeworld.com/articles/read/1603/how-to-determine-the-estimated-reading-time-of-a-text-with-php | |
function estimateReadingTime($text, $wpm = 200) { | |
$totalWords = str_word_count(strip_tags($text)); | |
$minutes = floor($totalWords / $wpm); | |
$seconds = floor($totalWords % $wpm / ($wpm / 60)); | |
return "<span class='read-time'>" . $minutes . "</span>"; | |
} | |
// Yoink https://wordpress.stackexchange.com/a/154364 | |
if ( ! function_exists( 'pagination' ) ) { | |
function pagination( $paged = '', $max_page = '', $topic = 'all' ) { | |
$big = 999999999; // need an unlikely integer | |
if( ! $paged ) { | |
$paged = get_query_var('paged'); | |
} | |
if( ! $max_page ) { | |
global $wp_query; | |
$max_page = isset( $wp_query->max_num_pages ) ? $wp_query->max_num_pages : 1; | |
} | |
echo paginate_links( array( | |
'base' => "%_%", | |
'current' => max( 1, $paged ), | |
'total' => $max_page, | |
'mid_size' => 1, | |
'prev_text' => __( '<span class="prev hide-me"></span>' ), | |
'next_text' => __( '<span class="next hide-me"></span>' ), | |
'type' => 'list', | |
'add_fragment' => "&topic=".$topic, | |
'format' => '?paged=%#%' | |
) ); | |
} | |
} | |
function blog_archive_ajax_pagination(){ | |
$paged = ($_POST['paged']) ? $_POST['paged'] : 1; | |
$temp = $posts; | |
$cat = $_POST['topic']; | |
if( !$cat ){ | |
$cat = 'all'; | |
} | |
if( $cat == 'all' ){ | |
$main_args = array( | |
'post_status' => 'publish', | |
'posts_per_page' => 6, | |
'paged' => $paged | |
); | |
} else { | |
$main_args = array( | |
'post_status' => 'publish', | |
'posts_per_page' => 6, | |
'paged' => $paged, | |
'tax_query' => array( | |
array( | |
'taxonomy' => 'category', | |
'field' => 'slug', | |
'terms' => $cat | |
) | |
) | |
); | |
} | |
$posts = new WP_Query( $main_args ); | |
if( $posts->have_posts() ){ | |
ob_start(); ?> | |
<div class="articles"> | |
<?php | |
while( $posts->have_posts() ){ | |
$posts->the_post(); | |
?> | |
<div class="article"> | |
<a href="<?php echo get_the_permalink( get_the_ID() ) ?>" class="featured-image" style="background-image: url(<?php echo get_the_post_thumbnail_url(get_the_ID()) ?>);"></a> | |
<div class="category"><?php echo get_the_category( get_the_ID() )[0]->name ?></div> | |
<h4 class="title"><?php echo get_the_title() ?></h4> | |
<div class="date-time"><?php echo date("M d, Y", strtotime(get_the_date())); ?> <span class="pipe">|</span> <?php echo estimateReadingTime(get_the_content()) ?> MIN READ</div> | |
<a href="<?php echo get_the_permalink( get_the_ID() ) ?>" class="read-more">Read More</a> | |
</div> | |
<?php | |
} | |
?> | |
</div> | |
<nav class="pagination"> | |
<?php pagination( $paged, $posts->max_num_pages, $cat); ?> | |
</nav> | |
<?php | |
} else { | |
// Error message: sorry, no posts here | |
} | |
$posts = null; | |
$posts = $temp; | |
$response = array( | |
'status' => 'success', | |
'html' => ob_get_clean(), | |
'paged' => $paged | |
); | |
wp_reset_postdata(); | |
wp_send_json_success($response); | |
wp_die(); | |
} | |
add_action( 'wp_ajax_nopriv_blog_archive_ajax_pagination', 'blog_archive_ajax_pagination' ); | |
add_action( 'wp_ajax_blog_archive_ajax_pagination', 'blog_archive_ajax_pagination' ); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment