I am trying to get paging to work on my future post loop, but to no avail. I am getting no links, when I expect them at the bottom, for pagination despite there being several valid posts in the database.
<?php
$args = array(
'post_type' => 'program',
'paged' => get_query_var('paged') ? get_query_var('paged') : 1,
'posts_per_page' => 1,
'post_status' => "future",
'order_by' => 'date',
'order' => 'ASC'
);
$program = new WP_Query;
$program->query( $args );
if($program->have_posts()): while($program->have_posts()): $program->the_post(); ?>
//The content loop
<?php endwhile; ?>
<div><?php previous_posts_link('« Previous'); ?></div>
<div><?php next_posts_link('More »'); ?></div>
<?php endif; ?>
<?php wp_reset_query(); ?>
Update Further Info
I have established that $program->max_num_pages always displays the correct number of pages, so using the offset
argument for WP_Query
, I have been able to roll my own paging. But this seems like it’s asking for trouble!!
Update Further Info
I have taken the rather drastic step of extending the WP_Query object. This is really over the top, but I have to make this work:
class MF_Query extends WP_Query{
function __construct(array $args){
if(!array_key_exists('posts_per_page',$args)) $args['posts_per_page'] = 10;
$args['offset'] = (isset($_GET['page'])?($_GET['page']-1)*$args['posts_per_page']:0);
parent::query($args);
}
function mf_next_page($link_text = "Next"){
$curPage = intval((isset($_GET['page'])?$_GET['page']:1));//Use 1 if $_GET['page'] not set
$link = "<a href='".remove_post_vars(curPageURL());
if($curPage<$this->max_num_pages){
return $link.constructQuery($this->merge(array("page"=>$curPage+1),$_GET))."'>".$link_text."</a>";
} else {
return false;
}
}
function mf_prev_page($link_text = "Prev"){
$curPage = (isset($_GET['page'])?$_GET['page']:1);//Use 1 if $_GET['page'] not set
$link = "<a href='".remove_post_vars(curPageURL());
if($curPage>1){
return $link.$this->constructQuery($this->merge(array("page"=>$curPage-1),$_GET))."'>$link_text</a>";
} else {
return false;
}
}
private function constructQuery(array $query){
$url_ext = "?";
foreach($query as $k => $v){
$url_ext .=$k."=".$v."&";
}
$url_ext = substr($url_ext, 0, -5);//chop last ampersand off
return $url_ext;
}
private function merge($get, $put){
//Get values from one array, and put them in another (overriding existing values if appropriate)
foreach ($get as $k => $v){
$put[$k]=$v;
}
return $put;
}
}
Adjacent post fetching relies on quite a bit of custom SQL inside. One of the assumptions it makes in that SQL is that you are only looking for published post.
You can use filter in
get_adjacent_post()
(that is used internally by those next/previous functions) to alter the query and get rid of published only limitation.