Post Formats in WordPress: Breaking Down Those Quotes

Here’s a function that would grab the contents HTML and parse out the first quote (blockquote element) together with it’s cite (usually the quote author) and the remaining text that comes after the quote. This is useful for when dealing with the quote post format in WordPress.

function get_blockquote() {
    $dom = new DOMDocument;
    $dom->loadHTML( apply_filters( 'the_content', get_the_content( '' ) ) );
    $blockquotes = $dom->getElementsByTagname( 'blockquote' );

    if ( $blockquotes->length > 0 ) {

        // First blockquote
        $blockquote = $blockquotes->item(0);

        $cite = $blockquote->getElementsByTagName( 'cite' )->item( 0 );
        $p = $blockquote->getElementsByTagName( 'p' );

        $cite_content = '';
        if ( $cite && $p ) {

            // Remove the cite from the paragraph
            foreach ( $p as $paragraph )
                try { $paragraph->removeChild( $cite ); }
                catch( Exception $e ) {}

            $cite_content = $dom->saveXML( $cite );
        }

        $blockquote_content = '';
        foreach ( $p as $paragraph ) {
            if ( strlen( trim( $paragraph->nodeValue ) ) > 0 )
                $blockquote_content .= $dom->saveXML( $paragraph );
            else
                $paragraph->parentNode->removeChild( $paragraph );

        $blockquote->parentNode->removeChild( $blockquote );
        $remaining_content = $dom->saveXML();
    }
    return $blockquote_content; // $cite_content or $remaining_content
}

As you can see you have an option of returning the quote contents, the author contents or the stuff that’s not related to the first quote. You can also bundle all three of them in an array if needed. Anyways, as I said, this might come useful when dealing with the quote post format in WordPress.

Quote post format in WordPress

We’ve got a great example on Theme.fm and the best part is that you don’t need to change the way you write quotes and since you’ve got the quote content, the author and the rest of the content as separate entities, you can style your first (main) quote however you like.

This continues my discussion on Tumblr-like Post Formats by Alex King and Crowd Favorite. And obviously the code snippet can be improved, but hey, who needs regular expressions? ;)

Encode Entities Inside PRE Tags

Here’s a little Python script that searches through a given file for pre tags and encodes anything in between. This is useful for when escaping from syntax highlighting plugins and replacing every occurrence of the code shortcode with a pre tag.

import re, sys

# First argument is the filename, output is filename.encoded
filename = sys.argv[1]
f = file(filename)
output = open('%s.encoded' % filename, 'w+');

# Read the whole file, fire the regular expressions
contents = f.read()
expr = re.compile(r'<pre>(.*?)</pre>', re.MULTILINE|re.DOTALL)
matches = expr.findall(contents)

# Loop through each match and replace < > with &lt; and &gt;
for match in matches:
	contents = contents.replace(match, match.replace('<', '&lt;').replace('>', '&gt;'));

# Write output file and close both files
output.write(contents)
output.close()
f.close()

Most syntax highlighting plugins will encode all entities on the fly for you so when you stop using them your code might break. Also, most highlighting plugins will render your TinyMCE visual editor useless when working with code, and I think it’s quite common to work with code using the visual editor in WordPress. At least Twenty Ten and Twenty Eleven understand that ;)

However, as seen from the replacement part, I don’t really encode all entities but rather replace the greater than and less than symbols. It’s enough for most cases but if you need a real entity encoding you should use the cgi.escape function which is similar to htmlspecialchars in php.

Feed this script with your database dump and it’ll create a new file with an .encoded prefix which you can feed back to MySQL. Please note though that this script reads the entier input file which may lead to slow execution, high memory usage and swapping when working with large files. Worked fine on my 30 megabyte database though.

How To: List Filters That You Are About to Apply

I was working on a project where I had to find out all the registered filters that I was about to apply, so here’s a WordPress quickie for you! I found this out by inspecting the apply_filters function inside the plugin.php core file, and apparently there’s a $wp_filter global that contains them all in an associative array where keys are tags.

So by doing a print_r at a certain time in your theme or function, you’re able to find out the whole list, but you might as well filter to the hook that you’re looking for. As an example let’s take “comment_text” as the filter tag and list all it’s callbacks — i.e. let’s find out what filters are applied to the comment text before we print it out. Note that this has to run at a point where the filters have already been added, probably before a call to the comment_text() function.

 global $wp_filter;
 print_r( $wp_filter['comment_text'] );

This may seem pretty useless at first sight, but did you know that the comment_text is passed through wptexturize, convert_chars, make_clickable, convert_smilies and several other filters? I didn’t, and I used this trick to find out, which lead me to the make_clickable function which I was looking for in the first place ;)

