Category Archives: Templates

Changes and additions to template files

Theme Change

WordPress has just released 3.5 beta 1, and with it the Twenty Twelve theme. As this blog is about WordPress, it seems fitting to use it as the blog’s theme.

EDIT: Temporary change to a dark theme because of the falling snow feature 🙂

Podcast Feed

Since my site has weekly MP3 uploads, it makes sense to create a podcast feed for it. Unfortunately, those updates were implemented with custom post types, which don’t generate podcast feeds automatically with the <enclosure> tags. Thus I would have to generate a custom feed myself.

The Codex page on Customizing Feeds explains how to get a custom post type to use my own custom feed. Since I’m using a child theme, I used get_stylesheet_directory() instead of get_template_directory().

When I first setup the custom post type and imported the existing content, the meta value _wp_attached_file included the full URL. It still does as the custom insert post functions for the custom post type have been written that way. Thus to generate the path to the file (to get the filesize for the RSS feed), I had to modify the output of get_attached_file() by using the get_attached_file filter.

Using the default RSS2 template as a starting point, I modified the template to produce a feed which more or less follows the iTunes format. The major challenge was getting the filesize of the MP3 files, this was done with the PHP filesize() function.

$size = filesize( get_attached_file( $child->ID ) );

The author and subtitle fields were field with the available post meta stored with the custom post type.

A strange problem I encountered was that this worked perfectly with iTunes on my test setup, but iTunes refused to recognize the feed properly on the live site. This was solved by using feedburner, and subscribing to the feedburner feed instead. However, this still doesn’t explain what’s wrong with the feed on the actual site which prevents iTunes from getting it properly.

Adding Links

This should be an easy thing to do. I added a page and created an unordered list of links. Done!

While looking at the WordPress admin options, I noticed a section for Links. That seemed a much better way to insert links. After all, if the functionality is already built in, why write the HTML code manually?

The problem is that the collection of links only seem to be used by the built in Links widget. This will limit it to the sidebars, which isn’t what I want. I want the list to be displayed on a page.

The solution is the wp_list_bookmarks() function. Create a page template then insert that function into the template.

Create a page and set the Links template you just created as the page template. There’s no need to put anything in the content section. Populate the Links area and WordPress will do the rest.

Another advantage of this method is that the task of keeping the links list updated can now be passed over to a non technical user as the interface is pretty simple.

Adding another Custom Post Type

A new requirement came in for the site I manage. There was a need to add about 3 years worth of question and answer PDF files to the site. The nature of this was similar to the newsletters. Each post would contain a link to a PDF file. The title would hold the question, but the writing area would not be deactivated so the question could be split if it is too long.

It is very likely that there would be similar files in the future, so I decided to make this a custom post type so a non techie administrator can handle future uploads. I considered doing this as a plugin, but I’m still not sure how to include page templates as part of plugins, so I decided to just incorporate it into my custom theme, like the other post types.

The first thing to do was to register the post type using the register_post_type() function. Straightforward stuff.

In the following paragraphs, {cpt} should be replaced with the name of the post type. If the custom post type is named “Books”, loop-{cpt}.php means loop-books.php.

The loop-{cpt}.php template file is where I customize the look of each custom post type. This is where I choose what to display and how to show it. In this case, I printed the words “Download the answer: “, followed by a link to the PDF file with the answer. As this is handled by the template, the look of every post will be consistent and this will not depend on the uploader entering the proper wording into the content area.

Next came the {cpt}-template.php file. This modifies the query so it only selects posts of the custom post type I’m interested in displaying. It then calls the loop template file using get_template_part( 'loop', {cpt} ); A blank page is then created in the admin area and assigned this page template. A link is added to the menu so this page shows up in the menu system.

A single-{cpt}.php file is also created. It calls the loop template using get_template_part() as well.

I also had to edit the sidebar.php file. My sidebar shows date archives for each custom post type. Which one to show depends on which post type is currently displayed. I registered a new widget area in functions.php, then modified the if-elseif statements in the sidebar.php file so it could support new post type. To see which post type is currently displayed, the get_post_type() WordPress function is used. I can’t remember what I was previously using, but it wasn’t good enough.

Another change was to style.css. Instead of targeting each widget area by ID to make them align right and set the sidebar width, I realized I could just use the widget-area class instead.

On the admin side, a meta box had to be added. I had already done this before so it was a simple matter of copying and editing the existing code. The meta_box class described in earlier posts is flexible enough to handle this with no problems. I did make sure to look through the save() function to make sure it could support the new file name format without any unpleasant surprises.

After all these code additions, I now have a new custom post type I can use to add question and answer PDF files through the admin interface. I added the existing content manually, and will teach the administrator to upload future ones.

