In my functions.php file I have the below function and on my category edit page I have added a new field to capture a 'template' value that is stored in a serialised array. The template value saves fine (I can extract and print the value) but I am having trouble using this value as a conditional operator in my function.
add_action( 'parse_query', 'category_posts_per_page', 10, 1 );
function category_posts_per_page( $q_obj ) {
global $wp_query;
$cat_ID = get_query_var('cat');
$get_cat_template = get_option('category_template');
if (isset($get_cat_template[$cat_ID]['template'])) {
$cat_template = $get_cat_template[$cat_ID]['template'];
}
else {
$cat_template = 'normal';
}
if ( is_category() && ( $cat_template == 'gallery' ) ) {
$q_obj->query_vars['posts_per_page'] = 1;
}
}
The problem line I think is ( is_category() && ( $cat_template == 'gallery' ) ) but I've drawn a blank due to my very rudimentary PHP skills.
If I change $cat_template == 'gallery' to $cat_template = 'gallery' I get the desired result of 1 post per page, but this happens across all categories, not just those with a stored value of 'gallery'.
With $cat_template == 'gallery' 10 posts are shown (i.e. the value set in Settings > Reading > Blog pages show at most)
Any suggestions much appreciated.
Jurre Hanema answers:
Let's see. The comparison undoubtly fails because either $cat_ID or $get_cat_template do not contain the values you expect.
Can you add
var_dump($cat_ID, $get_cat_template);
after
$get_cat_template = get_option('category_template');
and post the result please?
designbuildtest comments:
Hi Jurre,
add_action( 'parse_query', 'category_posts_per_page', 10, 1 );
function category_posts_per_page( $q_obj ) {
global $wp_query;
$cat_ID = get_query_var('cat');
$get_cat_template = get_option('category_template');
var_dump($cat_ID, $get_cat_template);
if (isset($get_cat_template[$cat_ID]['template'])) {
$cat_template = $get_cat_template[$cat_ID]['template'];
}
else {
$cat_template = 'normal';
}
if ( is_category() && ( $cat_template == 'gallery' ) ) {
$q_obj->query_vars['posts_per_page'] = 1;
}
}
outputs:
string(0) "" array(2) { [40]=> array(1) { ["template"]=> string(7) "gallery" } [29]=> array(1) { ["template"]=> string(5) "swipe" } }
designbuildtest comments:
I have a dozen categories, one has been assigned a template value of 'gallery', another of 'swipe' and remainder have no template value assigned.
Jurre Hanema comments:
From your answer the problem is clear.
You think that $cat_ID contains the current category ID, but in fact it contains an empty string. So it seems that get_query_var('cat') is not the right way to get the current category ID.
I have modified your function, most importantly by using get_queried_object() to determine the cat ID:
function category_posts_per_page($q_obj)
{
if($q_obj->is_category())
{
$obj = $q_obj->get_queried_object();
$get_cat_template = get_option('category_template');
$cat_ID = $obj->term_id;
if(isset($get_cat_template[$cat_ID]['template']))
{
$cat_template = $get_cat_template[$cat_ID]['template'];
} else
{
$cat_template = 'normal';
}
if($cat_template == 'gallery')
{
$q_obj->query_vars['posts_per_page'] = 1;
}
}
return $q_obj;
}
I think this should about do the trick.
designbuildtest comments:
Fantastic!!! Works perfectly. Many thanks Jurre.
Julio Potier answers:
Hello
Just to be sure, before this line :
if ( is_category() && ( $cat_template == 'gallery' ) ) {
type this :
wp_die(var_dump($cat_template));
And tell me the result, thank you
designbuildtest comments:
H Julio, result is:
string(6) "normal"
Julio Potier comments:
Si if it's "<em>normal</em>", the <strong>== "gallery"</strong> is not true, so there is more than 1 post.
Logical no ?
This means that :
if (isset($get_cat_template[$cat_ID]['template'])) {
return <strong>false</strong>.
designbuildtest comments:
If I change my function to:
add_action( 'parse_query', 'category_posts_per_page', 10, 1 );
function category_posts_per_page( $q_obj ) {
global $wp_query;
$cat_ID = get_query_var('cat');
$get_cat_template = get_option('category_template');
$cat_template = $get_cat_template[$cat_ID]['template'];
return $cat_template;
if ( is_category() && ( $cat_template == 'gallery' ) ) {
$q_obj->query_vars['posts_per_page'] = 1;
}
}
and use
echo category_posts_per_page();
in my category-gallery.php file I get the value of 'gallery', but posts_per_page is still more than 1.
Sorry, I probably doing something really stupid somewhere.
Julio Potier comments:
If you
return $cat_template;
before the end of function, the last IF won't work.
Try this :
add_action( 'parse_query', 'category_posts_per_page', 10, 1 );
function category_posts_per_page( $q_obj ) {
global $wp_query;
$cat_ID = get_query_var('cat');
$get_cat_template = get_option('category_template');
$cat_template = $get_cat_template[$cat_ID]['template'];
if ( is_category() && ( $cat_template == 'gallery' ) ) {
$q_obj->query_vars['posts_per_page'] = 1;
}
return $q_obj;
}
designbuildtest comments:
My loop still outputs more than one post unfortunately with the above code.
If I delete...
&& ( $cat_template == 'gallery' )
...I get one post per page as expected.
Julio Potier comments:
Of course but this is not you wanted to do.
designbuildtest comments:
Yes, I know. My problem still then seems to be getting $cat_template == 'gallery' to perform as expected.
If I assign all my posts to a 'Gallery' category and simply use:
add_action( 'parse_query', 'category_posts_per_page', 10, 1 );
function category_posts_per_page( $q_obj ) {
if ( is_category('Gallery') ) {
$q_obj->query_vars['posts_per_page'] = 1;
}
}
Again, everything works as it should (as you would expect).
Many thanks for your time and effort on this so far.
Arnav Joy answers:
what is the value of $cat_template
try print it after
if (isset($get_cat_template[$cat_ID]['template'])) {
$cat_template = $get_cat_template[$cat_ID]['template'];
}
else {
$cat_template = 'normal';
}
as
echo $cat_template;
check this first.
and how are you getting this ??
$get_cat_template[$cat_ID]['template'];
Arnav Joy comments:
how you are assigning template to a category?
Arnav Joy comments:
if you want to show one post only for this category then you can also try
category-slug.php
or
category-ID.php
then in any of these file you can use query_posts() as follows:-
query_posts( 'posts_per_page=1' );
Francisco Javier Carazo Gil answers:
Hi designbuildtest,
If you do:
$cat_template = 'gallery'
You are assigning, not comparing.
If you want to show more post, change this line:
add_action( 'parse_query', 'category_posts_per_page', $number_of_posts, 1 );
Francisco Javier Carazo Gil comments:
And as Arnav says, be sure that the $cat_template has always a right value.
designbuildtest comments:
Hi Francisco, many thanks for your suggestions. Please see my thread with Julio above. Hopefully this provides a few more clues.
Just Me answers:
try
set_query_var('posts_per_page', 1);
instead of
$q_obj->query_vars['posts_per_page'] = 1;