View Overrides

Graffiti uses very simple yet powerful templating system to display its site content.

Before we get into how to write theme and using templating system, it is important to understand the file structure.

  1. Each theme exists in its own folder in the /files/themes directory.
  2. Each theme must contain the following three files:
    1. Layout.view - This file is responsible for the basic "shell" of a theme. For those of you familiar with ASP.Net, it is very similar to a master page.
    2. Index.view - This file is responsible for rendering a list of posts. By default, this includes the home page, all category pages, tag pages, and the search results page.
    3. post.view - This file is responsible for rendering a single post (single piece of content). If enabled, this would also usually include comments.

Graffiti provides you with a lot of flexibility to render different content based on which page in your site is requested. One of the goals we used in creating Graffiti was to stick to the mantra of "Convention over Configuration". What this means is that you can specify different view files be used per page or section of the site without ever having to tell Graffiti they exist.

To accomplish this goal, Graffiti requires a file naming convention for custom views that follows a logical pattern based on the portions of the site that are being affected.  Before using any default view files inside a theme, Graffiti will check to see if any appropriately named view files exist in the theme.  If they exist, they are used instead of the three default views.  This allows you to selectively add support for custom views in your theme and leave the default views in place.  Structuring a theme in this way allows a user to modify your theme specific views without fear of breaking the default views on the site.

Here are some examples of how this works.

  • Category.view - this file will render all of the category pages. This will override index.view.
  • Category-Name.view - if this file name matches a category in Graffiti it will be used to render than category. This will override both category.view and index.view.
  • Category-Name.post.view - if this file name matches a category, it will be used to render all of the individual post pages in the category. This will override post.view.
  • Category-Name.Post-Name.view - if this file name matches a category and a post name, it will be used to render the post. This is important because two posts can have the same name if they are in different categories. This will override both Category-Name.post.view and post.view.
  • Search.view - this file will render the results of a search in Graffiti. This will override index.view.
  • Post-Name.view - if this file name matches the name of a post, it will be used to render the post. It is important to note that post names are only unique per category, so for more explicitly control, you may wan to consider Category-Name.Post-Name.view. This will override post.view.
  • Page.view - if this file exists, Graffiti will use it to render any uncategorized post. This will override post.view.

The overrides above will allow you to build a beautiful site and have complete control over each individual page. However, one of our other design goals to remove the need to duplicate any of your design elements across multiple files. In addition, we wanted to enable designers an easy way to keep their view files very simple and lightweight. To accomplish this goal, we added a second set of overrides which can be used based on location.

Here are a couple file examples:

  • Home.Layout.view - when Graffiti finds this file in the current theme, it will be used instead of Layout.view on the home page.
  • Search.Layout.view - when Graffiti finds this file in the current theme, it will be used instead of Layout.view on the search page.
  • Category.Layout.view - when Graffiti finds this file in the current theme, it will be used instead of Layout.view on all category pages.
  • Category-Name.Layout.view - when Graffiti finds this file in the current theme, it will be used instead of Layout.view on the current category page.

Finally, there is one additional set of file overrides.  You can also use templating syntax to accomplish similar tasks. The syntax takes the form of $FileName. The following files are available for you to use: header, sidebar, leftsidebar, rightsidebar, footer.  When Graffiti finds $FileName in any view, it will attempt to load and render a view based on that name. In addition, the same location based overrides as above also exist.

A couple of examples of $header:

  • If Graffiti encounters $header in any view, it will try to load and render a view named header.view in the current theme.
  • If $header was requested from the home page, Graffiti would first try home.header.view.
  • If it was used on a category page named "Sample" it would first try to the file sample.header.view, then category.Header.view, and finally header.view.

Tip: To limit looking up which files exist on every request, Graffiti caches known files in memory. This is a very big performance gain, but makes designing a new theme difficult. To get around this, you can turn off View caching by changing the following item, "Graffiti:Views:Cache", in your Settings.config file (/__config/settings.config) to false. Just remember to set it back to true before you deploy a site into production.