Separating Pings from Comments in WordPress 2.7
Update: Please keep in mind that WordPress 2.7 is yet to be released. Many things will change between now and November 10, 2008. I will try to keep this post as up to date as possible as things change.
WordPress 2.7 is introducing many new features surrounding comments. Of these is AJAX commenting and threaded comments. To take advantage of the later, you must use a function wp_list_comments instead of the old way of looping through the comments array with a foreach. Weblog Tools Collection has a good how to on the old way that can be found here.
I wanted to get this hashed out before 2.7 goes live so that theme designers and anyone else can implement this in time for the release.
I’ll be referencing the default theme from 2.7 in this how to. If you are interested in adding the new commenting features to your current pre 2.7 theme see this how to by Otto.
wp_list_comments is not documented yet on the WordPress codex. But some feature that are worth mentioning are the ability to specify the comment type to display and a callback so that you can decide how to structure the output.
Let us start by taking a look at the new comments “loop”:
<?php if ( have_comments() ) : ?>
<h3 id="comments"><?php comments_number('No Responses', 'One Response', '% Responses' );?> to “<?php the_title(); ?>”</h3>
<ol class="commentlist">
<?php wp_list_comments(); ?>
</ol>
<div class="navigation">
<div class="alignleft"><?php previous_comments_link() ?></div>
<div class="alignright"><?php next_comments_link() ?></div>
</div>
<?php else : // this is displayed if there are no comments so far ?>
<?php if ('open' == $post->comment_status) : ?>
<!-- If comments are open, but there are no comments. -->
<?php else : // comments are closed ?>
<!-- If comments are closed. -->
<p class="nocomments">Comments are closed.</p>
<?php endif; ?>
<?php endif; ?>
As you can see it is much simpler than the old comments “loop”. The majority of everything that is happening is now done via the function wp_list_comments.
To remove pings (pingbacks and trackbacks) we only need to make a few small changes. First open up your themes single.php:
Find the following code:
<?php comments_template(); ?>
And change it to:
<?php comments_template('', true); ?>
The above change tells comments_template to create a global array $comments_by_type that we will use later on.
First open up comments.php.
Look for the following code:
<?php if ( have_comments() ) : ?>
Directly below this add:
<?php if ( ! empty($comments_by_type['comment']) ) : ?>
Change this:
<?php wp_list_comments(); ?>
To this:
<?php wp_list_comments('type=comment'); ?>
Directly below the wp_list_comments function we modified is:
</ol>
Directly below this add:
<?php endif; ?>
The if statement prevents the comments heading and ol tags from displaying if you only have trackbacks and pingbacks on this post.
Much easier so far, right?
To display the pings we need to insert the following code beneath the endif we just added:
<?php if ( ! empty($comments_by_type['pings']) ) : ?>
<h3 id="pings">Trackbacks/Pingbacks</h3>
<ol class="commentlist">
<?php wp_list_comments('type=pings'); ?>
</ol>
<?php endif; ?>
The comments “loop” should now look like this:
<?php if ( have_comments() ) : ?>
<?php if ( ! empty($comments_by_type['comment']) ) : ?>
<h3 id="comments"><?php comments_number('No Responses', 'One Response', '% Responses' );?> to “<?php the_title(); ?>”</h3>
<ol class="commentlist">
<?php wp_list_comments('type=comment'); ?>
</ol>
<?php endif; ?>
<?php if ( ! empty($comments_by_type['pings']) ) : ?>
<h3 id="pings">Trackbacks/Pingbacks</h3>
<ol class="commentlist">
<?php wp_list_comments('type=pings'); ?>
</ol>
<?php endif; ?>
<div class="navigation">
<div class="alignleft"><?php previous_comments_link() ?></div>
<div class="alignright"><?php next_comments_link() ?></div>
</div>
<?php else : // this is displayed if there are no comments so far ?>
<?php if ('open' == $post->comment_status) : ?>
<!-- If comments are open, but there are no comments. -->
<?php else : // comments are closed ?>
<!-- If comments are closed. -->
<p class="nocomments">Comments are closed.</p>
<?php endif; ?>
<?php endif; ?>
Now the pings are displayed below the comments. The above code will show the pings in full comment boxes. I personally like a simple ordered list with a link and title of the ping. To achieve this without a foreach (Thanks Ryan Boren for the tip!)
Open your themes functions.php file and create a callback function for wp_list_comments. The following code should be inserted:
<?php
function list_pings($comment, $args, $depth) {
$GLOBALS['comment'] = $comment;
?>
<li id="comment-<?php comment_ID(); ?>"><?php comment_author_link(); ?>
<?php } ?>
Replace this:
<ol class="commentlist">
<?php wp_list_comments('type=pings'); ?>
With this:
<ol class="pinglist">
<?php wp_list_comments('type=pings&callback=list_pings'); ?>
If your theme doesn’t have a functions.php just create it and include the above code.
In this case our full comment “loop” should now look like:
<?php if ( have_comments() ) : ?>
<?php if ( ! empty($comments_by_type['comment']) ) : ?>
<h3 id="comments"><?php comments_number('No Responses', 'One Response', '% Responses' );?> to “<?php the_title(); ?>”</h3>
<ol class="commentlist">
<?php wp_list_comments('type=comment'); ?>
</ol>
<?php endif; ?>
<?php if ( ! empty($comments_by_type['pings']) ) : ?>
<h3 id="pings">Trackbacks/Pingbacks</h3>
<ol class="pinglist">
<?php wp_list_comments('type=pings&callback=list_pings'); ?>
</ol>
<?php endif; ?>
<div class="navigation">
<div class="alignleft"><?php previous_comments_link() ?></div>
<div class="alignright"><?php next_comments_link() ?></div>
</div>
<?php else : // this is displayed if there are no comments so far ?>
<?php if ('open' == $post->comment_status) : ?>
<!-- If comments are open, but there are no comments. -->
<?php else : // comments are closed ?>
<!-- If comments are closed. -->
<p class="nocomments">Comments are closed.</p>
<?php endif; ?>
<?php endif; ?>
One last (optional) task is to modify the comment counts to only reflect the number of comments minus pings.
Open your themes functions.php and add the following code:
<?php
add_filter('get_comments_number', 'comment_count', 0);
function comment_count( $count ) {
global $id;
$comments_by_type = &separate_comments(get_comments('post_id=' . $id));
return count($comments_by_type['comment']);
}
?>
Again if your theme doesn’t have a functions.php just create it and include the above code.
There you have it. If you have any questions let me know.
Possibly Related Posts:
- Add a Class to Parent Categories Using wp_list_categories in WordPress
- Adding a Link to the WordPress 2.7 Favorites Dropdown
- Better Howdy WordPress Plugin
- Changes Coming for Shadowbox JS
- Possibly Related Recent Posts WordPress Plugin
Comments
Comment from GaMerZ
Time October 6, 2008 at 1:25 pm
I have not took a look at 2.7 codes yet, is $comments_by_type a global variable?
<?php $pings = get_comments_by_type('type=pings'); ?>
<?php foreach ($comments_by_type['pings'] as $comment) : ?>
Note the $pings instead of $comments_by_type['pings'];
Comment from Matt
Time October 6, 2008 at 1:32 pm
@GaMerZ: Looks like I had pasted in a wrong bit of code. The code has been updated to its correct values.
Comment from Nathan Rice
Time October 6, 2008 at 1:48 pm
Absolutely fantastic tutorial! I was wondering if there was going to be a function of the new comments API that would allow this to happen more easily.
I just tweeted this :-)
Comment from Matt
Time October 6, 2008 at 2:07 pm
I just updated the how to with a tip from Ryan Boren about using a callback in wp_list_comments to build the output the way that you want it.
Comment from Rahul Bansal
Time October 6, 2008 at 4:24 pm
Nice one. :-)
I hope some senior coder will create dedicated page for “wp_list_comments()” on wordpress.org Codex. Because Codex is missing a lot of docs. :-(
Comment from Matt
Time October 7, 2008 at 12:07 pm
Just updated the how to. The comments_template function now accepts an argument for separating comments.
<?php comments_template('', true); ?>
When this change is made in single.php the array $comments_by_type will be defined and will not have to be created by the theme itself.
Comment from Monika
Time November 2, 2008 at 8:29 am
Hi thanks a lot for this instructions - it saves me time ;)
I have a question: Do you know where we can translate the new comments in our language? Because I would like to have another sentence for *your comment is awaiting ….* and I would like to have this in my language German ;)
thanks
Monika
Comment from Pete
Time November 7, 2008 at 3:30 pm
Hey Matt, thanks for the info’s.
However, this doesn’t work / works strange when comment paging is enabled. All Pingbacks/Trackbacks are listed only on the first page (the page with the oldest comments). In my case, they should be on every page after the comment form. Any workaround for this?
Comment from Aeolos
Time November 11, 2008 at 7:37 pm
Same issue with Pete. The code doesn’t play nice with paged comments.
Comment from Matt
Time November 11, 2008 at 7:55 pm
@Aeolos: I’m not sure how to fix that and haven’t looked but from a comment made by Viper007Bond in #wordpress-dev today:
currently doing yet another comments overhaul. current code doesn’t work well when excluding pings or passing a custom $comments
it looks like he is aware and working on fixing this in the core code.
Comment from Aeolos
Time November 11, 2008 at 8:01 pm
Thanks for the info.
Hopefully your code will still work without modification after the fix.
Also sorry about the double comment earlier.
Trackbacks/Pingbacks
- Get Your Theme Ready for 2.7, Part 2 « planetOzh
- sivel.net has a howto on using the new c … « WordPress Development Updates
- 如何分離 Comments 與 Pings | 我的普立茲
- WordPress Theme Releases for 10/09 » Weblog Tools Collection » Blog Archive
- Separating Pings and trackbacks from Comments in WordPress 2.7
- 如何分离WordPress2.7的comments与pings | 玩WordPress
- WordPress Wednesday News: WordCamp News, WordPress 2.7, Lester Chan Plugins Famous, Super Cache Updated | The Blog Herald
- WordPress Theme Releases for 10/09 | BlogBroker24-7
- WordPress Theme Releases for 10/09 | PATRON DIGITAL.COM
- WordPress Theme Releases for 10/09 | PATRONIT.NET
- WordPress Wednesday News: WordPress 2.7 Freeze, WordPress Themes News, WordCamp Bangkok | The Blog Herald
- WordPress Theme Releases for 10/09 · Softonix.com
- WORDPRESS 2.7 DE A À Z
- WordPress Theme Releases for 09.10.08 | PATRONIT.NET
- WordPress Wednesday News: WordPress 2.7 Soon, Security Upgrade, PodCamp-WordCamp Hawaii, PollDaddy, and More | The Blog Herald
- Wordpress 2.7 le nuove api dei commenti » Archivi Blog » WordPress Italy
- WordPress 2.7 Separate 留言和样式化留言
- Comment paging in WordPress 2.7 - nkuttler
- WordPress Wednesday News: WordPress 2.7 Beta 2, Danger WordPress Faker, and More WordCamps | The Blog Herald
- WordPress 2.7 News « Lorelle on WordPress
- WP2.7 Parent Child Themes | Visual Coma
- Wordpress 2.7 Checklist
- WordPress Wednesday News: 2.7 Delayed, Sneak Peak Video, Help WordPress iPhone, WordCamps | The Blog Herald
- WordPress 2.7 News | How to Use WordPress Fast
- Blog 23r9i0 - Separar comentarios y trackback/pingback
- Blog 23r9i0 - Separar comentarios y trackback-pingback wp2.7
Comment from ChaosKaizer
Time October 6, 2008 at 11:51 am
good write up, thanks.