主题¶
有一个由社区管理的主题仓库 Pelican Themes 供大家使用。
请注意,虽然我们已经尽全力审查与合并主题,但是由于他们是由社区提交的,因此支持性和互操作性各有不同。
Community themes can also be found on PyPI tagged with "Framework :: Pelican :: Themes".
创建主题¶
Pelican使用 Jinja 来生成HTML。如果你想要创建你自己的主题,请从 "simple" 主题 中找寻灵感。
要使用你自己创建的主题生成站点,你可以通过命令行中的 -t 参数指定主题:
pelican content -s pelicanconf.py -t /projects/your-site/themes/your-theme
如果你不希望每次都通过命令行手动指定主题,你可以在配置文件中定义 THEME 来指定你希望使用的主题的位置。
结构¶
你需要遵循下面的结构来制作你自己的主题:
├── static
│ ├── css
│ └── images
└── templates
├── archives.html // to display archives
├── article.html // processed for each article
├── author.html // processed for each author
├── authors.html // must list all the authors
├── categories.html // must list all the categories
├── category.html // processed for each category
├── index.html // the index (list all the articles)
├── page.html // processed for each page
├── period_archives.html // to display time-period archives
├── tag.html // processed for each tag
└── tags.html // must list all the tags. Can be a tag cloud.
static 文件夹包含了所有静态资源,会被复制输出到 theme 文件夹中。上面的文件夹布局结构包括了CSS和image文件夹,但是这只是举个例子。你可以根据需求安排文件。
templates 文件夹包含了需要用到的所有模板文件,这些模板文件会用于生成网站内容。上面列出的模板文件都是必须有的。当然,你可以添加一些其他的模板来帮助组织主题文件。
模板和变量¶
你可以将一些简单的语法嵌入到HTML文件中。以下文档描述了哪些模板需要存在于主题中,以及有哪些变量可以在模板中使用。
所有模板都能接收到配置文件中定义的变量,变量名都是全大写的,可以直接使用。
通用变量¶
下列变量在所有模板中均可使用。
变量名 |
描述 |
|---|---|
output_file |
当前正在生成的文件名。例如在Pelican渲染主页时,此变量的值就是“index.html”。 |
articles |
文章列表,以日期降序排列。所有元素都是 Article 对象,因此你可以访问 Article 对象的属性(例如title、summary、author等)。有时候此变量是隐藏的(例如在标签页面中)。但仍可以在 all_articles 变量中找到相关信息。 |
dates |
和articles相同的文章列表,但是以日期升序排列 |
hidden_articles |
处于隐藏状态的文章的列表 |
drafts |
处于草稿状态的文章的列表 |
period_archives |
一个字典,包含与时间段存档相关的元素(若启用了时间段存档)。详见 时间段存档的列表和链接 |
authors |
元组(author, articles)的列表,包含所有作者及对应文章。 |
categories |
元组(category, articles)的列表,包含所有分类及对应文章 |
tags |
元组(tag, articles)的列表,包含所有标签及对应文章 |
pages |
页面的列表 |
hidden_pages |
处于隐藏状态的页面的列表 |
draft_pages |
处于草稿状态的页面的列表 |
排序¶
URL包装器(分类、标签、作者),都拥有比较方法,使其易于按名称排序:
{% for tag, articles in tags|sort %}
如果你想要以不同条件进行排序,可以使用 Jinja的排序命令 ,其中有丰富的选项。
日期格式¶
Pelican会根据设置和地区( DATE_FORMATS/DEFAULT_DATE_FORMAT )对日期进行格式化,同时还会提供一个 locale_date 属性。 date 属性以 datetime 类表示。如果你需要使用与设置中不同的自定义日期格式,使用Jinja中的 strftime 过滤器即可。用法Python中的 strftime 相同,但是过滤器会根据设置中给出的地区对日期进行格式化:
{{ article.date|strftime('%d %B %Y') }}
检测已加载的插件¶
Pelican 提供了一个名为 plugin_enabled 的Jinja test,可用于检测某个插件是否启用。此test以字符串形式接受一个插件名称,并且返回一个布尔值。命名空间插件可以通过全名( pelican.plugins.plugin_name )或者短名称( plugin_name )指定。下面的例子中通过 webassets 插件来减小CSS的体积,但若此插件未启用,则回滚回普通的CSS:
{% if "webassets" is plugin_enabled %}
{% assets filters="cssmin", output="css/style.min.css", "css/style.scss" %}
<link rel="stylesheet" href="{{SITEURL}}/{{ASSET_URL}}">
{% endassets %}
{% else %}
<link rel="stylesheet" href="{{SITEURL}}/css/style.css}">
{% endif %}
index.html¶
站点的主页,可以理解为推文的索引页,生成为 index.html 。
如果开启了分页功能,后续的页面会以 index{number}.html 的形式生成。
变量名 |
描述 |
|---|---|
articles_paginator |
一个分页器对象,其中存放着文章列表 |
articles_page |
当前分页包含的文章的列表 |
articles_previous_page |
前一分页包含的文章的列表(若没有前一页,此变量值为 |
articles_next_page |
后一分页包含的文章的列表(若没有后一页,此变量值为 |
dates_paginator |
分页器对象,存放着以日期正序排列的文章列表。 |
dates_page |
以日期正序(从旧到新)排列时,当前分页包含的文章的列表。 |
dates_previous_page |
以日期正序(从旧到新)排列时,前一分页包含的文章的列表。(若没有前一页,此变量值为 |
dates_next_page |
以日期正序(从旧到新)排列时,后一分页包含的文章的列表。(若没有后一页,此变量值为 |
page_name |
值为 'index' ——在分页链接中很实用 |
category.html¶
此模板会应用于每个已存在的分类上,根据设置项 CATEGORY_SAVE_AS 确定输出路径(默认值为: category/{slug}.html )。如果启用了分页,后续页面会保存为 category/{slug}{number}.html 。
变量名 |
描述 |
|---|---|
category |
正在处理的分类名称 |
articles |
此分类下的文章 |
dates |
此分类下的文章,以日期正序排列 |
articles_paginator |
一个分页器对象,其中存放着文章列表 |
articles_page |
当前分页包含的文章的列表 |
articles_previous_page |
前一分页包含的文章的列表(若没有前一页,此变量值为 |
articles_next_page |
后一分页包含的文章的列表(若没有后一页,此变量值为 |
dates_paginator |
分页器对象,存放着以日期正序排列的文章列表 |
dates_page |
当前页面中的文章,以日期正序排列 |
dates_previous_page |
以日期正序(从旧到新)排列时,前一分页包含的文章的列表。(若没有前一页,此变量值为 |
dates_next_page |
以日期正序(从旧到新)排列时,后一分页包含的文章的列表。(若没有后一页,此变量值为 |
page_name |
变量值与CATEGORY_URL一致,所有在 {slug} 之后的字符都会被删除——这对分页链接很有用 |
article.html¶
此模板会应用于文章上,根据设置项 ARTICLE_SAVE_AS 确定输出路径(默认值为: {slug}.html )。在渲染文章过程中可以使用下列变量。
变量名 |
描述 |
|---|---|
article |
准备显示的文章对象 |
category |
当前文章所属分类的名称 |
文章源文件开头部分的元数据都会作为 article 对象的属性存在,属性名和元数据中指定的相同(但是是全小写的)。
例如,一篇文章源文件中添加了一个额外的元数据 FacebookImage :
Title: I love Python more than music
Date: 2013-11-06 10:06
Tags: personal, python
Category: Tech
Slug: python-je-l-aime-a-mourir
Author: Francis Cabrel
FacebookImage: http://franciscabrel.com/images/pythonlove.png
此元数据在 article.html 模板中可以通过 article.facebookimage 获取。通过这种方式,就可以实现例如Facebook的动态打开标签:
<meta property="og:image" content="{{ article.facebookimage }}"/>
page.html¶
此模板会应用于页面上,根据设置项 PAGE_SAVE_AS 确定输出路径(默认值为: pages/{slug}.html )。在渲染过程中可以使用下列变量。
变量名 |
描述 |
|---|---|
page |
准备显示的页面对象,可以从中获取标题、slug和具体内容。 |
tag.html¶
此模板会应用于标签页上,根据设置项 TAG_SAVE_AS 确定输出路径(默认值为: tag/{slug}.html )。若启用了分页,后续页面默认存储为。tag/{slug}{number}.html 。
变量名 |
描述 |
|---|---|
tag |
当前正在处理标签的名称 |
articles |
和此标签关联的文章 |
dates |
和此标签关联的文章,以日期正序排列 |
articles_paginator |
一个分页器对象,其中存放着文章列表 |
articles_page |
当前分页包含的文章的列表 |
articles_previous_page |
前一分页包含的文章的列表(若没有前一页,此变量值为 |
articles_next_page |
后一分页包含的文章的列表(若没有后一页,此变量值为 |
dates_paginator |
分页器对象,存放着以日期正序排列的文章列表 |
dates_page |
当前页面中的文章,以日期正序排列 |
dates_previous_page |
以日期正序(从旧到新)排列时,前一分页包含的文章的列表。(若没有前一页,此变量值为 |
dates_next_page |
以日期正序(从旧到新)排列时,后一分页包含的文章的列表。(若没有后一页,此变量值为 |
page_name |
变量值与TAG_URL一致,所有在 {slug} 之后的字符都会被删除——这对分页链接很有用 |
period_archives.html¶
此模板用于生成归档页面, YEAR_ARCHIVE_SAVE_AS 、 MONTH_ARCHIVE_SAVE_AS 与 DAY_ARCHIVE_SAVE_AS 分别对应着年、月、日的归档,只有指定了对应的路径才会生成归档页面。
变量名 |
描述 |
|---|---|
period |
一个元组,格式为 (year, month, day) ,指明了当前的时间段。 year 和 day 为数字, month 则为字符串。当时间段以年给定时,此元组只会有 year ;当时间段以年和月给定时此元组中则只会包含 year 和 month ;以此类推。 |
period_num |
一个元组,格式为 ( |
有关 period 的使用可以参考 "simple" 主题中的period_archives.html模板 .
列出归档与链接到归档¶
对于Pelican给出的归档时间段, period_archives 可用于生成对应的链接列表。此变量作为 通用变量 ,可在所有模板中使用。因此可以借此在自定义直接模板中或是侧边栏中实现链接索引。
period_archives 是一个字典,根据 *_ARCHIVE_SAVE_AS 设置的启用情况,其键对应为 year 、 month 与 day ,其值是包含字典的列表,每个字典依次表示一个时间段(顺序由 NEWEST_FIRST_ARCHIVES 设置决定),并包含以下键值对:
键 |
值 |
|---|---|
period |
一个元组,内容和 |
period_num |
一个元组,内容和 |
url |
当前时间段归档页面的URL,例如 |
save_as |
当前时间段归档页面的存储路径,例如 |
articles |
一个列表,其中为当前时间段内所有文章的 Article 对象。 |
dates |
和 |
下面的例子展示了如何在模板中使用 period_archives :
<ul>
{% for archive in period_archives.month %}
<li>
<a href="{{ SITEURL }}/{{ archive.url }}">
{{ archive.period | reverse | join(' ') }} ({{ archive.articles|count }})
</a>
</li>
{% endfor %}
</ul>
你可以根据需要的时间粒度将 for 语句中的 period_archives.month 改为 period_archives.year 或 period_archives.day 。
对象¶
下面是对在模板中可用对象的属性的详细说明。以下仅列出了较常用的一些,并不是全部。
Article¶
Article对象的字符串表示即为 source_path 属性。
属性 |
描述 |
|---|---|
author |
当前文章的 Author |
authors |
当前文章的多个 Authors |
category |
当前文章的 Category |
content |
当前文章渲染完成的内容 |
date |
当前文章的Datetime对象 |
date_format |
默认日期格式或是特定地区的日期格式 |
default_template |
默认的模板名称 |
in_default_lang |
布尔值,用于表示当前文章是不是以默认语言写的。 |
lang |
当前文章使用的语言。 |
locale_date |
以 date_format 格式化后的日期。 |
metadata |
文章元数据的字典。 |
save_as |
本篇文章生成保存的位置。 |
slug |
推文的slug |
source_path |
文章源文件的完整系统路径。 |
relative_source_path |
从 PATH 到当前文章源文件的相对路径。 |
status |
当前文章的状态,可能值为'published'或'draft'。 |
summary |
渲染后的摘要内容。 |
tags |
Tag 对象的列表。 |
template |
用于渲染的模板名称 |
title |
当前文章的标题。 |
translations |
当前文章所有翻译版本的 Article 对象。 |
url |
文章页面的URL。 |
Page¶
Page对象的字符串表示与 source_path 属性一致。
属性 |
描述 |
|---|---|
author |
当前页面的 Author 。 |
content |
当前页面渲染后的内容。 |
date |
当前页面日期对应的Datetime对象。 |
date_format |
默认日期格式或是特定地区的日期格式 |
default_template |
默认的模板名称 |
in_default_lang |
布尔值,用于表示当前文章是不是以默认语言写的。 |
lang |
当前文章使用的语言。 |
locale_date |
以 date_format 格式化后的日期。 |
metadata |
页面元数据的 字典 。 |
save_as |
保存页面的位置。 |
slug |
推文的slug |
source_path |
页面源文件的完整系统路径。 |
relative_source_path |
页面源文件相对于 PATH 的相对路径。 |
status |
页面的状态,可能值有'published'、'hidden'或者'draft'。 |
summary |
渲染后的摘要内容。 |
tags |
Tag 对象的列表。 |
template |
用于渲染的模板名称 |
title |
页面的标题。 |
translations |
当前文章所有翻译版本的 Article 对象。 |
url |
页面的URL |
订阅源¶
订阅源相关变量在3.0版本发生过变化。各变量现在都在名称中显示地表达了属于ATOM还是RSS。默认使用ATOM。旧的主题需要进行更新。下面是订阅源相关变量的完整列表:
AUTHOR_FEED_ATOM
AUTHOR_FEED_RSS
CATEGORY_FEED_ATOM
CATEGORY_FEED_RSS
FEED_ALL_ATOM
FEED_ALL_RSS
FEED_ATOM
FEED_RSS
TAG_FEED_ATOM
TAG_FEED_RSS
TRANSLATION_FEED_ATOM
TRANSLATION_FEED_RSS
继承¶
从3.0版本开始,Pelican支持从 simple 主题继承,因此可以在你自己的主题中重用 simple 主题。
如果 templates/ 目录中缺失了的某些必须要有的文件,会自动使用 simple 主题中的对应模板。因此如果 simple 主题中的一些模板正合你意,就没必要重新写个新的了。
你也可以使用 {% extends %} 指令在你自己的主题中扩展 simple 主题:
{% extends "!simple/index.html" %} <!-- extends the ``index.html`` template from the ``simple`` theme -->
{% extends "index.html" %} <!-- "regular" extending -->
例子¶
With this system, it is possible to create a theme with just one file.
main.css¶
The file is static/css/main.css (the default CSS_FILE):
body {
font-family : monospace ;
font-size : 100% ;
background-color : white ;
color : #111 ;
width : 80% ;
min-width : 400px ;
min-height : 200px ;
padding : 1em ;
margin : 5% 10% ;
border : thin solid gray ;
border-radius : 5px ;
display : block ;
}
a:link { color : blue ; text-decoration : none ; }
a:hover { color : blue ; text-decoration : underline ; }
a:visited { color : blue ; }
h1 a { color : inherit !important }
h2 a { color : inherit !important }
h3 a { color : inherit !important }
h4 a { color : inherit !important }
h5 a { color : inherit !important }
h6 a { color : inherit !important }
pre {
margin : 2em 1em 2em 4em ;
}
#menu li {
display : inline ;
}
#post-list {
margin-bottom : 1em ;
margin-top : 1em ;
}
Custom templates¶
If you want to customise the templates as well, you can extend them. For
example, to add a custom footer, create a templates/base.html:
{% extends "!simple/base.html" %}
{% block footer %}
<p>Custom footer</p>
{{ super() }}
{% endblock %}
第一行中,从
simple主题中扩展了base.html模板,因此无需重写整个文件。On the third line, we open the
footerblock which has already been defined in thesimpletheme.On the fourth line, we insert the extra footer content.
On the fifth line, the function
super()keeps the content previously inserted in theheadblock.On the last line, we close the
footerblock.
This file will be extended by all the other templates, so the custom footer will appear on all pages.