On several pages, including a category archive page (and in the category feed), WordPress by default shows posts in that category and its child or sub-categories.
What if you want to change which posts are included? Use the pre_get_posts filter to modify the query sent to the database and customise what posts are displayed. Here are some functions to add to your theme’s functions.php file.
Exclude A Specific Category
To exclude a specific category with category id ‘xx’ from the home page:
function exclude_category($query) {
if ($query->is_home) {
$query->set('cat', '-xx');
}
return $query;
}
add_filter('pre_get_posts', 'exclude_category');
Exclude Multiple Categories
Separate multiple categories with spaces. E.g. to exclude categories with ids ‘xx’, ‘xy’ and ‘xz’, change line 3 in the above to:
$query->set('cat', '-xx -xy -xz');
Include Categories
To include a single category with id ‘xx’, change line 3 in the above to:
$query->set('cat', 'xx');
To include multiple categories with ids ‘xx’, ‘xy’ and ‘xz’, change line 3 in the above to:
$query->set('cat', 'xx xy xz');
Exclude Child Categories
To show only the posts in the selected category and not those in its descendent categories add the following to functions.php:
function exclude_child_cats($query){
if ($query->is_category){
$this_category=get_query_var('cat');
$child_cats=get_categories(array('parent' => $this_category));
$this_category.=' ';
foreach($child_cats as $child_cat){
$this_category.='-'.$child_cat->cat_ID.' ';
}
$query->set('cat', $this_category);
}
}
add_filter('pre_get_posts','exclude_child_cats');
Other Pages You Can Test For
So far the examples have test whether the current page is the home page, using if($query->is_home), or a category archive page, using if($query->is_category). Here is a list of all the query types you can test for:
is_singleis_pageis_archiveis_dateis_yearis_monthis_dayis_timeis_authoris_categoryis_tagis_taxis_searchis_feedis_comment_feedis_trackbackis_homeis_404is_pagedis_adminis_attachmentis_singularis_robotsis_posts_page
These Changes Affect Your Feeds
So you want these same changes to your feed too? – Done!
WordPress generates your feeds ‘on-the-fly’, using the same query as for displaying your site in a browser. Therefore any changes you make using this method also apply to your feeds. Very cool!
UPDATE: This system works great if you are using the default permalinks settings, but will not work with “Pretty Permalinks”!