Themes: Improve document title output.

Introduces more flexibility in filtering all parts of the document title,the
separator, and a way to short-circuit title generation. Plugins can now also
check for theme support and reliably filter the entire output. See #18548.
Deprecates `wp_title()`.

Fixes #31078.


Built from https://develop.svn.wordpress.org/trunk@35294


git-svn-id: http://core.svn.wordpress.org/trunk@35260 1a063a9b-81f0-0310-95a4-ce76da25c4cd
This commit is contained in:
Konstantin Obenland
2015-10-20 16:21:25 +00:00
parent b8e250927f
commit c69e96422b
12 changed files with 316 additions and 230 deletions

View File

@@ -781,184 +781,141 @@ function has_site_icon( $blog_id = 0 ) {
}
/**
* Display title tag with contents.
* Returns document title for the current page.
*
* @since 4.4.0
*
* @global int $page Page number of a single post.
* @global int $paged Page number of a list of posts.
*
* @return string Tag with the document title.
*/
function wp_get_document_title() {
/**
* Allows to short-circuit the title generation.
*
* @since 4.4.0
*
* @param string $title The document title. Default empty string.
*/
$title = apply_filters( 'pre_get_document_title', '' );
if ( ! empty( $title ) ) {
return $title;
}
global $page, $paged;
$title = array(
'title' => '',
);
if ( is_home() && is_front_page() ) {
$title['title'] = get_bloginfo( 'name', 'display' );
/*
* If we're on the blog page and that page is not the homepage or a single page that is designated as
* the homepage, use the container page's title.
*/
} elseif ( ( is_home() && ! is_front_page() ) || ( ! is_home() && is_front_page() ) ) {
$title['title'] = single_post_title( '', false );
// If we're on a post / page.
} elseif ( is_singular() ) {
$title['title'] = single_post_title( '', false );
// If we're on a category or tag or taxonomy archive.
} elseif ( is_category() || is_tag() || is_tax() ) {
$title['title'] = single_term_title( '', false );
// If it's a search.
} elseif ( is_search() ) {
/* translators: %s: search phrase */
$title['title'] = sprintf( __( 'Search Results for “%s”' ), get_search_query() );
// If we're on an author archive.
} elseif ( is_author() && $author = get_queried_object() ) {
$title['title'] = $author->display_name;
// If we're on a post type archive.
} elseif ( is_post_type_archive() ) {
$title['title'] = post_type_archive_title( '', false );
// If it's a date archive.
} elseif ( is_year() ) {
$title['title'] = get_the_date( _x( 'Y', 'yearly archives date format' ) );
} elseif ( is_month() ) {
$title['title'] = get_the_date( _x( 'F Y', 'monthly archives date format' ) );
} elseif ( is_day() ) {
$title['title'] = get_the_date();
// If it's a 404 page.
} elseif ( is_404() ) {
$title['title'] = __( 'Page not found' );
}
// Add a page number if necessary.
if ( ( $paged >= 2 || $page >= 2 ) && ! is_404() ) {
$title['page'] = sprintf( __( 'Page %s' ), max( $paged, $page ) );
}
// Append the description or site title to give context.
if ( is_home() && is_front_page() ) {
$title['tagline'] = get_bloginfo( 'description', 'display' );
} else {
$title['site'] = get_bloginfo( 'name', 'display' );
}
/**
* Filters the separator for the document title.
*
* @since 4.4.0
*
* @param string $sep The separator. Default '-'.
*/
$sep = apply_filters( 'document_title_separator', '-' );
/**
* Filters the parts of the document title.
*
* @since 4.4.0
*
* @param array $title {
* The document title parts.
*
* @type string $title Title of the viewed page.
* @type string $page Optional. Page number if paginated.
* @type string $tagline Optional. Site description when on home page.
* @type string $site Optional. Site title when not on home page.
* }
*/
$title = apply_filters( 'document_title_parts', $title );
$title = implode( " $sep ", array_filter( $title ) );
$title = wptexturize( $title );
$title = convert_chars( $title );
$title = esc_html( $title );
$title = capital_P_dangit( $title );
return $title;
}
/**
* Displays title tag with content.
*
* @ignore
* @since 4.1.0
* @since 4.4.0 Improved title output replaced `wp_title()`.
* @access private
*
* @see wp_title()
*/
function _wp_render_title_tag() {
if ( ! current_theme_supports( 'title-tag' ) ) {
return;
}
// This can only work internally on wp_head.
if ( ! did_action( 'wp_head' ) && ! doing_action( 'wp_head' ) ) {
return;
}
echo '<title>' . wp_title( '|', false, 'right' ) . "</title>\n";
}
/**
* Display or retrieve page title for all areas of blog.
*
* By default, the page title will display the separator before the page title,
* so that the blog title will be before the page title. This is not good for
* title display, since the blog title shows up on most tabs and not what is
* important, which is the page that the user is looking at.
*
* There are also SEO benefits to having the blog title after or to the 'right'
* or the page title. However, it is mostly common sense to have the blog title
* to the right with most browsers supporting tabs. You can achieve this by
* using the seplocation parameter and setting the value to 'right'. This change
* was introduced around 2.5.0, in case backwards compatibility of themes is
* important.
*
* @since 1.0.0
*
* @global WP_Locale $wp_locale
* @global int $page
* @global int $paged
*
* @param string $sep Optional, default is '&raquo;'. How to separate the various items within the page title.
* @param bool $display Optional, default is true. Whether to display or retrieve title.
* @param string $seplocation Optional. Direction to display title, 'right'.
* @return string|void String on retrieve.
*/
function wp_title( $sep = '&raquo;', $display = true, $seplocation = '' ) {
global $wp_locale, $page, $paged;
$m = get_query_var('m');
$year = get_query_var('year');
$monthnum = get_query_var('monthnum');
$day = get_query_var('day');
$search = get_query_var('s');
$title = '';
$t_sep = '%WP_TITILE_SEP%'; // Temporary separator, for accurate flipping, if necessary
// If there is a post
if ( is_single() || ( is_home() && !is_front_page() ) || ( is_page() && !is_front_page() ) ) {
$title = single_post_title( '', false );
}
// If there's a post type archive
if ( is_post_type_archive() ) {
$post_type = get_query_var( 'post_type' );
if ( is_array( $post_type ) )
$post_type = reset( $post_type );
$post_type_object = get_post_type_object( $post_type );
if ( ! $post_type_object->has_archive )
$title = post_type_archive_title( '', false );
}
// If there's a category or tag
if ( is_category() || is_tag() ) {
$title = single_term_title( '', false );
}
// If there's a taxonomy
if ( is_tax() ) {
$term = get_queried_object();
if ( $term ) {
$tax = get_taxonomy( $term->taxonomy );
$title = single_term_title( $tax->labels->name . $t_sep, false );
}
}
// If there's an author
if ( is_author() && ! is_post_type_archive() ) {
$author = get_queried_object();
if ( $author )
$title = $author->display_name;
}
// Post type archives with has_archive should override terms.
if ( is_post_type_archive() && $post_type_object->has_archive )
$title = post_type_archive_title( '', false );
// If there's a month
if ( is_archive() && !empty($m) ) {
$my_year = substr($m, 0, 4);
$my_month = $wp_locale->get_month(substr($m, 4, 2));
$my_day = intval(substr($m, 6, 2));
$title = $my_year . ( $my_month ? $t_sep . $my_month : '' ) . ( $my_day ? $t_sep . $my_day : '' );
}
// If there's a year
if ( is_archive() && !empty($year) ) {
$title = $year;
if ( !empty($monthnum) )
$title .= $t_sep . $wp_locale->get_month($monthnum);
if ( !empty($day) )
$title .= $t_sep . zeroise($day, 2);
}
// If it's a search
if ( is_search() ) {
/* translators: 1: separator, 2: search phrase */
$title = sprintf(__('Search Results %1$s %2$s'), $t_sep, strip_tags($search));
}
// If it's a 404 page
if ( is_404() ) {
$title = __('Page not found');
}
$prefix = '';
if ( !empty($title) )
$prefix = " $sep ";
/**
* Filter the parts of the page title.
*
* @since 4.0.0
*
* @param array $title_array Parts of the page title.
*/
$title_array = apply_filters( 'wp_title_parts', explode( $t_sep, $title ) );
// Determines position of the separator and direction of the breadcrumb
if ( 'right' == $seplocation ) { // sep on right, so reverse the order
$title_array = array_reverse( $title_array );
$title = implode( " $sep ", $title_array ) . $prefix;
} else {
$title = $prefix . implode( " $sep ", $title_array );
}
if ( current_theme_supports( 'title-tag' ) && ! is_feed() ) {
$title .= get_bloginfo( 'name', 'display' );
$site_description = get_bloginfo( 'description', 'display' );
if ( $site_description && ( is_home() || is_front_page() ) ) {
$title .= " $sep $site_description";
}
if ( ( $paged >= 2 || $page >= 2 ) && ! is_404() ) {
$title .= " $sep " . sprintf( __( 'Page %s' ), max( $paged, $page ) );
}
}
/**
* Filter the text of the page title.
*
* @since 2.0.0
*
* @param string $title Page title.
* @param string $sep Title separator.
* @param string $seplocation Location of the separator (left or right).
*/
$title = apply_filters( 'wp_title', $title, $sep, $seplocation );
// Send it out
if ( $display )
echo $title;
else
return $title;
echo '<title>' . wp_get_document_title() . '</title>' . "\n";
}
/**
@@ -1039,13 +996,9 @@ function post_type_archive_title( $prefix = '', $display = true ) {
/**
* Display or retrieve page title for category archive.
*
* This is useful for category template file or files, because it is optimized
* for category page title and with less overhead than {@link wp_title()}.
*
* It does not support placing the separator after the title, but by leaving the
* prefix parameter empty, you can set the title separator manually. The prefix
* does not automatically place a space between the prefix, so if there should
* be a space, the parameter value will need to have it at the end.
* Useful for category template files for displaying the category page title.
* The prefix does not automatically place a space between the prefix, so if
* there should be a space, the parameter value will need to have it at the end.
*
* @since 0.71
*
@@ -1060,11 +1013,7 @@ function single_cat_title( $prefix = '', $display = true ) {
/**
* Display or retrieve page title for tag post archive.
*
* Useful for tag template files for displaying the tag page title. It has less
* overhead than {@link wp_title()}, because of its limited implementation.
*
* It does not support placing the separator after the title, but by leaving the
* prefix parameter empty, you can set the title separator manually. The prefix
* Useful for tag template files for displaying the tag page title. The prefix
* does not automatically place a space between the prefix, so if there should
* be a space, the parameter value will need to have it at the end.
*
@@ -1082,11 +1031,7 @@ function single_tag_title( $prefix = '', $display = true ) {
* Display or retrieve page title for taxonomy term archive.
*
* Useful for taxonomy term template files for displaying the taxonomy term page title.
* It has less overhead than {@link wp_title()}, because of its limited implementation.
*
* It does not support placing the separator after the title, but by leaving the
* prefix parameter empty, you can set the title separator manually. The prefix
* does not automatically place a space between the prefix, so if there should
* The prefix does not automatically place a space between the prefix, so if there should
* be a space, the parameter value will need to have it at the end.
*
* @since 3.1.0
@@ -1144,14 +1089,10 @@ function single_term_title( $prefix = '', $display = true ) {
/**
* Display or retrieve page title for post archive based on date.
*
* Useful for when the template only needs to display the month and year, if
* either are available. Optimized for just this purpose, so if it is all that
* is needed, should be better than {@link wp_title()}.
*
* It does not support placing the separator after the title, but by leaving the
* prefix parameter empty, you can set the title separator manually. The prefix
* does not automatically place a space between the prefix, so if there should
* be a space, the parameter value will need to have it at the end.
* Useful for when the template only needs to display the month and year,
* if either are available. The prefix does not automatically place a space
* between the prefix, so if there should be a space, the parameter value
* will need to have it at the end.
*
* @since 0.71
*