January is Theme Month

In January 2009 I will be concentrating on themes and themeing.

Got a theme question, or conundrum? Let me know.

WordPress Shortcodes: what? why? how?

WordPress 2.5 implemented a new way of inserting content into posts: shortcodes. If you haven’t had the need to use the new gallery shortcode you might not have come across the details. So, what are they?

Plugin authors have used all sorts of methods of adding codes to posts to specify where the content of their plugin should be included. Shortcodes takes this idea, and builds a standard method into WordPress.

There is one included in WordPress 2.5 by default and that is the gallery shortcode. The gallery shortcode inserts all of the images that are attached to the post into that post using one simple code that looks like this: [gallery]

Shortcodes also accept options so, for example, if you wanted to include the gallery from a different post you can specify the post id, like this: [gallery id=”6″]

The gallery shortcode also lets you specify the order of the images, the size, the way they are marked up, by default it uses a definition list, and the number of columns. You can read more about the options in the gallery shortcode at the WordPress Codex.

Shortcodes can even be used to surround text, if the plugin requires it: [code]Some text here[/code]

Shortcodes should help to bring consistency to the way plugins work, helping users to get to grips with them more easily, but also help plugin authors. There is an easy to use API that takes the work out of producing plugins that find and replace content, or even just insert it, with options.

I have used it for one plugin so far. Fun with Photo Data displays EXIF data in a list. While it wasn’t difficult to create without shortcodes, using the Shorcodes API made it easier still. For complex plugins this could be make a significant difference.

My WordPress plugin generator has been updated to include shortcode functionality and you can read more information about the Shortcodes API at the WordPress Codex.

Authors in Comments

Earlier today Miriam at WordPress Garage posted a quick challenge: how to display a list of authors who had posted in a particular category. I had an idea at the time but I wasn’t in a position to test the idea, so now I am home I have written a quick function to do just that.

The function

These two functions are best placed in your functions.php file or can be added loose to the category template file, either would be fine.

function get_authors_by_cat($cat_id, $sort = true){
 
	$author_id_array = array();
	$author_details_array = array();
 
	$cat_posts = get_posts('category='.(int) $cat_id);
 
	foreach ($cat_posts as $cat_post){
		if (!in_array($cat_post->post_author , $author_id_array)){
			$author_id_array[] = $cat_post->post_author;
			$author_details_array[] = get_userdata($cat_post->post_author);
		}
	}
 
	if ($sort === true ){
		usort($author_details_array , 'author_by_cat_sort');
	}
 
	return $author_details_array;
}
 
function author_by_cat_sort($a, $b){
        $al = strtolower($a->display_name);
        $bl = strtolower($b->display_name);
        if ($al == $bl) {
            return 0;
        }
        return ($al > $bl) ? +1 : -1;
}

There are two functions here, the first retrieves all the posts from the category and loops through them to make sure. The second function is a callback for the usort function. This allows the list to be sorted by the display name of the authors.

This could be done more efficiently by querying the database directly but I wanted to avoid that option as a lot of people are not comfortable doing that themselves.

Using the Function

