Files
codex-obscura-hugo-theme/README.md
2026-03-24 20:30:43 -04:00

385 lines
11 KiB
Markdown

# Codex Obscura
> *A dark academia pixel Hugo theme with a fall color palette.*
>
> Candlelit manuscripts meet cozy stationery. Books, tea, fountain pens, and the quiet rustle of digital marginalia.
---
```
██████╗ ██████╗ ██████╗ ███████╗██╗ ██╗
██╔════╝██╔═══██╗██╔══██╗██╔════╝╚██╗██╔╝
██║ ██║ ██║██║ ██║█████╗ ╚███╔╝
██║ ██║ ██║██║ ██║██╔══╝ ██╔██╗
╚██████╗╚██████╔╝██████╔╝███████╗██╔╝ ██╗
╚═════╝ ╚═════╝ ╚═════╝ ╚══════╝╚═╝ ╚═╝
```
---
## Features
- **Fall color palette** — deep ambers, burnt orange, rust, forest green, umber, parchment cream
- **Pixel art borders** — CSS-only pixel-perfect box shadow borders on all cards and widgets
- **Blinking `█` cursor** in the site title (optional, easily disabled)
- **Dark academia typography** — VT323 (pixel/terminal) for headings + Josefin Sans for body text
- **Dust mote ambient animation** — soft floating particles that drift across the page like dust in a library
- **Sidebar** — sys-info widget with live uptime counter, recent posts, tag cloud, and optional marginalia quote
- **Year-grouped archive** — posts grouped by year in terminal `ls -la` style
- **Tag filtering** — clickable tag chips at the top of the archive page with active highlighting
- **Post subtitles** — optional per-post tagline shown on cards and single pages
- **Responsive (Mostly)** — two-column desktop, stacked mobile
- **RSS feed** — full RSS out of the box
- **SEO-ready** — Open Graph, Twitter Card, canonical URLs
- **Syntax highlighting** — via highlight.js with Common Lisp support, add more lines to layout/partials/head.html for more
- **LaTeX rendering** — via KaTeX with Hugo passthrough for clean math expressions
- **Custom code blocks** — shortcode with language label and optional title
- **Comments** — Comentario integration (self-hosted, privacy-focused)
---
## Installation
### As a Git Submodule (recommended)
First run `hugo new site <sitename>`
```bash
cd <sitename>
git submodule add https://git.johnabs.xyz/bs-sensei/codex-obscura-hugo-theme
```
### Manual
Download and place the folder at `themes/codex-obscura/` inside your Hugo site, which you should have made using `hugo new site <sitename>`
---
## Configuration
After creating your site at <sitename> from above and adding the template, you should first go to the `content` folder and create an about.md, resume.md, and a donate.md in your content folder or these will redirect to "Not Found". Your posts link will also redirect, unless you make a folder within content called `posts` and make `post1.md` inside it and add some text. Examples of each of these are provided below for your convenience.
A full `hugo.toml` example:
```toml
baseURL = "https://yourdomain.com/"
languageCode = "en-us"
title = "Your Site Title"
theme = "codex-obscura"
paginate = 8
summaryLength = 20
[markup.highlight]
codeFences = false # disable Chroma — we use highlight.js instead
[markup.goldmark.renderer]
unsafe = true # you can probably set this to false, try both. False works for me :)
[markup.goldmark.extensions.passthrough]
enable = true
[markup.goldmark.extensions.passthrough.delimiters]
block = [["$$", "$$"]]
inline = [["$", "$"]]
[params]
description = "Your site description shown in the hero card."
author = "Your Name"
tagline = "a brief italicized tagline"
sidebarQuote = "A quote you love."
sidebarQuoteAuthor = "The Author"
resumePDF = "/files/resume.pdf"
comentarioURL = "https://comments.yourdomain.com"
[params.social]
github = "yourusername"
mastodon = "https://mastodon.social/@you"
email = "you@example.com"
[[menu.main]]
name = "home"
url = "/"
weight = 1
[[menu.main]]
name = "posts"
url = "/posts/"
weight = 2
[[menu.main]]
name = "tags"
url = "/tags/"
weight = 3
[[menu.main]]
name = "about"
url = "/about/"
weight = 4
[[menu.main]]
name = "resume"
url = "/resume/"
weight = 5
[[menu.main]]
name = "donate"
url = "/donate/"
weight = 6
[taxonomies]
tag = "tags"
category = "categories"
```
---
## Creating Content
```bash
# New blog post
hugo new posts/my-entry.md
# New about page
hugo new about.md
```
### Post front matter
```yaml
---
title: "My Entry"
date: 2024-10-31
draft: false
description: "A brief description shown in meta tags."
summary: "Optional hand-written summary overriding auto-generation."
subtitle: "a quiet meditation on autumn leaves"
tags: ["autumn", "philosophy", "notes"]
author: "Archivist"
featured: true # pins to homepage
nocomments: true # disables comments on this post
---
```
The `<!--more-->` divider can be placed anywhere in the body to manually control where the summary cuts off:
```markdown
This sentence will appear as the summary.
<!--more-->
The rest of the post continues here.
```
---
## Special Pages
### About
Create `content/about.md` with any content. Hugo uses `_default/single.html`.
### Resume
Create `content/resume.md`:
```yaml
---
title: "Resume"
type: "resume"
layout: "single"
resumeName: "Your Name"
resumeTitle: "Your subtitle"
email: "you@example.com"
location: "somewhere cozy"
website: "https://yoursite.com"
github: "yourusername"
resumePDF: "/files/resume.pdf"
_build:
list: never
---
```
Use `##` for sections, `###` for job/entry titles, `####` for subtitle/date lines. Place your PDF at `static/files/resume.pdf`.
### Donate
Create `content/donate.md`:
```yaml
---
title: "Support"
type: "donate"
layout: "single"
_build:
list: never
kofi: "yourusername"
liberapay: "yourusername"
github_sponsors: "yourusername"
bitcoin: "bc1qyouraddress"
ethereum: "0xyouraddress"
monero: "4youraddress"
litecoin: "ltc1youraddress"
---
```
Crypto wallet cards include QR codes generated client-side in the site's amber color palette. Remove any platforms you don't use and they won't appear.
---
## Syntax Highlighting
The theme uses **highlight.js** instead of Hugo's built-in Chroma for better Common Lisp support as it's my preferred language.
This is already added to `layouts/partials/head.html`, and more can be added as you go as shown below:
```html
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/styles/base16/monokai.min.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/highlight.common.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/lisp.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/python.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/r.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/julia.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/bash.min.js"></script>
<script>
hljs.highlightAll();
</script>
```
### Custom code block shortcode
Create `layouts/shortcodes/code.html` in your site root (this one you need to do!! I can't do it for you in advance):
```html
<div class="code-block">
{{- with .Get "lang" }}
<div class="code-block__header">
<span class="code-block__lang">{{ . }}</span>
{{- with $.Get "title" }}
<span class="code-block__title">{{ . }}</span>
{{- end }}
</div>
{{- end }}
<div class="code-block__body">
{{ highlight (trim .Inner "\n") (.Get "lang" | default "text") "" }}
</div>
</div>
```
Use it in posts:
```
{{< code lang="python" title="fibonacci.py" >}}
def fib(n):
return n if n < 2 else fib(n-1) + fib(n-2)
{{< /code >}}
```
---
## LaTeX
I added KaTeX to `layouts/partials/head.html` for math typesetting:
```html
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css">
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.js"></script>
<script defer src="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/contrib/auto-render.min.js"
onload="renderMathInElement(document.body, {
delimiters: [
{left: '$$', right: '$$', display: true},
{left: '$', right: '$', display: false}
]
});">
</script>
```
Then write inline math with `$x^2$` and display math with `$$\int_0^\infty e^{-x}dx$$`.
---
## Comments (Comentario)
Install and run a [Comentario](https://gitlab.com/comentario/comentario) instance, then add to `hugo.toml`:
```toml
[params]
comentarioURL = "https://comments.yourdomain.com"
```
Comments appear automatically on all posts. Disable per-post with `nocomments: true` in front matter.
---
## Color Palette
| Variable | Value | Use |
|--------------------|-----------|------------------------|
| `--amber` | `#d4a228` | Primary accent |
| `--orange` | `#c4601c` | Secondary accent |
| `--rust` | `#8a2e08` | Deep accent |
| `--forest-light` | `#4e7830` | Terminal prompt green |
| `--text-parchment` | `#e8d5a3` | Primary text |
| `--bg-primary` | `#130e07` | Main background |
| `--bg-secondary` | `#1c1509` | Card backgrounds |
Override any variable by adding a `static/css/custom.css` and referencing it in `hugo.toml`:
```toml
[params]
customCSS = ["css/custom.css"]
```
---
## Typography
| Role | Font | Notes |
|----------|--------------|-----------------------------|
| Terminal | VT323 | Headings, nav, UI elements |
| Body | Josefin Sans | Paragraph text, sans-serif |
| Code | Courier Prime| Code blocks, monospace |
All loaded from Google Fonts.
---
## File Structure
```
codex-obscura/
├── archetypes/
│ └── default.md
├── exampleSite/
│ ├── hugo.toml
│ └── content/
│ ├── resume.md
│ └── donate.md
├── layouts/
│ ├── index.html # Homepage
│ ├── _default/
│ │ ├── baseof.html
│ │ ├── single.html # Single post
│ │ └── list.html # Archive / tag pages
│ ├── resume/
│ │ └── single.html # Resume page
│ ├── donate/
│ │ └── single.html # Donate page with QR codes
│ ├── tags/
│ │ └── terms.html # Tag index
│ └── partials/
│ ├── head.html
│ ├── header.html
│ ├── footer.html
│ ├── sidebar.html
│ └── comments.html # Comentario integration
├── static/
│ ├── css/main.css
│ ├── js/main.js # Dust mote animation
│ └── favicon.svg
├── theme.toml
└── README.md
```
---
## License
MIT — Please attribute my work to me!
---
*"The library is infinite and the lights are always low."*