In the first part of this tutorial, we created a very simple blog with an “About” page and a couple of posts. But it has a very barebones look, and we want some custom navigation links, along with a few more custom pages.
Changing the layout
Overriding the default theme
If you looked at the files in your website’s directory, you’ll see there’s only
your content. The layout and CSS styles come from the default PieCrust theme,
which ships with PieCrust’s code (in piecrust/resources/theme
).
What we can do, with a simple command, is copy all of the default theme’s files into our website, for easy customization:
$ chef themes override
pages/_category.html
pages/_index.html
pages/_tag.html
templates/default.html
templates/partial_post.html
templates/post.html
All of those files have been copied into your website’s directory – and it will warn you if it was ever going to overwrite some of your own files.
There are a few files we’ll be editing here:
pages/_index.html
: That’s the main page.templates/default.html
: That’s the default layout for all the pages (including_index.html
andabout.html
, which we created in part 1 of this tutorial).templates/post.html
: That’s the default layout for a blog post.
Rewriting the main page
Let’s start with the pages/_index.html
page. You’ll see a lot of stuff in
there. Don’t worry, that’s just the default welcome text for when you create an
empty website and you preview it right away.
Let’s just keep the top section – which loops over the latest blog posts and
displays them – and delete everything after (and including) <--markdown-->
.
For this blog, however, maybe we want something different for the home page. How about we only show a list of dates and titles? Let’s rewrite the part we kept.
First, we don’t need to write stuff in raw HTML at this point so remove theformat: none
from the configuration header (at the top of the file). This will
revert the page back to the default Markdown formatter.
Second, change the code to:
{% for post in pagination.posts %}
* {{post.date}} **[{{post.title}}]({{post.url}})**
{% endfor %}
<section>
{% if pagination.prev_page %}<div class="prev"><a href="{{ pagination.prev_page }}">Next Posts</a></div>{% endif %}
{% if pagination.next_page %}<div class="next"><a href="{{ pagination.next_page }}">Previous Posts</a></div>{% endif %}
</section>
We’re still showing links to the previous/next pagination at the bottom, but now instead of showing a classic river of posts, we’re showing a concise and simple list.
Note how the
for
loop generates several lines starting with a star, which gets formatted by Markdown into an HTML list. Also see how we create links with the usual Markdown syntax, but we pass it the title and URL of each post being looped upon by using Jinja syntax.
Now that we refresh the browser, the home page looks very clean and simple… maybe too clean and simple though. Visitors may want a little hint as to what each blog post talks about, especially if you’re the kind of blogger to give cryptic or funny titles to your posts. This is a good way to show how defining and using metadata on your content is super easy in PieCrust.
Let’s change the loop to:
{% for post in pagination.posts %}
* {{post.date}} **[{{post.title}}]({{post.url}})**{%if post.hint%}: {{post.hint}}{%endif%}
{% endfor %}
This will show a post’s hint
if it is defined. Of course, if you refresh the
page now, nothing will change.
Now go into some of your posts, and add something like this to their configuration header:
---
<existing configuration settings...>
hint: Where we announce things
---
Refresh the home page, and you’ll see this new piece of metadata displayed next to the post’s title!
Using page metadata in PieCrust is both easy and powerful, because you can sort, filter, display, and more, based on those metadata values.
Changing the default layout
Because the main page doesn’t specify any custom layout, it will use the default
layout which is located at templates/default.html
. If you open that file,
you’ll realize that it’s where the default PieCrust theme does all the stuff you
see it doing: setting the page title, defining some simple CSS theme, etc.
In order not to get lost in HTML/CSS considerations, instead of just looking at how PieCrust works, let’s do a simple edit. We’ll add a link to the “About” page we created in the first part of this tutorial in the footer part of every page.
Edit templates/default.html
and replace the last line of the footer
(i.e. just before </footer>
) with this:
<p><a href="{{pcurl('about')}}">About this site</a> – {{ piecrust.branding|safe }}</p>
Refresh your browser, and you should see a link to the “About” page at the bottom of every page, including blog posts.
Blog posts use the
post
layout by default (which you can find attemplates/post.hml
) instead ofdefault
. But in the case of PieCrust’s default theme, which we override here, it’s the same layout. Indeed, if you open thepost
layout, you’ll see it only has one line which says that it extends thedefault
layout.
You’ll probably spend lots of time in here, tweaking your navigation sidebars and your margins and whatnot. Besides fighting CSS and browser inconsistencies, you’ll also probably refer a lot to the Jinja templating documentation for your template logic, unless you end up using another template engine.
Next steps
In the third part of this tutorial, we’ll look at PieCrust’s built-in asset pipeline, by writing some CSS code.