*
* Care should be taken to protect the email address and assure that email
* harvesters do not capture your commentors' email address. Most assume that
- * their email address will not appear in raw form on the blog. Doing so will
+ * their email address will not appear in raw form on the site. Doing so will
* enable anyone, including those that people don't want to get the email
* address and use it for their own means good and bad.
*
*
* Care should be taken to protect the email address and assure that email
* harvesters do not capture your commentors' email address. Most assume that
- * their email address will not appear in raw form on the blog. Doing so will
+ * their email address will not appear in raw form on the site. Doing so will
* enable anyone, including those that people don't want to get the email
* address and use it for their own means good and bad.
*
*
* Care should be taken to protect the email address and assure that email
* harvesters do not capture your commentors' email address. Most assume that
- * their email address will not appear in raw form on the blog. Doing so will
+ * their email address will not appear in raw form on the site. Doing so will
* enable anyone, including those that people don't want to get the email
* address and use it for their own means good and bad.
*
* If the default page displays the oldest comments, the permalinks for comments on the default page
* do not need a 'cpage' query var.
*/
- $default_comments_page = get_option( 'default_comments_page' );
if ( 'oldest' === get_option( 'default_comments_page' ) && 1 === $cpage ) {
$cpage = '';
}
* default theme. If either does not exist, then the WordPress process will be
* halted. It is advised for that reason, that the default theme is not deleted.
*
- * @uses $withcomments Will not try to get the comments if the post has none.
+ * Will not try to get the comments if the post has none.
*
* @since 1.5.0
*
* @global int $user_ID
* @global string $user_identity
* @global bool $overridden_cpage
+ * @global bool $withcomments
*
* @param string $file Optional. The file to load. Default '/comments.php'.
* @param bool $separate_comments Optional. Whether to separate the comments by comment type.
'order' => 'ASC',
'status' => 'approve',
'post_id' => $post->ID,
- 'hierarchical' => 'threaded',
'no_found_rows' => false,
'update_comment_meta_cache' => false, // We lazy-load comment meta for performance.
);
+ if ( get_option('thread_comments') ) {
+ $comment_args['hierarchical'] = 'threaded';
+ } else {
+ $comment_args['hierarchical'] = false;
+ }
+
if ( $user_ID ) {
$comment_args['include_unapproved'] = array( $user_ID );
} elseif ( ! empty( $comment_author_email ) ) {
'count' => true,
'orderby' => false,
'post_id' => $post->ID,
- 'parent' => 0,
'status' => 'approve',
);
+ if ( $comment_args['hierarchical'] ) {
+ $top_level_args['parent'] = 0;
+ }
+
if ( isset( $comment_args['include_unapproved'] ) ) {
$top_level_args['include_unapproved'] = $comment_args['include_unapproved'];
}
}
}
+ /**
+ * Filters the arguments used to query comments in comments_template().
+ *
+ * @since 4.5.0
+ *
+ * @see WP_Comment_Query::__construct()
+ *
+ * @param array $comment_args {
+ * Array of WP_Comment_Query arguments.
+ *
+ * @type string|array $orderby Field(s) to order by.
+ * @type string $order Order of results. Accepts 'ASC' or 'DESC'.
+ * @type string $status Comment status.
+ * @type array $include_unapproved Array of IDs or email addresses whose unapproved comments
+ * will be included in results.
+ * @type int $post_id ID of the post.
+ * @type bool $no_found_rows Whether to refrain from querying for found rows.
+ * @type bool $update_comment_meta_cache Whether to prime cache for comment meta.
+ * @type bool|string $hierarchical Whether to query for comments hierarchically.
+ * @type int $offset Comment offset.
+ * @type int $number Number of comments to fetch.
+ * }
+ */
+ $comment_args = apply_filters( 'comments_template_query_args', $comment_args );
$comment_query = new WP_Comment_Query( $comment_args );
$_comments = $comment_query->comments;
// Trees must be flattened before they're passed to the walker.
- $comments_flat = array();
- foreach ( $_comments as $_comment ) {
- $comments_flat[] = $_comment;
- $comment_children = $_comment->get_children( array(
- 'format' => 'flat',
- 'status' => $comment_args['status'],
- 'orderby' => $comment_args['orderby']
- ) );
-
- foreach ( $comment_children as $comment_child ) {
- $comments_flat[] = $comment_child;
+ if ( $comment_args['hierarchical'] ) {
+ $comments_flat = array();
+ foreach ( $_comments as $_comment ) {
+ $comments_flat[] = $_comment;
+ $comment_children = $_comment->get_children( array(
+ 'format' => 'flat',
+ 'status' => $comment_args['status'],
+ 'orderby' => $comment_args['orderby']
+ ) );
+
+ foreach ( $comment_children as $comment_child ) {
+ $comments_flat[] = $comment_child;
+ }
}
+ } else {
+ $comments_flat = $_comments;
}
/**
*/
$wp_query->comments = apply_filters( 'comments_array', $comments_flat, $post->ID );
- // Set up lazy-loading for comment metadata.
- add_action( 'get_comment_metadata', array( $wp_query, 'lazyload_comment_meta' ), 10, 2 );
-
$comments = &$wp_query->comments;
$wp_query->comment_count = count($wp_query->comments);
$wp_query->max_num_comment_pages = $comment_query->max_num_pages;
}
/**
- * Display the JS popup script to show a comment.
- *
- * If the $file parameter is empty, then the home page is assumed. The defaults
- * for the window are 400px by 400px.
- *
- * For the comment link popup to work, this function has to be called or the
- * normal comment link will be assumed.
- *
- * @global string $wpcommentspopupfile The URL to use for the popup window.
- * @global int $wpcommentsjavascript Whether to use JavaScript. Set when function is called.
- *
- * @since 0.71
- *
- * @param int $width Optional. The width of the popup window. Default 400.
- * @param int $height Optional. The height of the popup window. Default 400.
- * @param string $file Optional. Sets the location of the popup window.
- */
-function comments_popup_script( $width = 400, $height = 400, $file = '' ) {
- global $wpcommentspopupfile, $wpcommentsjavascript;
-
- if (empty ($file)) {
- $wpcommentspopupfile = ''; // Use the index.
- } else {
- $wpcommentspopupfile = $file;
- }
-
- $wpcommentsjavascript = 1;
- $javascript = "<script type='text/javascript'>\nfunction wpopen (macagna) {\n window.open(macagna, '_blank', 'width=$width,height=$height,scrollbars=yes,status=yes');\n}\n</script>\n";
- echo $javascript;
-}
-
-/**
- * Displays the link to the comments popup window for the current post ID.
- *
- * Is not meant to be displayed on single posts and pages. Should be used
- * on the lists of posts
- *
- * @global string $wpcommentspopupfile The URL to use for the popup window.
- * @global int $wpcommentsjavascript Whether to use JavaScript. Set when function is called.
+ * Displays the link to the comments for the current post ID.
*
* @since 0.71
*
* Default false.
*/
function comments_popup_link( $zero = false, $one = false, $more = false, $css_class = '', $none = false ) {
- global $wpcommentspopupfile, $wpcommentsjavascript;
-
$id = get_the_ID();
$title = get_the_title();
$number = get_comments_number( $id );
}
echo '<a href="';
- if ( $wpcommentsjavascript ) {
- if ( empty( $wpcommentspopupfile ) )
- $home = home_url();
- else
- $home = get_option('siteurl');
- echo $home . '/' . $wpcommentspopupfile . '?comments_popup=' . $id;
- echo '" onclick="wpopen(this.href); return false"';
+ if ( 0 == $number ) {
+ $respond_link = get_permalink() . '#respond';
+ /**
+ * Filter the respond link when a post has no comments.
+ *
+ * @since 4.4.0
+ *
+ * @param string $respond_link The default response link.
+ * @param integer $id The post ID.
+ */
+ echo apply_filters( 'respond_link', $respond_link, $id );
} else {
- // if comments_popup_script() is not in the template, display simple comment link
- if ( 0 == $number ) {
- $respond_link = get_permalink() . '#respond';
- /**
- * Filter the respond link when a post has no comments.
- *
- * @since 4.4.0
- *
- * @param string $respond_link The default response link.
- * @param integer $id The post ID.
- */
- echo apply_filters( 'respond_link', $respond_link, $id );
- } else {
- comments_link();
- }
- echo '"';
+ comments_link();
}
+ echo '"';
if ( !empty( $css_class ) ) {
echo ' class="'.$css_class.'" ';
$attributes = '';
/**
- * Filter the comments popup link attributes for display.
+ * Filter the comments link attributes for display.
*
* @since 2.5.0
*
- * @param string $attributes The comments popup link attributes. Default empty.
+ * @param string $attributes The comments link attributes. Default empty.
*/
echo apply_filters( 'comments_popup_link_attributes', $attributes );
*
* Only affects users with JavaScript disabled.
*
+ * @internal The $comment global must be present to allow template tags access to the current
+ * comment. See https://core.trac.wordpress.org/changeset/36512.
+ *
* @since 2.7.0
*
+ * @global WP_Comment $comment Current comment.
+ *
* @param string $noreplytext Optional. Text to display when not replying to a comment.
* Default false.
* @param string $replytext Optional. Text to display when replying to a comment.
* to their comment. Default true.
*/
function comment_form_title( $noreplytext = false, $replytext = false, $linktoparent = true ) {
- $comment = get_comment();
+ global $comment;
if ( false === $noreplytext ) $noreplytext = __( 'Leave a Reply' );
if ( false === $replytext ) $replytext = __( 'Leave a Reply to %s' );
if ( 0 == $replytoid )
echo $noreplytext;
else {
+ // Sets the global so that template tags can be used in the comment form.
$comment = get_comment($replytoid);
$author = ( $linktoparent ) ? '<a href="#comment-' . get_comment_ID() . '">' . get_comment_author( $comment ) . '</a>' : get_comment_author( $comment );
printf( $replytext, $author );
*/
$r = apply_filters( 'wp_list_comments_args', $r );
- /*
- * If 'page' or 'per_page' has been passed, and does not match what's in $wp_query,
- * perform a separate comment query and allow Walker_Comment to paginate.
- */
- if ( is_singular() && ( $r['page'] || $r['per_page'] ) ) {
- $current_cpage = get_query_var( 'cpage' );
- if ( ! $current_cpage ) {
- $current_cpage = 'newest' === get_option( 'default_comments_page' ) ? 1 : $wp_query->max_num_comment_pages;
- }
-
- $current_per_page = get_query_var( 'comments_per_page' );
- if ( $r['page'] != $current_cpage || $r['per_page'] != $current_per_page ) {
- $comments = get_comments( array(
- 'post_id' => get_queried_object_id(),
- 'orderby' => 'comment_date_gmt',
- 'order' => 'ASC',
- 'status' => 'all',
- ) );
- }
- }
-
// Figure out what comments we'll be looping through ($_comments)
if ( null !== $comments ) {
$comments = (array) $comments;
$_comments = $comments;
}
} else {
- if ( empty($wp_query->comments) )
- return;
- if ( 'all' != $r['type'] ) {
- if ( empty($wp_query->comments_by_type) )
- $wp_query->comments_by_type = separate_comments($wp_query->comments);
- if ( empty($wp_query->comments_by_type[$r['type']]) )
- return;
- $_comments = $wp_query->comments_by_type[$r['type']];
- } else {
- $_comments = $wp_query->comments;
- }
+ /*
+ * If 'page' or 'per_page' has been passed, and does not match what's in $wp_query,
+ * perform a separate comment query and allow Walker_Comment to paginate.
+ */
+ if ( $r['page'] || $r['per_page'] ) {
+ $current_cpage = get_query_var( 'cpage' );
+ if ( ! $current_cpage ) {
+ $current_cpage = 'newest' === get_option( 'default_comments_page' ) ? 1 : $wp_query->max_num_comment_pages;
+ }
+
+ $current_per_page = get_query_var( 'comments_per_page' );
+ if ( $r['page'] != $current_cpage || $r['per_page'] != $current_per_page ) {
+
+ $comments = get_comments( array(
+ 'post_id' => get_the_ID(),
+ 'orderby' => 'comment_date_gmt',
+ 'order' => 'ASC',
+ 'status' => 'all',
+ ) );
+
+ if ( 'all' != $r['type'] ) {
+ $comments_by_type = separate_comments( $comments );
+ if ( empty( $comments_by_type[ $r['type'] ] ) ) {
+ return;
+ }
- // Pagination is already handled by `WP_Comment_Query`, so we tell Walker not to bother.
- if ( $wp_query->max_num_comment_pages ) {
- $default_comments_page = get_option( 'default_comments_page' );
- $cpage = get_query_var( 'cpage' );
- if ( 'newest' === $default_comments_page ) {
- $r['cpage'] = $cpage;
+ $_comments = $comments_by_type[ $r['type'] ];
+ } else {
+ $_comments = $comments;
+ }
+ }
- // When first page shows oldest comments, post permalink is the same as the comment permalink.
- } elseif ( $cpage == 1 ) {
- $r['cpage'] = '';
+ // Otherwise, fall back on the comments from `$wp_query->comments`.
+ } else {
+ if ( empty($wp_query->comments) )
+ return;
+ if ( 'all' != $r['type'] ) {
+ if ( empty($wp_query->comments_by_type) )
+ $wp_query->comments_by_type = separate_comments($wp_query->comments);
+ if ( empty($wp_query->comments_by_type[$r['type']]) )
+ return;
+ $_comments = $wp_query->comments_by_type[$r['type']];
} else {
- $r['cpage'] = $cpage;
+ $_comments = $wp_query->comments;
}
- $r['page'] = 0;
- $r['per_page'] = 0;
+ if ( $wp_query->max_num_comment_pages ) {
+ $default_comments_page = get_option( 'default_comments_page' );
+ $cpage = get_query_var( 'cpage' );
+ if ( 'newest' === $default_comments_page ) {
+ $r['cpage'] = $cpage;
+
+ /*
+ * When first page shows oldest comments, post permalink is the same as
+ * the comment permalink.
+ */
+ } elseif ( $cpage == 1 ) {
+ $r['cpage'] = '';
+ } else {
+ $r['cpage'] = $cpage;
+ }
+
+ $r['page'] = 0;
+ $r['per_page'] = 0;
+ }
}
}
if ( null === $r['reverse_top_level'] )
$r['reverse_top_level'] = ( 'desc' == get_option('comment_order') );
+ wp_queue_comments_for_comment_meta_lazyload( $_comments );
+
if ( empty( $r['walker'] ) ) {
$walker = new Walker_Comment;
} else {
* @since 4.2.0 Introduced the 'submit_button' and 'submit_fields' arguments.
* @since 4.4.0 Introduced the 'class_form', 'title_reply_before', 'title_reply_after',
* 'cancel_reply_before', and 'cancel_reply_after' arguments.
+ * @since 4.5.0 The 'author', 'email', and 'url' form fields are limited to 245, 100,
+ * and 200 characters, respectively.
*
* @param array $args {
* Optional. Default arguments and form fields to override.
$html5 = 'html5' === $args['format'];
$fields = array(
'author' => '<p class="comment-form-author">' . '<label for="author">' . __( 'Name' ) . ( $req ? ' <span class="required">*</span>' : '' ) . '</label> ' .
- '<input id="author" name="author" type="text" value="' . esc_attr( $commenter['comment_author'] ) . '" size="30"' . $aria_req . $html_req . ' /></p>',
+ '<input id="author" name="author" type="text" value="' . esc_attr( $commenter['comment_author'] ) . '" size="30" maxlength="245"' . $aria_req . $html_req . ' /></p>',
'email' => '<p class="comment-form-email"><label for="email">' . __( 'Email' ) . ( $req ? ' <span class="required">*</span>' : '' ) . '</label> ' .
- '<input id="email" name="email" ' . ( $html5 ? 'type="email"' : 'type="text"' ) . ' value="' . esc_attr( $commenter['comment_author_email'] ) . '" size="30" aria-describedby="email-notes"' . $aria_req . $html_req . ' /></p>',
+ '<input id="email" name="email" ' . ( $html5 ? 'type="email"' : 'type="text"' ) . ' value="' . esc_attr( $commenter['comment_author_email'] ) . '" size="30" maxlength="100" aria-describedby="email-notes"' . $aria_req . $html_req . ' /></p>',
'url' => '<p class="comment-form-url"><label for="url">' . __( 'Website' ) . '</label> ' .
- '<input id="url" name="url" ' . ( $html5 ? 'type="url"' : 'type="text"' ) . ' value="' . esc_attr( $commenter['comment_author_url'] ) . '" size="30" /></p>',
+ '<input id="url" name="url" ' . ( $html5 ? 'type="url"' : 'type="text"' ) . ' value="' . esc_attr( $commenter['comment_author_url'] ) . '" size="30" maxlength="200" /></p>',
);
$required_text = sprintf( ' ' . __('Required fields are marked %s'), '<span class="required">*</span>' );
$fields = apply_filters( 'comment_form_default_fields', $fields );
$defaults = array(
'fields' => $fields,
- 'comment_field' => '<p class="comment-form-comment"><label for="comment">' . _x( 'Comment', 'noun' ) . '</label> <textarea id="comment" name="comment" cols="45" rows="8" aria-required="true" required="required"></textarea></p>',
+ 'comment_field' => '<p class="comment-form-comment"><label for="comment">' . _x( 'Comment', 'noun' ) . '</label> <textarea id="comment" name="comment" cols="45" rows="8" maxlength="65525" aria-required="true" required="required"></textarea></p>',
/** This filter is documented in wp-includes/link-template.php */
- 'must_log_in' => '<p class="must-log-in">' . sprintf( __( 'You must be <a href="%s">logged in</a> to post a comment.' ), wp_login_url( apply_filters( 'the_permalink', get_permalink( $post_id ) ) ) ) . '</p>',
+ 'must_log_in' => '<p class="must-log-in">' . sprintf(
+ /* translators: %s: login URL */
+ __( 'You must be <a href="%s">logged in</a> to post a comment.' ),
+ wp_login_url( apply_filters( 'the_permalink', get_permalink( $post_id ) ) )
+ ) . '</p>',
/** This filter is documented in wp-includes/link-template.php */
- 'logged_in_as' => '<p class="logged-in-as">' . sprintf( __( '<a href="%1$s" aria-label="Logged in as %2$s. Edit your profile.">Logged in as %2$s</a>. <a href="%3$s">Log out?</a>' ), get_edit_user_link(), $user_identity, wp_logout_url( apply_filters( 'the_permalink', get_permalink( $post_id ) ) ) ) . '</p>',
+ 'logged_in_as' => '<p class="logged-in-as">' . sprintf(
+ /* translators: 1: edit user link, 2: accessibility text, 3: user name, 4: logout URL */
+ __( '<a href="%1$s" aria-label="%2$s">Logged in as %3$s</a>. <a href="%4$s">Log out?</a>' ),
+ get_edit_user_link(),
+ /* translators: %s: user name */
+ esc_attr( sprintf( __( 'Logged in as %s. Edit your profile.' ), $user_identity ) ),
+ $user_identity,
+ wp_logout_url( apply_filters( 'the_permalink', get_permalink( $post_id ) ) )
+ ) . '</p>',
'comment_notes_before' => '<p class="comment-notes"><span id="email-notes">' . __( 'Your email address will not be published.' ) . '</span>'. ( $req ? $required_text : '' ) . '</p>',
'comment_notes_after' => '',
'id_form' => 'commentform',
$comment_fields = array( 'comment' => $args['comment_field'] ) + (array) $args['fields'];
/**
- * Filter the comment form fields.
+ * Filter the comment form fields, including the textarea.
*
* @since 4.4.0
*