You have a few issues here
-
remove_filter( current_filter(), __FUNCTION__ )
is used in wrong context here for what you need to do.remove_filter()
unsets the filter from theGLOBALS
array once the filter has run once, so your filter is removed after the first run. This happens with spaghetti functions. -
You should always return the default filter (or some custom default) value the make sure that something is returned as is should your conditions fail
-
get_the_title()
simply usesget_post
to get the post object to return the$post_title
property of the object if no post object is passed toget_the_title()
. So, instead of usingget_the_title()
which is affected by the filter, simply useget_post
and from there get the post title
I would simply rewrite your filter as follow:
add_filter( 'the_title', function ( $title, $id )
{
// Make sure we are not in admin, if so, return $title
if ( is_admin() // Check if we are in admin
)
return $title;
//Should work on single product pages, product archive pages, and search pages.
if (
is_post_type_archive( 'eproduct' ) ||
is_singular ( 'eproduct' ) ||
is_search()
) {
$brand_id = get_post_meta( $id, '_wpcf_belongs_brand-listing_id', $single = true);
// Make sure we have a $brand_id to avoid bugs and unexpected output
if ( $brand_id ) {
$brand_title = get_post( $brand_id )->post_title;
$title = $brand_title . ' ' . $title;
}
// Either return title as is or our new modified title
return $title;
}
// Make sure we return $title if our conditions should fail
return $title;
}, 10, 2 );
Just an extra note, you would probably want to wrap everything in a in_the_loop()
condition to only target titles in the main query loop
EDIT
I forgot to say, the code above would require at least PHP 5.4 due to direct array de-referencing. The code is also untested