Hugo Prose is a minimalist theme derived from the XMin theme, and inspired by Wowchemy (previously known as the Academic theme), Distill, and tufte.css. This theme itself is completely plain-text and lightweight, and does not use any icons, images, or emojis.1 By default, the theme only uses two JavaScript libraries, MathJax and highlight.js, and they are loaded only when necessary. The rest of JavaScript is written from scratch and also relatively short. This theme does not use any CSS frameworks, and the full CSS code is also written from scratch (about 300 lines).

It is not the man who has too little that is poor, but the one who hankers after more.

Letters from a Stoic

This page introduces the features of this Hugo theme that you can fiddle with.

Site configurations

Below are the possible options that you may configure for a site based on this theme.

Each page has a menu in the header and a menu in the footer. The header menu is defined in the header option in menu in config.yaml, and similarly, the footer menu is defined in the footer option, e.g.,

menu:
  header:
    - name: Home
      url: ""
      weight: 1
    - name: About
      url: "about/"
      weight: 2
  footer:
    - name: Contact
      url: "404.html"
      weight: 1
    - name: Categories
      url: "categories/"
      weight: 2
      pre: "optional"

The url of a menu item can be either a relative URL pointing to a page on this website, or an external link (e.g., url: "https://github.com/yihui"). The order of the menu items is determined by the weight values. If a menu item has a pre value, it will be used as the class of the menu item. The special value optional indicates that this menu item will be hidden on small screens.2

The header menu can be made sticky via the parameter stickyMenu in config.yaml:

params:
  stickyMenu: true

Home page

The body of the home page consists of an introduction, followed by a series of info cards, and then a number of the latest posts and pages.

  • The introduction comes from content/_index.md. The Markdown content can contain arbitrary elements.

  • The info cards come from the content/card/ directory. Each (Markdown) file is displayed on the home page as a separate card. The title is displayed vertically on the left or right side.3 If you want to customize the style of a certain card, you may use the YAML option style in the file, e.g.,

    ---
    title: "Courses"
    style: "background: darkorange; color: white;"
    ---
    

    This will add a dark orange background to the card, and change the color of text to white. You can use any CSS styles here (e.g., font-size, background-image, and padding).

  • The number of latest posts and pages can be defined via the homePosts option in params in config.yaml, e.g.,

    params:
      homePosts: 10
    

    The default is 6.

  • The mainSections parameter can be used to select the sections of pages to be included on the home page, e.g.,

    params:
      mainSections: ["post", "news"]
    

Besides the menu in the footer, you can specify a copyright statement in the footer parameter in config.yaml, e.g.,

params:
  footer: "© Frida Gomam 2015 -- 2020"

Comments

Disqus, Utterances

Searching

This theme supports searching out of the box based on Fuse.js. A few critical configurations:

  • The site needs to generate a JSON index. This is done via a layout file index.json.json in layouts/_default/, and the config in config.yaml:

    outputs:
      home: [html, rss, json]
    
  • A menu item with the ID menu-search configured in config.yaml, e.g.,

    menu:
      header:
        - name: Search
          url: "#"
          identifier: menu-search
    
  • The version of Fuse can be configured via the parameter fuseVersion in config.yaml, e.g.,

    params:
      fuseVersion: 6.4.3
    

    If no fuseVersion is specified, the latest version of Fuse.js will be used. You may also download a copy of Fuse.js to the static/ folder of your site and use this copy instead of loading it from CDN. To do that, you may download Fuse.js to, say, static/js/fuse.js and modify the partial template layouts/partials/foot_custom.html. Replace

    {{ with .Site.Params.fuseVersion }}
    <script src="https://cdn.jsdelivr.net/npm/fuse.js@{{ . }}"></script>
    {{ end }}
    

    with

    <script src="{{ relURL "/js/fuse.js" }}"></script>
    

    That way, you can also use search when viewing the site offline, because Fuse.js is no longer loaded from CDN.

Articles

At the moment, I’m too tired to complete the documentation. If you want to be an early adopter of this theme, you might have to read the source.

Multiple authors

If an article has multiple authors, specify their names in an array in the author field.

Author’s bio is loaded from the database data/authors.yaml.

Table of contents

TOC can be automatically generated, no matter if you use Hugo/goldmark or Pandoc/R Markdown.

Number sections

Section headers can be automatically numbered, no matter if you use Hugo/goldmark or Pandoc/R Markdown.

Footnotes, citations, and sidenotes

Footnotes and citation entries4 are moved to the right margin by default. If you want to write arbitrary sidenotes, use the classes side and side-left/side-right.

This is a sidenote on the left side. You can include anything in the note. For example, here is a bullet list:

  • Get up
  • Do the work
  • Go to bed
<div class="side side-left">

Content to be displayed as a sidenote.

</div>

Appendix

  • Author’s bio

  • Custom fields

  • License

  • Suggest changes

Drafts

Mark an article as draft by adding draft: true to the YAML metadata. Draft articles are styled with a background of diagonal lines and a watermark “Draft.” For listing pages, draft articles are also indicated by the background.

Floats

Full-width elements

Apply the class fullwidth, e.g.,

<div class="fullwidth">

Content to be displayed with its maximum width.

</div>
History of stoics

Figure 3.1: Beginning around 301 BC, Zeno taught philosophy at the Stoa Poikile (“Painted Porch”), from which his philosophy got its name. Unlike the other schools of philosophy, such as the Epicureans, Zeno chose to teach his philosophy in a public space, which was a colonnade overlooking the central gathering place of Athens, the Agora.