The new custom post type gave 404 errors when first used. I found that it was necessary to place flush_rewrite_rules() into the functions.php file as the usual method of resaving the permalinks didn’t work. However, after refreshing the page, the 404 errors went away and I could take out the flush_rewrite_rules() line. It is important to remove this line once the site works, or the site will be severely slowed by the constant regeneration of rewrite rules.

i18n

This post is on internationalization, specifically for the Chinese subsite. Those who have been following along will know that I have a custom post type for newsletters, and that this is displaying a link to the PDF file to be downloaded by getting the URL from the _wp_attached_file meta value. For the English version, it displays some text before the link (“Download MM: “). Obviously, this text should be in Chinese for the Chinese subsite. Looks like internationalization is a good way to achieve this.

Declare Theme Text Domain

Put this on top of the functions.php file.

load_theme_textdomain('theme_name', STYLESHEETPATH . '/languages');

Mark String as Translatable

The next step is to mark the ‘Download MM’ string as something to be translated. This is done by putting it in a special function __()

__( 'Download MM', 'theme_name' )

poEdit

This is a program which will get all the translatable strings out of the source code and create a .po file. It also provides an interface for supplying the translation and automatically generates the .mo file.

Rename Files

The final step is to copy the .po and .mo files to the theme’s languages folder (newly created). It is also necessary to rename them to zh_CN.mo and zh_CN.po so that the translated string would get picked up correctly.

Resources Used

The link on the WordPress Codex to the guides on the Urban Giraffe are excellent.
http://urbangiraffe.com/articles/translating-wordpress-themes-and-plugins/
http://urbangiraffe.com/articles/localizing-wordpress-themes-and-plugins/

Additional Widget Areas

In my theme, the sidebar is filled populated by using widgets. It would make sense for the links there to change depending on the type of content in the main window. If sermons are shown, then links for speakers, themes and sermon archives should be displayed. If it is newsletters, then categories and newsletter archives should be shown. For pages, a list of all the pages should be displayed. This was accomplished by adding more widget areas to the theme, then displaying the relevant widget area depending on what the main content is.

Adding Widget Areas

First, remove the existing action to initialize the default twenty ten widgets. The twenty ten function will be called later.

remove_action('widgets_init', 'twentyten_widgets_init');

Write a new function to call the default twenty ten widget function, and add the extra code for the additional widget areas.

function mbpc_widgets_init() {
	twentyten_widgets_init();

	// Area 3, will show up when certain conditions are met, see sidebar.php 
	register_sidebar( array(
		'name' => __( 'Third Widget Area', 'twentyten' ),
		'id' => 'third-widget-area',
		'description' => __( 'The third widget area', 'twentyten' ),
		'before_widget' => '<li id="%1$s" class="widget-container %2$s">',
		'after_widget' => '</li>>,
		'before_title' => '<h3 class="widget-title">',
		'after_title' => '</h3>',
	) );

	// Area 4, will show up when certain conditions are met, see sidebar.php 
	register_sidebar( array(
		'name' => __( 'Fourth Widget Area', 'twentyten' ),
		'id' => 'fourth-widget-area',
		'description' => __( 'The fourth widget area', 'twentyten' ),
		'before_widget' => '<li id="%1$s" class="widget-container %2$s">',
		'after_widget' => '</li>',
		'before_title' => '<h3 class="widget-title">',
		'after_title' => '</h3>',
	) );

}

Hook the function onto the widgets_init action.

add_action('widgets_init', 'mbpc_widgets_init');

There will now be additional widget areas which can be customized from the admin interface.

Loading Sidebars

This is relatively easy. WordPress already has the functions to check if a sidebar is active and to include it in a theme. In fact, it’s all there in the existing sidebar.php code. Use the is_active_sidebar('widget-name'); and dynamic_sidebar('widget-name'); functions.

Conditional Widgets

At each point in the code where a widget is loaded, there is a conditional check. To check for custom post types, use is_post_type_archive('cpt-name');. To check if it’s a custom taxonomy, is_tax(). For page templates, is_page_template('template-name.php');

By modifying the conditions to check for categories, pages, etc, I could choose a widget to display depending on the main content.

Add the Widgets

Now go into the admin interface and setup the widgets!

Built in Categories with Custom Post Types

How to do that is covered in detail in this post on adding a new custom post type.

However, view by category doesn’t work by default with custom post types. This is because the query doesn’t cater for it, thus I had to override category.php and modify the query.

Copy category.php from the twenty ten theme and paste it in my own theme folder. Add the following code before the loop is called.

global $wp_query;
$args = array_merge($wp_query>query,array('post_type'=>array('post','newsletter'),'paged'=>get_query_var('paged')));
query_posts($args);

This file has also been modified the call the custom loop for newsletters because that post type will have some extra meta data for display.