To use the function in your theme you need to include the following in your where you want the list to appear (replacing the number 18 with the ID of the category that you want to list authors for.

<?php
 
$authordata_array = get_authors_by_cat(18, $sort = true);
foreach ($authordata_array as $authordata){
?>
 
	<?php the_author(); ?>
	<?php the_author_posts_link (); ?>
 
<?php
}
 
?>

Notice that in the foreach loop you should be able to use the normal author based template tags. You can find a list at http://codex.wordpress.org/Template_Tags

Controlling Archives

If you want to display a list of archive links in WordPress the way you do it is with the template tag: wp_get_archives. But what if you want a little more control?

Unlike bookmarks and categories there doesn’t seem to be a quick and easy way to retrieve an array of archive links as an array for later use. So what do you do if you want a list of archives exactly the same as that generated from the code below, but you want to insert something else into that list?

<?php wp_get_archives('type=monthly&limit=12'); ?>

WordPress has three functions that make it much easier to generate lists of archives manually:

  • get_day_link( $day , $month , $year );
  • get_month_link( $month , $year );
  • get_year_link( $year );

These functions each return the appropriate permalink for the date provided to them. All you need to do is to calculate the dates you want to include.

The code snippet below shows the links for this and the previous 11 months and adds a class (selected) to the list item if the page it is displayed on is an archive from the month and year selected.

for ($i = 0; $i < 12; $i++){
 
	$the_date = mktime(0, 0, 0, date("m")-$i, date("d"),   date("Y"));
	$year = date("Y", $the_date );
	$month = date("m", $the_date);
	$selected_class = '';
 
	if ( $wp_query->get('monthnum') == $month && $wp_query->get('year') == $year ){
		$selected_class = ' class="selected" ';
	}
 
	echo '<li'.$selected_class.'>';
	echo '<a href="'.get_month_link($year, $month).'">'.date('F Y',$the_date).'</a>';
	echo '</li>';
 
}

This can be amended in a variety of ways to add extra functionality to a theme, including paging, listing posts inline, and even combining with Javascript to produce a dynamic menu of years, months and days.

Testing on Mulitple Versions

I’ve had a dilemma for a little while. I’m developing a theme that I wanted to test on multiple local versions of WordPress, but copying it between directories seemed to be a bit painful, as does stopping and starting Apache each time I want to re-test. I have finally found a pretty workable solution: Use the same themes folder for every installation of WordPress. Here’s how I’ve done it.

Note: If you haven’t already installed a local version of WordPress this post possibly isn’t for you. I suggest reading these first: Installing WordPress Locally Part 1 - Installing WordPress Locally Part 2

Two Instances of Apache

First I have created a folder for each WordPress installation, unzipped the versions (in my case 2.3.2 and 2.5), created a separate database schema for each in Mysql and completed the WordPress config files to point the right schema.

Second, I have created multiple Apache config files and shortcuts. The config file (on Windows at least) by default is called httpd.conf. The lines that differ in each config file are:

...
Listen 8080 (Change the port to anything different)
...
ServerName locahost:8080 (the port number should match the first change above)
...
DocumentRoot "C:\wordpress" (point to the folder where the installation can be found)
...

To create a new shortcut (again Windows only. If a Mac / Linux fan can give some advice in the comments it would be much appreciated) find the shortcut file, there is often one in the start menu, under Apache, labelled ‘Start Apache in Console’ and copy it. Right click on it and select properties. The target field will have the path to the original conf file in it, it will be something like:

…”C:\Program Files\Apache Group\Apache2\conf\httpd.conf”…

Change only this part of the target, there will be other paths in there but only this one should be changed to point to your new conf file.

You should now be able to run two, or more, instances of Apache side by side by using these shortcuts.

Redirect WordPress to one Themes Folder

Once you have all the versions of WordPress up and running you will need a very simple plugin to tell WordPress to look in a different folder for themes:

add_filter('theme_root' , 'theme_root_intercept');
 
function theme_root_intercept($root){
	return "C:\favewordpressinst/wp-content/themes";
}

This intercepts the request for the theme folder and gives it the one you want it to use. Just change the path to suit you.

Redirect the Browser

Finally, we need to redirect any browser requests by adding the following line (suitably amended ) to you .htaccess file:

RewriteRule ^wp-content/themes/(.*)$ http://localhost:8080/wp-content/themes/$1 [L]

If you are using permalinks this will need to be above the rewrite conditions.

What about plugins?

There doesn’t seem to be similar filter for plugins so it is does involve making a minor edit to a core file.

WordPress uses two constants to find the plugin path, ABSPATH which you can’t really mess with, and PLUGINDIR which you can. You can change it in wp-settings.php which is in the main folder. Because it will have the current ABSPATH added on front you will need to make this come back up enough directories to find the one you need; for example:

define('PLUGINDIR', '../wordpress-svn/wp-content/plugins');

You will also need a similar .htaccess directive, but relating to the plugins directory instead.

I haven’t had much time to test this yet so treat it with caution and don’t link to any data you want to keep.

 Page 1 of 5  1  2  3  4  5 »