feat: add landing layout and harden rendering

This commit is contained in:
Friday authored and Nuno C. committed 2026-08-17 20:19:02 +01:00
1 parent 405c905754
commit 345f806d80
24 files changed
+353 -193

No files matched your search

+2 -2
View File
@@ -50,9 +50,9 @@ fingerprintAlgorithm = "sha512" # Valid values are "sha512" (default), "sha384",
showScrollToTop = true
[homepage]
layout = "custom" # valid options: page, profile, hero, card, background, custom
layout = "landing" # valid options: page, profile, hero, card, background, landing, custom
# homepageImage = "/img/iceland.jpg" # used in: hero, and card
showRecent = false
showRecent = true
showRecentItems = 12
showMoreLink = true
showMoreLinkDest = "docs"
+22 -22
View File
@@ -1,29 +1,29 @@
---
title: "Welcome to Blowfish! :tada:"
description: "This page was built using the Blowfish theme for Hugo."
title: "Build a site that feels unmistakably yours."
description: "A modern, flexible Hugo theme for blogs, documentation, portfolios, and more."
---
{{< lead >}}
Blowfish gives you expressive layouts, thoughtful defaults, and practical content building blocks, so you can focus on the thing you want to say.
{{< /lead >}}
<div class="flex px-4 py-2 mb-8 text-base rounded-md bg-primary-100 dark:bg-primary-900">
<span class="flex items-center pe-3 text-primary-400">
{{< icon "triangle-exclamation" >}}
</span>
<span class="flex items-center justify-between grow dark:text-neutral-300">
<span class="prose dark:prose-invert">This is a demo of the <code id="layout">background</code> layout.</span>
<button
id="switch-layout-button"
class="px-4 mx-[3px] !text-neutral !no-underline rounded-md bg-primary-600 hover:!bg-primary-500 dark:bg-primary-800 dark:hover:!bg-primary-700"
>
Switch layout &orarr;
</button>
</span>
</div>
{{< cta url="/docs/installation/" label="Get started" >}}
&nbsp;
{{< cta url="/docs/" label="Explore the docs" style="outline" >}}
{{< feature-grid >}}
{{< feature icon="list-check" title="Make it yours" url="/docs/configuration/" >}}
A coherent system of layouts, colours, typography, and content controls.
{{< /feature >}}
{{< feature icon="code" title="Compose faster" url="/docs/shortcodes/" label="Browse shortcodes" >}}
Useful components for richer stories, clearer documentation, and less custom glue.
{{< /feature >}}
{{< feature icon="heart" title="Made in the open" url="/users/" >}}
Explore real sites, community contributions, and patterns that hold up in production.
{{< /feature >}}
{{< /feature-grid >}}
```shell
npx blowfish-tools
```
{{< youtubeLite id="SgXhGb-7QbU" label="Blowfish-tools demo" >}}
{{< alert "circle-info" >}}
This homepage uses Blowfish's built-in `landing` layout and standard shortcodes. No custom homepage template is required.
{{< /alert >}}
@@ -9,7 +9,7 @@ series: ["Documentation"]
series_order: 5
---
Blowfish provides a fully flexible homepage layout. There are two main templates to choose from with additional settings to adjust the design. Alternatively, you can also provide your own template and have complete control over the homepage content.
Blowfish provides flexible homepage layouts with settings to adjust each design. Alternatively, you can also provide your own template and have complete control over the homepage content.
The layout of the homepage is controlled by the `homepage.layout` setting in the `params.toml` configuration file. Additionally, all layouts have the option to include a listing of [recent articles](#recent-articles).
@@ -57,6 +57,12 @@ The card layout is an extension of the page layout. It provides the same level o
To enable the Card layout, set `homepage.layout = "card"` and `homepage.homepageImage` in the `params.toml` configuration file.
## Landing layout
The Landing layout is designed for product sites, documentation hubs, and personal sites that need a stronger opening statement. It gives homepage content a spacious, editorial hero treatment while still rendering standard Markdown and Blowfish shortcodes, so the full page stays portable and easy to maintain.
To enable the Landing layout, set `homepage.layout = "landing"` in the `params.toml` configuration file. Use `content/_index.md` for the title, lead, calls to action, feature grids, and other content.
## Custom layout
@@ -68,7 +74,7 @@ With the configuration value set, create a new `custom.html` file and place it i
To include [recent articles](#recent-articles) on the custom layout, use the `recent-articles/main.html` partial.
As an example, the [homepage]({{< ref "/" >}}) on this site uses the custom layout to allow toggling between the profile and page layouts. Visit the [GitHub repo](https://github.com/nunocoracao/blowfish/blob/main/exampleSite/layouts/partials/home/custom.html) to see how it works.
The included example site uses the built-in Landing layout and standard content shortcodes. Visit the [GitHub repo](https://github.com/nunocoracao/blowfish/tree/main/exampleSite) to see how it is configured.
## Recent articles
+29 -3
View File
@@ -936,7 +936,7 @@ The `tabs` shortcode is commonly used to present different variants of a particu
| `default` | **Optional.** Label of the tab to be active by default. If not set, the first tab will be active. |
| `label` | **Required.** The text label displayed on the tab button. |
| `icon` | **Optional.** Icon name to display before the label. |
| `md` | **Optional.** Render tab content as Markdown (default `true`). Set `md=false` to allow nested shortcodes inside tab content. |
| `md` | **Optional.** Render tab content as Markdown (default `true`). Use `md=false` when the content is already HTML. |
**Example 1: Basic Usage**
@@ -963,7 +963,7 @@ The `tabs` shortcode is commonly used to present different variants of a particu
```
{{</* /tab */>}}
{{</* tab label="Linux" md=false */>}}
{{</* tab label="Linux" */>}}
{{</* alert */>}}See [documentation](https://code.visualstudio.com/docs/setup/linux#_install-vs-code-on-linux).{{</* /alert */>}}
{{</* /tab */>}}
@@ -994,12 +994,38 @@ The `tabs` shortcode is commonly used to present different variants of a particu
```
{{< /tab >}}
{{< tab label="Linux" md=false >}}
{{< tab label="Linux" >}}
{{< alert >}}See [documentation](https://code.visualstudio.com/docs/setup/linux#_install-vs-code-on-linux).{{< /alert >}}
{{< /tab >}}
{{< /tabs >}}
Nested shortcodes are supported with the default Markdown behaviour. For example, an accordion can live inside a tab without its generated HTML being rendered as Markdown a second time:
`````md
{{</* tabs */>}}
{{</* tab label="Details" */>}}
{{</* accordion mode="open" */>}}
{{</* accordionItem title="What is included?" */>}}
- Responsive behaviour
- Accessible markup
{{</* /accordionItem */>}}
{{</* /accordion */>}}
{{</* /tab */>}}
{{</* /tabs */>}}
`````
{{< tabs >}}
{{< tab label="Details" >}}
{{< accordion mode="open" >}}
{{< accordionItem title="What is included?" >}}
- Responsive behaviour
- Accessible markup
{{< /accordionItem >}}
{{< /accordion >}}
{{< /tab >}}
{{< /tabs >}}
**Example 2: With Group, Default, and Icon**
`````md
@@ -17,4 +17,4 @@ Emoji-Ersetzungen erfolgen in Blowfish automatisch, sodass Sie Kurzcode in Ihren
**Beispiel:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
Der [Emoji-Spickzettel](http://www.emoji-cheat-sheet.com/) ist eine nützliche Referenz für Emoji-Kurzcodes.
Hugos [Emoji-Referenz](https://gohugo.io/quick-reference/emojis/) enthält unterstützte Emoji-Kurzcodes.
@@ -17,4 +17,4 @@ Los reemplazos de emoji son automáticos en Blowfish, por lo que puedes usar có
**Ejemplo:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
La [hoja de trucos de Emoji](http://www.emoji-cheat-sheet.com/) es una referencia útil para los códigos abreviados de emoji.
La [referencia de emoji de Hugo](https://gohugo.io/quick-reference/emojis/) contiene los códigos abreviados compatibles.
@@ -17,4 +17,4 @@ Les remplacements d'emoji sont automatiques dans Blowfish, vous pouvez donc util
**Exemple :** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
L'[aide-mémoire Emoji](http://www.emoji-cheat-sheet.com/) est une référence utile pour les codes abrégés emoji.
La [référence emoji de Hugo](https://gohugo.io/quick-reference/emojis/) contient les codes abrégés pris en charge.
@@ -17,4 +17,4 @@ Emoji replacements are automatic throughout Blowfish, so you can use shorthand c
**Example:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
The [Emoji cheat sheet](http://www.emoji-cheat-sheet.com/) is a useful reference for emoji shorthand codes.
Use Hugo's [emoji reference](https://gohugo.io/quick-reference/emojis/) for supported shorthand codes.
@@ -17,4 +17,4 @@ type: 'sample'
**例:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:
[絵文字チートシート](http://www.emoji-cheat-sheet.com/)は絵文字ショートハンドコードのための便利な参照ページです。
対応する絵文字ショートハンドコードは、Hugo の[絵文字リファレンス](https://gohugo.io/quick-reference/emojis/)を参照してください。
+1 -1
View File
@@ -17,4 +17,4 @@ Emoji replacements are automatic throughout Blowfish, so you can use shorthand c
**Example:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
The [Emoji cheat sheet](http://www.emoji-cheat-sheet.com/) is a useful reference for emoji shorthand codes.
Use Hugo's [emoji reference](https://gohugo.io/quick-reference/emojis/) for supported shorthand codes.
@@ -17,4 +17,4 @@ As substituições de emoji são automáticas em todo o Blowfish, então você p
**Exemplo:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
A [folha de dicas de Emoji](http://www.emoji-cheat-sheet.com/) é uma referência útil para códigos abreviados de emoji.
Use a [referência de emojis do Hugo](https://gohugo.io/quick-reference/emojis/) para consultar os códigos abreviados compatíveis.
@@ -17,4 +17,4 @@ As substituições de emoji são automáticas em todo o Blowfish, pelo que pode
**Exemplo:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
A [folha de referência de Emoji](http://www.emoji-cheat-sheet.com/) é uma referência útil para códigos abreviados de emoji.
Consulte a [referência de emojis do Hugo](https://gohugo.io/quick-reference/emojis/) para os códigos abreviados suportados.
@@ -17,4 +17,4 @@ Blowfish 会自动的进行表情符号渲染,因此您可以在内容和 fron
**例如:** `see_no_evil` :see_no_evil:, `hear_no_evil` :hear_no_evil:, `speak_no_evil` :speak_no_evil:.
[Emoji 清单](http://www.emoji-cheat-sheet.com/) 可以很方便的查找 Emoji 对应的表情代码。
请使用 Hugo 的 [Emoji 参考](https://gohugo.io/quick-reference/emojis/) 查阅受支持的简写代码。
+29 -67
View File
@@ -1,70 +1,32 @@
{{ $jsHome := resources.Get "js/home.js" | resources.Minify | resources.Fingerprint (.Site.Params.fingerprintAlgorithm | default "sha512") }}
<div class="relative isolate overflow-hidden">
<div aria-hidden="true" class="absolute inset-x-0 -top-40 -z-10 transform-gpu overflow-hidden blur-3xl sm:-top-80">
<div class="relative left-[calc(50%-11rem)] aspect-[1155/678] w-[36rem] -translate-x-1/2 rotate-[30deg] bg-gradient-to-tr from-primary-400 to-secondary-500 opacity-20 sm:left-[calc(50%-30rem)] sm:w-[72rem]"></div>
</div>
<section class="mx-auto max-w-7xl px-4 pb-14 pt-12 sm:px-6 sm:pb-20 sm:pt-20 lg:px-8">
<div class="mx-auto max-w-4xl text-center">
<p class="mb-5 inline-flex items-center gap-2 rounded-full border border-primary-200 bg-primary-50 px-4 py-1.5 text-sm font-semibold text-primary-700 dark:border-primary-900 dark:bg-primary-950/50 dark:text-primary-300">
{{ partial "icon.html" "wand-magic-sparkles" }}
The modern Hugo theme toolkit
</p>
<h1 class="text-balance text-5xl font-black tracking-tight text-neutral-950 dark:text-white sm:text-7xl">
Build a site that feels unmistakably yours.
</h1>
<p class="mx-auto mt-6 max-w-2xl text-pretty text-lg leading-8 text-neutral-600 dark:text-neutral-300 sm:text-xl">
Blowfish combines expressive layouts, thoughtful defaults, and practical building blocks for blogs, docs, portfolios, and everything in between.
</p>
<div class="mt-9 flex flex-wrap items-center justify-center gap-3">
<a class="inline-flex items-center gap-2 rounded-xl bg-primary-600 px-5 py-3 font-semibold text-white shadow-lg shadow-primary-500/20 transition hover:-translate-y-0.5 hover:bg-primary-500 focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600" href="{{ "docs/installation" | relLangURL }}">
Get started
{{ partial "icon.html" "link" }}
</a>
<a class="inline-flex items-center gap-2 rounded-xl border border-neutral-300 bg-white/70 px-5 py-3 font-semibold text-neutral-800 transition hover:border-primary-400 hover:text-primary-600 dark:border-neutral-700 dark:bg-neutral-900/70 dark:text-neutral-100 dark:hover:text-primary-400" href="{{ "docs" | relLangURL }}">
Explore the docs
{{ partial "icon.html" "file-lines" }}
</a>
</div>
</div>
<div class="mx-auto mt-14 grid max-w-5xl gap-4 sm:grid-cols-3">
<a class="group rounded-2xl border border-neutral-200 bg-white/70 p-6 shadow-sm transition hover:-translate-y-1 hover:border-primary-300 hover:shadow-xl hover:shadow-primary-500/10 dark:border-neutral-800 dark:bg-neutral-900/70 dark:hover:border-primary-700" href="{{ "docs/configuration" | relLangURL }}">
<span class="mb-5 inline-flex rounded-xl bg-primary-100 p-3 text-primary-600 dark:bg-primary-950 dark:text-primary-400">{{ partial "icon.html" "list-check" }}</span>
<h2 class="text-lg font-bold text-neutral-950 dark:text-white">Make it yours</h2>
<p class="mt-2 text-sm leading-6 text-neutral-600 dark:text-neutral-400">A coherent system of layouts, colours, typography, and content controls.</p>
</a>
<a class="group rounded-2xl border border-neutral-200 bg-white/70 p-6 shadow-sm transition hover:-translate-y-1 hover:border-secondary-300 hover:shadow-xl hover:shadow-secondary-500/10 dark:border-neutral-800 dark:bg-neutral-900/70 dark:hover:border-secondary-700" href="{{ "docs/shortcodes" | relLangURL }}">
<span class="mb-5 inline-flex rounded-xl bg-secondary-100 p-3 text-secondary-600 dark:bg-secondary-950 dark:text-secondary-400">{{ partial "icon.html" "code" }}</span>
<h2 class="text-lg font-bold text-neutral-950 dark:text-white">Compose faster</h2>
<p class="mt-2 text-sm leading-6 text-neutral-600 dark:text-neutral-400">Useful shortcodes for richer stories, clearer documentation, and less custom glue.</p>
</a>
<a class="group rounded-2xl border border-neutral-200 bg-white/70 p-6 shadow-sm transition hover:-translate-y-1 hover:border-primary-300 hover:shadow-xl hover:shadow-primary-500/10 dark:border-neutral-800 dark:bg-neutral-900/70 dark:hover:border-primary-700" href="{{ "users" | relLangURL }}">
<span class="mb-5 inline-flex rounded-xl bg-primary-100 p-3 text-primary-600 dark:bg-primary-950 dark:text-primary-400">{{ partial "icon.html" "heart" }}</span>
<h2 class="text-lg font-bold text-neutral-950 dark:text-white">Made in the open</h2>
<p class="mt-2 text-sm leading-6 text-neutral-600 dark:text-neutral-400">A growing collection of real sites, community contributions, and useful patterns.</p>
</a>
</div>
</section>
<section class="border-y border-neutral-200 bg-neutral-50/70 py-12 dark:border-neutral-800 dark:bg-neutral-900/40">
<div class="mx-auto max-w-7xl px-4 sm:px-6 lg:px-8">
<div class="mb-8 flex flex-col justify-between gap-4 sm:flex-row sm:items-end">
<div>
<p class="text-sm font-bold uppercase tracking-[0.18em] text-primary-600 dark:text-primary-400">Fresh from the reef</p>
<h2 class="mt-2 text-3xl font-black tracking-tight text-neutral-950 dark:text-white">See the theme in motion.</h2>
</div>
<a class="inline-flex items-center gap-2 font-semibold text-primary-600 hover:text-primary-500 dark:text-primary-400" href="{{ "docs" | relLangURL }}">Browse all documentation {{ partial "icon.html" "link" }}</a>
</div>
{{ partial "recent-articles-demo.html" . }}
</div>
</section>
<section class="mx-auto max-w-7xl px-4 py-16 sm:px-6 lg:px-8">
{{ partial "sponsors.html" . }}
{{ partial "contributors.html" . }}
</section>
<div id="background">
{{ partial "home/background.html" . }}
</div>
<div id="hero" style="display:none">
{{ partial "home/hero.html" . }}
</div>
<div id="profile" style="display:none">
{{ partial "home/profile.html" . }}
</div>
<div id="card" style="display:none">
{{ partial "home/card.html" . }}
</div>
<div id="page" style="display:none">
{{ partial "home/page.html" . }}
</div>
<section class="max-w-7xl mx-auto px-4">
{{ partial "sponsors.html" . }}
</section>
<script defer type="text/javascript" src="{{ $jsHome.RelPermalink }}" integrity="{{ $jsHome.Data.Integrity }}"></script>
<section class="max-w-7xl mx-auto px-4">
{{ partial "contributors.html" . }}
</section>
<section>
{{ partial "recent-articles-demo.html" . }}
</section>
<script
defer
type="text/javascript"
src="{{ $jsHome.RelPermalink }}"
integrity="{{ $jsHome.Data.Integrity }}"></script>