Archived topic
Add Custom Search Box for a certain Category
12 replies · Started by Dave on January 5, 2021
I would like to add a custom search box that searches only 1 category.
Is this possible?
Cheers,
Dave
Hi,
Can you explain a bit more on how it would work?
Does it only appear on the specific category archive page it appears into?
How and where do you want it placed? Do you want to replace the default search icon? Or perhaps add a sidebar that contains this search box?
Let us know.
It would be a search box for a specific page in its custom header. (see private information for link).
Basically they would punch in the search term and the results would be limited to a certain category.
I don't want to replace the default search but would want some custom text in the box as a CTA.
Cheers,
Dave
To clarify further:
Did you mean, the specific search function should only run on the specified page, else the search should run as it normally does?
If so, you'll need to use pre_get_posts.
https://developer.wordpress.org/reference/hooks/pre_get_posts/
Say for example, you only want the search form to behave differently on the "Experiences" page with
function wpsites_display_one_category( $query ) {
if ( $query->is_page('experiences') && $query->is_main_query() ) {
if ( $query->is_search ) {
$query->set(
'category_name', array('category_slug_1, category_slug_2')
);
}
}
add_action( 'pre_get_posts', 'wpsites_display_one_category' );
Where is_page() contains the "Experiences" page slug. $query->is_search is when you're doing a search query and the $query->set() category_name means the search query searches for posts on this specified category.
Thanks Elvin. One question that I have is if I have more than one search function on the page (a site wide search box in the main menu) would that be affected as well? Or is it possible to have two different search boxes on one page?
cheers,
Dave
What is the snippet code if I want the search box on the blog page to only search for blog posts?
Do I need to use a separate search box for each page? Right now, on my staging site, I have a separate page called "Search the Site", which outputs Blog Posts, CPT's, and Pages, and I have a search input box on my blog page which outputs the same. I would love it if my blog search only output blog post search results excluding CPT's and pages.
Please let me know.
Thanks,
Search the Site https://savacaystage.wpengine.com/search-site/
Blog https://savacaystage.wpengine.com/blog/
@Dave
Thanks Elvin. One question that I have is if I have more than one search function on the page (a site wide search box in the main menu) would that be affected as well? Or is it possible to have two different search boxes on one page?
Ah if that's the case, this is what you should do instead. Note: This will require child theme files.
https://www.wpbeginner.com/wp-tutorials/how-to-use-multiple-search-forms-in-wordpress/
Alternatively, you can try looking for a plugin that does this for you.
@Alan
You need something like this:
function search_filter($query) {
if ( ! is_page('Search the Site') && $query->is_main_query() ) {
if ( $query->is_search ) {
$query->set( 'post_type', 'post' );
}
}
}
add_action( 'pre_get_posts', 'search_filter' );
This only searches for post_type that are single posts.
If Search the Site doesn't work. try replacing it with the page's slug or page_id.
Unfortunately, that did not work. For the page_id it shows as https://savacaystage.wpengine.com/wp-admin/post.php?post=84&action=edit. What should I use for that between the single quotes?
Please let me know.
Thanks,
Please refer to the official documentation of WordPress about is_page().
https://developer.wordpress.org/reference/functions/is_page/
The documentation mentioned the parameters accepted which are:
Page ID, title, slug, or array of such
Also, I've corrected the code a bit to remove the space between ! and is_page() so it should be !is_page(...) (no space) rather than ! is_page('...')(with space).
Let us know.
The following code works, but then my Blog page (84) and Search the Site page display only blog posts. I want only blog posts for my Blog page but all three types, Tours, Posts, and CPT, for the Search the Site page...
Please let me know.
Thanks,
function search_filter($query) {
if ( !is_page( 84 ) && $query->is_main_query() ) {
if ( $query->is_search ) {
$query->set( 'post_type', 'post' );
}
}
}
add_action( 'pre_get_posts', 'search_filter' );
The following code works, but then my Blog page (84) and Search the Site page display only blog posts. I want only blog posts for my Blog page but all three types, Tours, Posts, and CPT, for the Search the Site page…
To clarify: Are "Tours" and "Posts" category names or are they names of post types? This is important for the query->set()
Here's an example.
function search_filter($query) {
if ( is_page('84') && $query->is_main_query() ) {
$query->set( 'post_type', 'post' );
} if ( $query->is_search ) {
$query->set( 'post_type', array('post','custom_post_type_1','custom_post_type_2') );
$query->set( 'cat', '-22, -21 );
}
}
add_action( 'pre_get_posts', 'search_filter' );
Where -22 and -21 in $query->set( 'cat', '-22, -21 ); are the category ids you want to exclude. If you want to specify, use positive values for the IDs.
And on this line $query->set( 'post_type', array('post','custom_post_type_1','custom_post_type_2') );,
custom_post_type_1 and custom_post_type_2 are CPT slug names.
You'll also have to set the conditions.
if ( $query->is_search ) is the condition if you want to do something when the query is a search.
There are plenty of reference for this incase you still find it confusing:
https://webhostinghero.org/how-to-exclude-categories-from-search-in-wordpress/
https://www.billerickson.net/customize-the-wordpress-query/
This is getting a little too complicated for me. I will just ask my developer to handle it.
Since Dave is also involved, not sure if this should be marked resolved...
Thanks,
This is getting a little too complicated for me. I will just ask my developer to handle it.
Since Dave is also involved, not sure if this should be marked resolved…
Thanks,
No problem. :)