I’m creating a theme with a custom post type for team members, I’ve also got the following page structure:
about <-- this is a page
about/team-members <-- this is a page, lists all the team members
about/team-members/joe-bloggs <-- this is a custom post type (team member) entry
The third structure here uses the about and team member pages, but goes on to use the custom post type slug to make it look like it’s parents are team member and about. I’ve achieved this by setting the following options on the custom post type:
...
'rewrite' => array( 'slug' => 'about/team-members', 'with_front' => false)
...
This works great, however when I get down to the team member post level I no longer get the current-page, current-ancestor classes on the parent pages. I know why this is, because we’re not technically on a pagea parent of those pages, however is there a way I can trick/fix/bodge so the pages DO apear as parents?
I had achieved this nicely by using pages for team members, however a custom post type was chosen instead for easy of use for the administrator.
Thanks guys + girls!
When Working with pages you can select a parent page and that value is saved as the parent page id number in the child page’s
post_parent
field in the database.In your case, you are using a custom post type so you would need to create your own metabox for the parent page; something like:
It has nothing to do with
register_post_type
. You are tricking WordPress into thinking that it is a child page of another post type (page).I went with a custom walker to achieve something similar… avoids needs for custom fields, but all posts of a type have to sit below the same point in the page tree.
Disclaimer: After giving it a try this seems a not longer existing problem to me, because – at least for me – it just works on my WP 3.9.2 installation. Couldn’t find a according bug tracker though.
I have out together a little plugin to test this, which might help someone. But like I said in above disclaimer, I couldn’t reproduce the problem in a current wordpress installation. I’ve separated the plugin into four files, they are going together into one directory inside the plugin directory.
plugin-cpt_menu_hierarchy.php:
include-register_post_type.php:
include-cpt_parent_meta_box.php:
include-menu_highlighting.php:
A possible solution is whenever the custom post type is saved, you can set its’ parent to be
about/team-members
prgrammatically.Here are the steps:
I had some more time to dig into this myself (sorry if I wasted anyone’s time), and I figured that for me, the best way to solve the highlighting problem would be to kinda re-do what
_wp_menu_item_classes_by_context()
is doing, that is iterate over all parents and ancestors of the menu item that acts as the parent of my custom post type, and add classes appropriately.Since I also wanted to have the parent page for my custom post type fixed, and easily changeable without having to update all posts once the parent changes, I’ve decided to use an option instead of populating the
post_parent
field of my custom post type posts. I’ve used ACF for that since I’m using it in my theme anyways, but using the default WordPress option functionality would of course do it too.For my needs I could make use of the
wp_nav_menu_objects
filter. Additionally I had to filter thepage_for_posts
option so that it returns a falsely/empty value, this avoids the default posts page to be highlighted too.Note that I didn’t go all the way, the filter only adds the
current-menu-ancestor
andcurrent-menu-parent
classes, as this was enough for my needs!For the sake of completeness, when populating
post_parent
(see @Bainternet’s answer) instead of using options, then retrieving the parent ID could look something like this:http://codex.wordpress.org/Function_Reference/get_post_type_object
http://codex.wordpress.org/Function_Reference/get_page_by_path
EDIT 1:
Since pointers do not work: