Codex

zh-cn:主题开发

Contents


本文介绍如何开发设计你自己的 WordPress 主题。如果你希望了解更多如何安装和应用主题的内容,请参阅应用主题文档。本文的内容不同于应用主题,因为所讨论的是编写代码去构建你自己的主题的技术内容,而非怎样去激活主题或者是哪里可以获得新主题。

为什么要开发WordPress主题

WordPress主题由一系列文件和CSS样式表构成,构成了一个美丽的WordPress网站。每个主题都是不同的, 这样WordPress用户就可以随时更改WordPress网站的外观。 你也许想为自己开发 WordPress 主题,或者制作公开发行的的主题。但是除了这个为什么要自己制作主题呢?


  • 创建自己独特的WordPress主题外观.
  • 利用模板模板标签, 和 WordPress循环 来产生不同的效果.
  • 为了产生不同的效果,比如在category pages页面和搜索结果页面产生个性的效果.
  • 为了迅速从两个主题改变你的博客外观,可以充分利用 Theme or style switcher 这个插件迅速改变外观.
  • 设计WordPress主题,这样大家就可以通过网络更好的使用你的作品.

WordPress主题有很多优点.

  • WordPress主题把CSS样式表和模板文件 从系统中独立出来,所以这样升级博客的时候就不会破坏你的主题样式.
  • 允许你自由的定制主题样式.
  • 允许你迅速改变主题.
  • 你甚至都不需要学习HTML,CSS,PHP等,即可拥有一个美观的主题.

为什么要自己制作主题呢?这才是问题的关键.

  • 这是一个学习 CSS, HTML/XHTML, 和PHP的好机会.
  • 这是一个积累你的 CSS, HTML/XHTML, PHP实践经验的的机会.
  • 制作主题的过程中充满创造力.
  • 这非常的有趣(大多数情况下).
  • 如果你 设计公共主题, 你会感觉非常好,因为你为 WordPress 社区做出了自己的贡献 (好吧,装13吧,哈哈)

主题开发标准

WordPress 主题应该按照如下标准开发:

主题的剖析

WordPress主题目录位于 wp-content/themes/。主题的目录拥有所有样式文件, 模板文件, 一些函数 (functions.php), 图片等。比如说一个叫做 "zhuti"的主题就会放在 wp-content/themes/zhuti/目录里。请避免使用数字名字,这可能会导致无法正常显示出来。

WordPress每一个发行版都会有一个默认的主题。请认真查看默认的主题,这样可能会对制作你自己的主题有帮助。

WordPress 主题除了图片和JavaScript,经常由三种文件构成.一种是样式表style.css, 控制着页面的外观. 第二个是函数(functions.php)。另一种是 模板文件,它控制着从数据库中调出的数据所呈现的外观。让我们单独看一下。

主题CSS

CSS文件不仅列出了一些主题的样式设计, style.css 必须 以注释的形式列出主题的详细信息 两个不同的主题是不允许拥有相同的表述的 , 因为这样会导致主题选择出错.如果你通过拷贝一个你已经制作的主题来制作你新的主题, 请确保现更改这些头部注释.

下面是CSS头部注释的例子,被称作style sheet header,比如主题叫做 "Twenty Ten":

/*
Theme Name: Twenty Ten
Theme URI: http://wordpress.org/
Description: The 2010 default theme for WordPress.
Author: the WordPress team
Version: 1.0 
Tags: black, blue, white, two-columns, fixed-width, custom-header, custom-background, threaded-comments, sticky-post, translation-ready, microformats, rtl-language-support, editor-style, custom-menu (optional)

General comments and license statement (optional).
*/

这些位于style.css里的文件是必须要写的,这是用来区分安装的主题.

样式表指南

  • 当创作你的CSS的时候请参考CSS coding standards
  • 尽可能使用有效地 CSS. 作为例外,也可以使用一些前缀,遵循CSS3标准.
  • 尽量减少使用CSS hacks. 明显IE是个例外,如果可能的话,将CSS hack文件区分开来或者使用独立的文件。
  • 所有的 HTML 元素应该被声明,文章页面还有评论部分。
    • Tables, captions, images, lists, block quotes, et cetera.
  • 强烈建议添加打印友好的字体
    • 你能通过使用media="print"属性来包含一个适用于打印的样式表文件,或者在你的主样式表文件中增加一部分专为打印提供的设置。

子主题

最简单的主题可能是子主题,其仅仅包含一个style.css文件,也可以加上一些图片。之所以它能工作是因为它是以另一个主题为基础进行工作的。

更多关于子主题的信息,请看Child Themes或者由op111写的不错的教材

函数文件

一个主题可以使用functions 文件,位于主题的子目录,叫做 functions.php. 这个文件就像一个插件, 如果它位于你正在使用的主题里的话, 他在你的主题初始化的时候就会自动加载(后台和前台都一样加载).对于这个文件的建议:

  • 定义你的模板使用的函数.
  • 启用缩略图功能,如职位,自定义标题和背景,和导航菜单.
  • 设置一个选项菜单,让网站拥有者可以自定义颜色,样式,和你的主题的其他特性.


默认的WordPress的主题包含一个functions.php文件,它定义这些功能很多,所以你可能会把它当做参考.既然functions.php基本上可以作为一个插件,所以Function_Reference可以让你更多的了解这个函数,以及你可以怎么利用这些函数.

模板文件

模板 是一些PHP文件,他可以输出HTML代码呈献给浏览器,决定着主题的外观.下面让我们来看一下主题的模板.

WordPress允许为你的网站定义不同的模板.他虽然不是必需的,但是这些不同的模板为你的网站添上一笔. 模板是根据Template Hierarchy的,由一个具体的主题决定.

作为一个主题开发者,你可以自由决定如何定制你的模板.比如说,极端情况下, 你甚至可以仅仅使用一个文件index.php作为模板文件,所有 页面都会使用这个模板.更多的情况是,使用不同的模板文件产生不同的结果,以达到最大定制.

模板文件列表

这里是被WordPress确认的主题文件列表.当然,你的主题可以包含任何样式表,图像或者文件.记住 下面列出的文件对WordPress有特殊的意义-- 点击Template Hierarchy 查看具体情况.

style.css
主样式表,这个文件 必须 位于你的主题里面,而且必须在头部注释处写清楚你的主题的信息.
rtl.css
rtl stylesheet. 如果网站的阅读方向是自右向左的,他会自动被包含进来. 你可以使用一个插件来生成这个文件the RTLer.
index.php
主模板.如果你的主题使用自己的模板, index.php 是必须要有的.
comments.php
评论模板.
front-page.php
The front page template, it is only used if you use a static front page.
home.php
主页模板, which is the front page by default. If you use a static front page this is the template for the page with the latest posts.
single.php
The single post template. Used when a single post is queried. For this and all other query templates, index.php is used if the query template is not present.
single-<post-type>.php
The single post template used when a single post from a custom post type is queried. For example, single-books.php would be used for displaying single posts from the custom post type books. index.php is used if the query template for the custom post type is not present.
page.php
The page template. Used when an individual Page is queried.
category.php
The category template. Used when a category is queried.
tag.php
The tag template. Used when a tag is queried.
taxonomy.php
The term template. Used when a term in a custom taxonomy is queried.
author.php
The author template. Used when an author is queried.
date.php
日期/时间模板,按时间查询时使用的模板。
archive.php
文档模板。查询分类,作者或日期时使用的模板。需要注意的是,该模板将会分别被category.phpauthor.phpdate.php所覆盖(如果存在的话)。
search.php
搜索结果模板,显示搜索结果时使用的模板。
attachment.php
附件模板,查看单个附件时使用的模板,同时也是查看单个图片时默认模板。
image.php
图片附件模板。当在wordpress中查看单个图片时将调用此模板,如果不存在此模板,则调用attachment.php模板。
404.php
404 未找到 模板。当WordPress无法查找到匹配查询的日志或页面时,使用404.php文件。

这些文件在WordPress中有特殊的意义Template Hierarchy,即当对应的条件标签Conditional Tag返回'true'的时候,他们将在这种情况下代替index.php ,例如,如果当前显示的是单一的一篇博文,那么is_single() 这个函数将返回'true',并且,如果有一个single.php文件存在于当前主题中,该文件模板就将起作用.

基本模板

在最简单的情况下,一个WordPress主题由两个文件构成:

  • style.css
  • index.php

这些文件都位于主题目录. 这index.php 模板 是非常灵活的.他可以用来包含所有的引用 header, sidebar, footer, content, categories, archives, search, error, 和其它在WordPress产生的文件.

或者,他也可以模块化,使用单独的文件分担工作.如果你没有提供其它的模板文件,WordPress 会使用默认文件.比如说,如果你没有提供comments.php 文件, WordPress会自动使用 wp-comments.php 模板文件 Template Hierarchy. (Note: As of version 3.0, the default files aren't guaranteed to be present or to be the same as they have been. It's much safer to supply your own template files.)

典型的模板文件包括:

  • comments.php
  • footer.php
  • header.php
  • sidebar.php

使用这些模板文件,你可以把这些文件嵌入到index.php 中,最后生成的文件里.

include 用法:

<?php get_sidebar(); ?>

<?php get_footer(); ?>

关于更多的如何利用各种模板,如何产生不同的信息, 请阅读 Templates 文档.

Query-based Template Files

WordPress can load different Templates for different query types. There are two ways to do this: as part of the built-in Template Hierarchy, and through the use of Conditional Tags within The Loop of a template file.

To use the Template Hierarchy, you basically need to provide special-purpose Template files, which will automatically be used to override index.php. For instance, if your Theme provides a template called category.php and a category is being queried, category.php will be loaded instead of index.php. If category.php is not present, index.php is used as usual.

You can get even more specific in the Template Hierarchy by providing a file called, for instance, category-6.php -- this file will be used rather than category.php when generating the page for the category whose ID number is 6. (You can find category ID numbers in Manage > Categories if you are logged in as the site administrator in WordPress version 2.3 and below. In WordPress 2.5 the ID column was removed from the Admin panels. You can locate the category id by clicking 'Edit Category' and looking on the URL address bar for the cat_ID value. It will look '...categories.php?action=edit&cat_ID=3' where '3' is the category id). For a more detailed look at how this process works, see Category Templates.

If your Theme needs to have even more control over which Template files are used than what is provided in the Template Hierarchy, you can use Conditional Tags. The Conditional Tag basically checks to see if some particular condition is true, within the WordPress Loop, and then you can load a particular template, or put some particular text on the screen, based on that condition.

For example, to generate a distinctive stylesheet in a post only found within a specific category, the code might look like this:

<?php
if ( is_category( '9' ) ) {
    get_template_part( 'single2' ); // looking for posts in category with ID of '9'
} else {
    get_template_part( 'single1' ); // put this on every other category post
}
?>

Or, using a query, it might look like this:

<?php
$post = $wp_query->post;
if ( in_category( '9' ) ) {
    get_template_part( 'single2' );
} else {
    get_template_part( 'single1' );
}
?>

In either case, this example code will cause different templates to be used depending on the category of the particular post being displayed. Query conditions are not limited to categories, however, see the Conditional Tags article to look at all the options.

定义模板

It is possible to use the WordPress plugin system to define additional templates that are shown based on your own custom criteria. This advanced feature can be accomplished using the template_redirect action hook. More information about creating plugins can be found in the Plugin API reference.

Including Template Files

To load another template (other than header, sidebar, footer, which have predefined included commands like get_header()) into a template, you can use get_template_part(). This makes it easy for a Theme to reuse sections of code.

Referencing Files From a Template

When referencing other files within the same Theme, avoid hard-coded URIs and file paths. Instead reference the URIs and file paths with bloginfo(): see Referencing Files From a Template.

Note that URIs that are used in the stylesheet are relative to the stylesheet, not the page that references the stylesheet. For example, if you include an images/ directory in your Theme, you need only specify this relative directory in the CSS, like so:

h1 {
    background-image: url(images/my-background.jpg);
}

Plugin API Hooks

开发主题的时候,需要注意的是你的主题最好能和用户可能安装的任何插件共存。插件可以通过“动作钩子(Action Hooks, 查看 Plugin API)”为wordpress增加功能。

大部分Action Hooks存在于wp的php核心中,所以你的主题不需要任何多余的特殊标签来让它可以正常运转。但是少数的Action Hooks需要在你的主题中做特殊处理,以使插件能够将头,尾,侧边栏等信息输出到页面中。如下是你需要包含到主题 中的Action Hooks列表:

wp_head()
Goes in the <head> element of a theme, in header.php. Example plugin use: add JavaScript code.
wp_footer()
Goes in footer.php, just before the closing </body> tag. Example plugin use: insert PHP code that needs to run after everything else, at the bottom of the footer. Very commonly used to insert web statistics code, such as Google Analytics.
wp_meta()
Typically goes in the <li>Meta</li> section of a Theme's menu or sidebar; sidebar.php template. Example plugin use: include a rotating advertisement or a tag cloud.
comment_form()
Goes in comments.php directly before the comment form's closing tag (<tt</form></tt>). Example plugin use: display a comment preview. As of WordPress 3.0, you should use the default comment form instead, see comment_form().

For a real world usage example, you'll find these plugin hooks included in the default Theme's templates.

Untrusted Data

You should escape dynamically generated content in your Theme, especially content that is output in HTML attributes. As noted in WordPress Coding Standards, text that goes into attributes should be run through esc_attr so that single or double quotes do not end the attribute value and invalidate the XHTML and cause a security issue. Common places to check are titlealt, and value attributes.

In a few cases there might already be a template tag for common cases where safe output is needed. One such case involves the "title" attribute when used with the_title() for post and page titles. To avoid a security vulnerability, use the_title_attribute() instead. Here's an example of correct escaping for the title attribute in a post title link when using translatable text:

<?php echo esc_attr( sprintf( __( 'Permanent Link to %s', 'theme-name' ), the_title_attribute( 'echo=0' ) ) ); ?>

Replace deprecated escape calls with the correct calls: wp_specialcharshtmlspecialchar with esc_htmlclean_url with esc_url, and attribute_escape with esc_attr. See Data_Validation for more.

翻译 / i18n 支持

为了保证本地化翻译的顺利进行,使用 gettext 函数包裹所有需要被翻译的文字部分。这是翻译工作变得十分简单。更多资料请访问 WordPress_Localization i18n for WordPress Developers.

主题的 class

使用以下标签标签增加 WordPress系统产生的 class 属性, body,post 和 comment 标签。 关于post class,只能位于The Loop.

模板文件清单

当开发一个主题的时候,检查你的模板文件是不是遵守了这些标准。

Head 文件(header.php)

  • 使用合适的 DOCTYPE 声明。
  • 开始的 <html> 标签应该包含 language_attributes().
  • "content-type" meta 元素应该位于最前面,包括 title 标签。
  • 使用 bloginfo() 获得标题和博客描述。
  • 使用 automatic feed links 增加 FEED 输出。
  • 增加 wp_head(). 插件会使用这个钩子增加他们的脚本样式表和一些其他的功能。

这里是一份格式正确的 HTML5 头部:

<!DOCTYPE html>
<html <?php language_attributes(); ?>>
<head>
<meta charset="<?php bloginfo( 'charset' ); ?>" />
<title><?php wp_title(); ?> <?php bloginfo( 'name' ); ?></title>
<link rel="profile" href="http://gmpg.org/xfn/11" />
<link rel="stylesheet" href="<?php bloginfo( 'stylesheet_url' ); ?>" type="text/css" media="screen" />
<link rel="pingback" href="<?php bloginfo( 'pingback_url' ); ?>" />
<?php if ( is_singular() && get_option( 'thread_comments' ) ) wp_enqueue_script( 'comment-reply' ); ?>
<?php wp_head(); ?>
</head>

导航菜单 (header.php)

  • 主题得主导航菜单应该支持自定义菜单wp_nav_menu().
    • 菜单应该支持长的菜单名和大量的列表。这些不应该破坏主题的外观。
    • 次级菜单应该正确的显示。如果可能的话,使二级菜单支持下拉。下拉菜单允许显示菜单的深度而不只是顶级菜单。

小工具 (sidebar.php)

  • 主题应该尽可能的支持小工具的使用。 所有看起来像是一个小工具的地方(标签云,链接表,分类目录)或者可以放置小工具的地方(sidebar)应该允许使用小工具。
  • 当有小工具从外观>小工具激活时,小工具区域默认显示的内容应该消失。

页面底部 (footer.php)

  • body 前面,紧紧挨着body 调用 wp_footer()

比如:

<?php wp_footer(); ?>
</body>
</html>

索引 (index.php)

  • 以全文或者摘要的形式显示一列文章。根据情况选用使用或者其他的。
  • 包含 wp_link_pages() 来支持文章内部分页。

归档 (archive.php)

  • 显示归档标题(标签,分类,作者归档)。
  • 以摘要的形式或者全文显示文章。
  • 包含 wp_link_pages() 来支持文章内部分页。

页面 (page.php)

  • 显示标题和内容。
  • 显示评论列表和评论框(除非关闭了评论)。
  • 包含 wp_link_pages() 来内部分页。
  • 元数据,必然标签,分类目录,日期,作者不应该被显示出来。

日志单独页面 (single.php)

  • 包含 wp_link_pages() 在文章内部产生分页效果。
  • 显示标题和内容。
    • 标题应该使用纯文本代替指向自己的链接。
  • 显示发表日期。
    • 尊重时间和日期的默认格式,没必要就别自己设置。(用户自己设置的是最合适的。)
    • 使用 the_time( get_option( 'date_format' ) )获得输出的日期和时间格式。
  • 显示作者名字(如果有的话)。
  • 显示分类目录和标签。
  • 为登陆用户显示“编辑”。
  • 显示评论列表和评论框。

评论 (comments.php)

  • 作者的评论应该高亮显示区分。
  • 如果有头像的话显示头像。
  • 支持嵌套评论。
  • 显示trackbacks/pingbacks。

搜索 (search.php)

  • 显示一系列文章的摘要或者全文显示, 选择一种合适的方式。
  • 搜索结果页面显示搜索输入的内容。非常简单但是非常有用,这可以提醒用户刚才搜索了什么--尤其是在没有结果的时候。使用 the_search_query 或者 get_search_query 显示或者返回结果。例:
    <h2><?php printf( __( 'Search Results for: %s' ), '<span>' . get_search_query() . '</span>'); ?></h2>
  • 在搜索结果页面再一次包含搜索框是对用户非常友好的。使用 get_search_form()调用搜索框。

JavaScript

  • JavaScript 代码应该外部引用。
  • 使用 wp_enqueue_script 引入你的脚本。
  • 直接写入 HTML 的 JavaScript 应该使用 CDATA 来阻止在老版本的浏览器出错。
<script type="text/javascript">
/* <![CDATA[ */
// content of your Javascript goes here
/* ]]> */
</script>

预览

为你的主题做一个预览,并且名字命名为screenshot.png,放在主题目录下。预览一定是真实的预览效果,而且是 PNG 或者 JPG 格式的。

主题选项

主题可以自由的包含是否有选项设置页面。参考 [1].

当增加选项页面的时候使用 edit_theme_options 而不是 switch_themes 选项面板, unless the user actually should be able to switch Themes to be able to use your options panel. WordPress itself uses the edit_theme_options capability for menus, background, header, widgets, et cetera. See more at Roles and Capabilities and Adding Administration Menus.

A note about network mode and Theme options:

If you are using the edit_themes capability anywhere in your Theme, and the Theme is running on a network-enabled WordPress install (previously WordPress MU), be aware that the edit_themes capability used for accessing Theme options pages will prevent site admins in a network from seeing the options menu. Use edit_theme_options instead.

主题测试过程

  1. 修正PHP和WordPress错误.在你的 wp-config.php 文件里添加下面代码增加调试功能,检查deprecated function calls and other WordPress-related errors: define('WP_DEBUG', true);.

参考Deprecated Functions Hook for more information.

  1. Check template files against Template File Checklist (see above).
  2. Do a run-through using the Theme Unit Test.
  3. Validate HTML and CSS. See Validating a Website.
  4. Check for JavaScript errors.
  5. Test in all your target browsers. For example, IE6, IE7, IE8, Safari, Chrome, Opera, and Firefox.
  6. Clean up any extraneous comments, debug settings, or TODO items.
  7. See Theme Review if you are publicly releasing the Theme by submitting it to the Themes Directory.

资源和参考书

编码标准

主题设计

CSS

模板

测试

发行与提高

教学资源

以下是有关WordPress主题和模板文件的推荐文章清单:

主题制作全教程 By Ludou
wordpress主题制作教程 By 站长百科
WordPress 主题教程:从零开始制作 WordPress 主题 By 我爱水煮鱼

本文已被标记为需要加工。欢迎您踊跃编辑,来帮助 Codex。