If you’re wondering what the array keys are in the array that you’ve printed, those are the priorities which were passed (or defaulted) when calling add_filter.

I hope this turns out to be useful to somebody, so thanks for retweeting!

A Thought on WordPress Page Templates

WordPress Page TemplatesI was looking into more premium themes for WordPress the other day, and I see that most of them simply love to give users different page templates. Not all of them are doing it the correct way, but it still is a value add to a WordPress theme.

If you recall from the Codex pages, Page Templates in WordPress are defined with a special comment header in the template files. They can then be chosen at the Edit Page screen from within the WordPress admin area and the chosen template will be used instead of the standard page.php (or other fallback). So today I was playing around with that, and thought that it’d be nice if page templates actually showed the way they look before I’m applying them, at least schematically.

So I fired up my image editor and came up with this screenshot (on the right). Of course you can simply select a page template and then hit the preview button before publishing, and that works most of the times, but what if there are ten or twenty page templates defined by the theme? The template names I’ve seen aren’t too descriptive, then again, there isn’t much space there for that, so an extra description field would definitely be cool. A schematic representation would clearly show what the template looks like, if it has got any sidebars on the right, top, bottom? Or maybe an icon representing a specific logic behind the template. A grid of blocks for “Portfolio Page” for example.

That now makes me thing that post formats can have icon representations too, look at Tumblr! And the WordPress design team has a great taste, according to the icon set in the admin area ;)

I actually ran a short experiment and found a great function called get_page_templates (thank you @nacin!) which returns an array of the available page templates associated with the currently running theme. Below is the draft code that I came up with, it basically lists all the page templates available together with the URLs to their images. Description can be added same way.

$templates = get_page_templates();
$base = trailingslashit( get_stylesheet_directory() );

foreach ( $templates as $template_name => $template_file ) {
    $template_data = implode( '', file( $base . $template_file ) );
    $template_image = '';

    if ( preg_match( '|Template Image:(.*)$|mi', $template_data, $template_image ) );
         $template_image = trim( $template_image[1] );

    if ( $template_image )
        $template_image = trailingslashit( get_stylesheet_directory_uri() ) . $template_image;

    echo "Template Name: {$template_name}<br />Template Image: {$template_image}";
}

This could be used inside a new (or the existing) meta box on the Edit Page screen, and with a few more lines of code and some javascript magic, we can override the default functionality. But do we need to?

Right, do we need to? I know that you, my friends, are more techy than just WordPress users, but think about the normal people for a second. Would this be an easier way to access and work with Page Templates in WordPress? Or does this just make it even more complicated than it already is? Thank you for your input and retweets!

Snippet: Using jQuery 1.5 in WordPress

Yes! jQuery 1.5 was released and I’m sure some of you can’t wait to start using it in their WordPress themes and plugins. So, with a few filters magic, we can get jQuery 1.5 up and running. Add the following code to your theme’s function.php file:

add_filter( 'script_loader_src', 'my_script_loader_src', 10, 2 );
function my_script_loader_src( $src, $handle ) {
    if ( $handle == "jquery" )
        return "http://code.jquery.com/jquery-1.5.min.js";
    return $src;
}

And that’s it! Now every call to wp_enqueue_script jquery will pass through this filter and load up 1.5 instead of the one shipped with your WordPress bundle. Feel free to change the URL of the jQuery script to different CDNs including Microsoft’s and Google’s.

I guess this post will be outdated upon the next WordPress release, but it still may be valuable, since the same trick is used to run jQuery and other libraries shipped with WordPress from different sources like Google or Amazon CloudFront.

Snippet: A "Feed Only" Shortcode for WordPress

This might be valuable for banner ads, pitches to get people on to your website rather than simply reading stuff in their RSS feeds. You can address your RSS subscribers differently in each and every post, just by using this WordPress shortcode trick!

I’m not and ad-guy myself and I don’t care much if people read my feed or browse my website, as long as they’re reading my content. But I do know that some of you own websites that are driven by adverts and that’s good. Giving not full content but excerpts in your RSS feeds is one way to solve the problem, but that annoys most people including myself.

With this shortcode trick, you’ll be able to squeeze content into your posts that will be displayed in your feeds only. And by extending this example with a few extra lines, you’ll be able to do the same thing but the other way round — hide certain parts of your content in your RSS feed. Combining the two you might be able to give the full post content, where for instance the download link is visible to people on your website, while people reading your RSS feed get a different message, like “download available from this website”.

On to the code (for functions.php)!

function feedonly_shortcode( $atts, $content = null) {
	if (!is_feed()) return "";
	return $content;
}
add_shortcode('feedonly', 'feedonly_shortcode');