If you want the full-width element to be scrollable, you can apply an additional class fullscroll, e.g.,

<div class="fullwidth fullscroll">

Super wide content to be scrolled horizontally.

</div>
Along the River During the Qingming Festival

Figure 3.2: This painting is known as the “Qing Court Version” of Along the River During the Qingming Festival. Here, the figural scenes are numerous and detailed, happening around noteworthy landmarks and places such as the serene rustic countryside, the Rainbow Bridge (虹橋) and its crowded markets, the lively surroundings and throughways at the city walls and gates, the busy streets and various packed shops, the secluded literati gardens, the Songzhu Hall (松竹軒) as well as the beautiful site of the Jinming Lake (金明池).

Embedded elements

Use the embed-left or embed-right class to embed a content block to be floated to the left or right, and the block will exceed the article margin by 200px, e.g.,

<div class="embed-right">

Content to be embedded onto the margin.

</div>

One application is to embed videos in an article, when the video needs a narrative. For example, you can embed a video on the right side, and provide a narrative in the body of the article, which will be on the left side of the video.

By default, the max-width of the embedded element is 600px (the actual width could be smaller), out of which 200px will be in the margin, meaning that there will be at least 400px left for the narrative in the article body.

When the screen width is smaller than 1200px, the embedded elements will be floated back into the article as normal block-level elements.

Quotes

Use the quote-left or quote-right class to make content float to the left or right.

<div class="quote-left">

A quote to be floated to the left.

</div>

The quotes do not have to be literally quotes. These environments can contain any content, although quotes may be the most common application.

Here is a quote that I’ve never said.

The default width of the content is 45% of the container. You have seen an example of quote-right at the beginning of this article. Here is an example of quote-left on the left side. The quotes will stop floating and become normal block-level elements when the screen width is smaller than 800px.

List pages

Open face characters

The first alphabetical character in each summary block is converted to an open face character such as:

𝔸 𝔹 ℂ 𝔻 𝔼 𝔽 𝔾 ℍ 𝕀 𝕁 𝕂 𝕃 𝕄 ℕ 𝕆 ℙ ℚ ℝ 𝕊 𝕋 𝕌 𝕍 𝕎 𝕏 𝕐 ℤ 𝕒 𝕓 𝕔 𝕕 𝕖 𝕗 𝕘 𝕙 𝕚 𝕛 𝕜 𝕝 𝕞 𝕟 𝕠 𝕡 𝕢 𝕣 𝕤 𝕥 𝕦 𝕧 𝕨 𝕩 𝕪 𝕫

Responsive design

Screen size

Attribute \ width 650 - 800px 800 - 1264px > 1264px
Menu optional items hidden shown <=
Table of contents position => body / static left margin / sticky
Floats position => body / static beside or overlapping body
Sidenotes position => body / static side
Home posts layout one column two columns <=

Dark theme

This theme uses the prefer-color-scheme CSS media feature to respond to the dark color theme of the system. If you change your system to the dark mode, the web pages will automatically switch to the dark mode.

Custom layouts

TODO

section anchors


  1. This example website does contain images and videos as demos, though. ↩︎

  2. For example, pre: "optional" will generate the menu item <li class="optional">. It may be an unimportant item that you do not mind hiding on smaller screens. ↩︎

  3. We recommend that you keep the title short so it can fit on one line. ↩︎

  4. Note that if you want to use citations, you have the R Markdown format with the R package blogdown. Plain Markdown posts (.md files) do not support citations. ↩︎

Author's bio

Yihui Xie (https://yihui.org) is a software engineer at RStudio. He earned his PhD from the Department of Statistics, Iowa State University. He has authored several R packages, such as knitr, bookdown, blogdown, xaringan, DT, and tinytex. He also co-authored a few other R packages, including shiny, rmarkdown, and leaflet. He has published a number of books, including Dynamic Documents with R and knitr, bookdown: Authoring Books and Technical Documents with R Markdown, blogdown: Creating Websites with R Markdown, R Markdown: The Definitive Guide, and R Markdown Cookbook. He is the founder of the Capital of Statistics (https://cosx.org). He initiated the Chinese R conference in 2008.

Acknowledgments

We thank the authors of the Wowchemy theme, tufte.css, and the Distill framework for inspirations. Many users in the R community have asked for a Distill-like Hugo theme directly or indirectly, including but not limited to Emi Tanaka, Duncan Garmonsway, Frank Harrell, Josiah Parry, and Alison Hill. We are not sure if this Hugo Prose theme would make it easier or even harder to answer the frequently asked question “blogdown or distill?”

The images on this page are from Wikipedia entries Stoicism and 清明上河图. The CSS style for draft posts was borrowed from Fabian Tamp’s paperesque theme. Wladimir Palant’s tutorial helped a lot with our implementation of the client-side search.

Reuse

Text and figures are licensed under Creative Commons Attribution CC BY 4.0. The source code is licensed under MIT. The full source is available at https://github.com/yihui/hugo-prose.

Suggest changes

If you find any mistakes (including typos) or want to suggest changes, please feel free to edit the source file of this page on Github and create a pull request.

Citation

For attribution, please cite this work as

Yihui Xie (2024). About Hugo Prose. Hugo Prose. https://prose.yihui.org/about/

BibTeX citation

@misc{
  title = "About Hugo Prose",
  author = "Yihui Xie",
  year = "2024",
  journal = "Hugo Prose",
  note = "https://prose.yihui.org/about/"
}