Once that is done, go ahead and create a new post, write some content, and then add:

... some content ...
[feedonly]Dear RSS readers, I'd really appreciate if you you came to <a href="http://yourwebsite.com">my website</a> and clicked a few banner ads ;)[/feedonly]

When you publish that you won’t see the text between the feedonly short codes on your website, but you will if you open up your RSS feed.

I believe this is a more intelligent and interactive way to speak to your RSS subscribers, rather than just sticking banners at the top/bottom of each feed entry, which don’t get clicked anyway ;) Hope this gets you closer to your feed readers, and please don’t annoy them too much ;)

Thank you for reading!

Using Google's URL Shortener (goo.gl) in WordPress

The Google URL Shortener API has been released this week so I came up with a short snippet that generates short goo.gl URLs. The script is quite simple, you can paste it in your theme’s functions.php file or create a plugin out of it, so without further ado:

function googl_shortlink($url, $post_id) {
	global $post;
	if (!$post_id && $post) $post_id = $post->ID;

	if ($post->post_status != 'publish')
		return "";

	$shortlink = get_post_meta($post_id, '_googl_shortlink', true);
	if ($shortlink)
		return $shortlink;

	$permalink = get_permalink($post_id);

	$http = new WP_Http();
	$headers = array('Content-Type' => 'application/json');
	$result = $http->request('https://www.googleapis.com/urlshortener/v1/url', array( 'method' => 'POST', 'body' => '{"longUrl": "' . $permalink . '"}', 'headers' => $headers));
	$result = json_decode($result['body']);
	$shortlink = $result->id;

	if ($shortlink) {
		add_post_meta($post_id, '_googl_shortlink', $shortlink, true);
		return $shortlink;
	}
	else {
		return $url;
	}
}

add_filter('get_shortlink', 'googl_shortlink', 9, 2);

For the tech people I’ll explain what I’m trying to do here. So first of all we don’t want to shorten links on draft posts as that could be a waste of resources, so we return an empty string. The magic with get_post_meta and add_post meta in the middle and at the end of the function are done for caching purposes — we don’t want to send too many requests to the Google API so let’s keep the already shortened links in the post’s custom fields. This may be annoying in the UI so you might want to add an underscore in the meta key (“_googl_shortlink”) which will make it invisible to the UI.

Next up, I retrieve the permalink of the published post, since we don’t want to shorten an already shortened URL which is that ugly one by WordPress. I use that permalink in an HTTP request to Google’s API using WordPress’ WP_Http object. Note that I’ve added the Content-Type header, which is required by Google, otherwise it’ll return an error. I decode the result body using json_decode (you need PHP 5.2 or later to do this) and if there’s a valid id, which is the shortened URL, I save it to the post’s meta and return the shortlink. If something went wrong, I return the original WordPress’ short URL.

So, clicking on the “Get Shortlink” button in your admin UI will now produce a Goo.gl shortened link to your post. Neat eh? You can also use short links in your theme, somewhere in The Loop:

echo "Shortlink: " . wp_get_shortlink();

Goo.gl Analytics

Right, you might want to see your short links’ analytics at some point. Well, Goo.gl shortened links are all public and their analytics are public too, so all you have to do is browse to goo.gl/info/code where code is the 5-6 alphanumeric digits attached to your shortened URL at the end.

For convenience I wrote a little snippet that would output the short URL and a link to it’s analytics page in your posts list screen inside the admin panel. Below is the code that should go to your functions.php file or plugin file:

function googl_post_columns($columns) {
	$columns['shortlink'] = 'Shortlink';
	return $columns;
}

function googl_custom_columns($column) {
	global $post;
	if ('shortlink' == $column)
	{
		$shorturl = wp_get_shortlink();
		$shorturl_caption = str_replace('http://', '', $shorturl);
		$shorturl_info = str_replace('goo.gl/', 'goo.gl/info/', $shorturl);
		echo "<a href='{$shorturl}'>{$shorturl_caption}</a> (<a href='{$shorturl_info}'>info</a>)";
	}
}

add_action('manage_posts_custom_column', 'googl_custom_columns');
add_filter('manage_edit-post_columns', 'googl_post_columns');

I wrote about custom columns in a post called Custom Post Types in WordPress 3.0, which should give you a general idea of what’s going on here. For more details visit the WordPress Codex.

That’s about it! Yeah, I know there’s some stuff that can be improved here, like smooth error handling, but it’s up to you to implement it. For more info check out the Google URL Shortener Getting Started page. A good place for experiments with Google’s APIs is Google APIs Console.

The plugin-version of this code is available at the WordPress plugin directory: Goo.gl for WordPress. Thank you for reading and retweeting ;)