jekyll-theme-docsteer 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (53) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +21 -0
  3. data/README.md +107 -0
  4. data/_data/navigation.yml +44 -0
  5. data/_includes/buy-me-a-coffee.html +10 -0
  6. data/_includes/doc-footer.html +38 -0
  7. data/_includes/faq-list.html +52 -0
  8. data/_includes/footer.html +43 -0
  9. data/_includes/head-custom.html +4 -0
  10. data/_includes/head.html +61 -0
  11. data/_includes/navbar.html +70 -0
  12. data/_includes/scripts.html +22 -0
  13. data/_includes/search-modal.html +24 -0
  14. data/_includes/sidebar.html +48 -0
  15. data/_includes/toc.html +11 -0
  16. data/_layouts/default.html +45 -0
  17. data/_layouts/doc.html +37 -0
  18. data/_layouts/faq.html +51 -0
  19. data/_layouts/home.html +74 -0
  20. data/_layouts/page.html +13 -0
  21. data/_sass/docsteer/_base.scss +56 -0
  22. data/_sass/docsteer/_components.scss +166 -0
  23. data/_sass/docsteer/_content.scss +300 -0
  24. data/_sass/docsteer/_faq.scss +140 -0
  25. data/_sass/docsteer/_footer.scss +51 -0
  26. data/_sass/docsteer/_home.scss +184 -0
  27. data/_sass/docsteer/_layout.scss +52 -0
  28. data/_sass/docsteer/_lightbox.scss +73 -0
  29. data/_sass/docsteer/_navbar.scss +169 -0
  30. data/_sass/docsteer/_print.scss +13 -0
  31. data/_sass/docsteer/_reset.scss +57 -0
  32. data/_sass/docsteer/_responsive.scss +31 -0
  33. data/_sass/docsteer/_search.scss +98 -0
  34. data/_sass/docsteer/_sidebar.scss +159 -0
  35. data/_sass/docsteer/_skins.scss +193 -0
  36. data/_sass/docsteer/_syntax.scss +72 -0
  37. data/_sass/docsteer/_toc.scss +46 -0
  38. data/_sass/docsteer/_tokens.scss +96 -0
  39. data/_sass/docsteer/_utilities.scss +18 -0
  40. data/_sass/docsteer.scss +22 -0
  41. data/assets/css/main.scss +4 -0
  42. data/assets/images/favicon.svg +14 -0
  43. data/assets/images/logo.svg +14 -0
  44. data/assets/js/lightbox.js +96 -0
  45. data/assets/js/main.js +275 -0
  46. data/assets/js/search.js +186 -0
  47. data/assets/vendor/fontawesome/NOTICE.md +18 -0
  48. data/assets/vendor/fontawesome/css/all.min.css +9 -0
  49. data/assets/vendor/fontawesome/webfonts/fa-brands-400.woff2 +0 -0
  50. data/assets/vendor/fontawesome/webfonts/fa-regular-400.woff2 +0 -0
  51. data/assets/vendor/fontawesome/webfonts/fa-solid-900.woff2 +0 -0
  52. data/assets/vendor/fontawesome/webfonts/fa-v4compatibility.woff2 +0 -0
  53. metadata +190 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 0b49a45ae03e89044c653d5cae4fa3749d6b3c4a3d7c6837555a383242700ee3
4
+ data.tar.gz: 1f9b744dc050ff685596ba7d853ed230cdf08224d4aa9caceead2363470ec14e
5
+ SHA512:
6
+ metadata.gz: c506de353cb020505952ca9bd4b6c7e69f1bddc933c538e0d1bbc58beaf0f01cedddf9becacf21ca7c2dc17677a6c2cb028a0a56533fa41ecba9af3463f2cfa7
7
+ data.tar.gz: 046a10b8e0e8814a576703ef264c368ae356464d71cb28baf83ed2bf4f2ba4cf44000912a9363a14ee162fd8c1c63445d38f51174a5cd1aff6d5e27fdafb9854
data/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Cristian Castellari
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,107 @@
1
+ # DocSteer
2
+
3
+ **Simple, searchable docs and knowledge bases for teams** — a fast,
4
+ framework-free Jekyll theme for technical documentation, help centres and
5
+ internal wikis.
6
+
7
+ [**Live demo**](https://Skyflash.github.io/docsteer) ·
8
+ [Documentation](https://Skyflash.github.io/docsteer/docs/introduction/) ·
9
+ MIT licensed
10
+
11
+ ![DocSteer](assets/images/screenshot.png)
12
+
13
+ ---
14
+
15
+ ## Features
16
+
17
+ | | |
18
+ | --- | --- |
19
+ | 🎨 **6 colour skins** | `aqua`, `violet`, `mint`, `ember`, `graphite`, `clay` — each with light **and** dark, switchable in `_config.yml` or live in the navbar |
20
+ | 🌗 **Dark mode** | Follows the OS, or a manual toggle stored in `localStorage`, no flash on load |
21
+ | 🔍 **Live search** | Prebuilt JSON index + keyboard-driven modal (`/`, <kbd>⌘K</kbd>), zero dependencies |
22
+ | 🖼️ **Image lightbox** | Click-to-zoom, galleries, captions, keyboard nav |
23
+ | 📑 **Auto TOC** | Built from your headings, with scroll-spy |
24
+ | ❓ **FAQ pages** | `layout: faq` — accordion built on native `<details>`, deep-linkable questions, indexed by the search, `FAQPage` structured data |
25
+ | 📱 **Responsive & pixel-perfect** | 320 px phones → ultrawide, real mobile drawer |
26
+ | ⚡ **Fast** | ~7 kB vanilla JS (all deferred), compressed CSS, `preconnect`/`preload` |
27
+ | 🔎 **SEO ready** | `jekyll-seo-tag`, sitemap, RSS, Open Graph, JSON-LD |
28
+ | ✏️ **Easy to customise** | All colours in one Sass map, documented CSS tokens, upgrade-safe override files |
29
+ | 🧩 **Font Awesome** | 6.5.2 Free, **bundled locally** by default (offline / firewall-safe); CDN optional |
30
+ | ☕ **Buy me a coffee** | Optional support button (navbar / sidebar / footer) |
31
+
32
+ ## Quick start
33
+
34
+ ```bash
35
+ git clone https://github.com/Skyflash/docsteer.git
36
+ cd docsteer
37
+ bundle install
38
+ bundle exec jekyll serve --livereload
39
+ # → http://localhost:4000
40
+ ```
41
+
42
+ Then:
43
+
44
+ 1. Edit **`_config.yml`** — everything is under the `docsteer:` key.
45
+ 2. Pick a skin: `docsteer: { skin: violet }`.
46
+ 3. Add pages to **`_docs/`** and list them in **`_data/navigation.yml`**.
47
+
48
+ Full guide: [`/docs/introduction/`](https://Skyflash.github.io/docsteer/docs/introduction/).
49
+
50
+ ## Project layout
51
+
52
+ ```
53
+ _config.yml All theme options (docsteer: key)
54
+ _data/navigation.yml Top nav + grouped sidebar
55
+ _layouts/ default · home · doc · page
56
+ _includes/ header, sidebar, footer, search modal, TOC (overridable)
57
+ _includes/head-custom.html ← your meta/fonts; never overwritten by upgrades
58
+ _sass/docsteer/ one partial per concern
59
+ _sass/docsteer/_skins.scss ← all six palettes live here
60
+ assets/js/ main.js · search.js · lightbox.js (independent)
61
+ assets/css/main.scss entry point
62
+ search.json search index (Liquid-generated)
63
+ _docs/ the theme's own documentation (sample content)
64
+ ```
65
+
66
+ ## Configuration
67
+
68
+ See [`_docs/configuration.md`](_docs/configuration.md) or the rendered
69
+ [Configuration page](https://Skyflash.github.io/docsteer/docs/configuration/).
70
+ Highlights:
71
+
72
+ ```yaml
73
+ docsteer:
74
+ skin: aqua # aqua | violet | mint | ember | graphite | clay
75
+ mode: auto # auto | light | dark
76
+ search: { enabled: true, collections: [docs], hotkey: true }
77
+ lightbox: { enabled: true }
78
+ toc: { enabled: true, min_headings: 2 }
79
+ buy_me_a_coffee: { username: "cristiancastellari", show_in: [navbar, footer] }
80
+ footer: { show_credit: true }
81
+ ```
82
+
83
+ ## Deploying
84
+
85
+ GitHub Pages (via Actions), Netlify, Vercel, Cloudflare Pages — see
86
+ [`_docs/deploying.md`](_docs/deploying.md). Build command
87
+ `bundle exec jekyll build`, publish `_site/`.
88
+
89
+ ## Customising
90
+
91
+ - **Colours** — edit the map in `_sass/docsteer/_skins.scss`; every value
92
+ becomes a CSS custom property.
93
+ - **Sizing / fonts** — `_sass/docsteer/_tokens.scss`.
94
+ - **Head tags** — `_includes/head-custom.html` (kept empty so upgrades are safe).
95
+ - **Add a skin** — map entry + navbar list entry + `.skin-dot--name` gradient.
96
+
97
+ ## License
98
+
99
+ [MIT](LICENSE). Attribution appreciated, not required
100
+ (`footer.show_credit: false` to remove it).
101
+ Font Awesome is under its own [Free License](https://fontawesome.com/license/free).
102
+
103
+ ## Support
104
+
105
+ If DocSteer saved you time, you can
106
+ [**buy me a coffee** ☕](https://www.buymeacoffee.com/cristiancastellari). Bug reports and
107
+ PRs welcome in [Issues](https://github.com/Skyflash/docsteer/issues).
@@ -0,0 +1,44 @@
1
+ # Top navigation (navbar)
2
+ main:
3
+ - title: Docs
4
+ url: /docs/introduction/
5
+ icon: fa-solid fa-book
6
+ - title: Guides
7
+ url: /docs/live-search/
8
+ icon: fa-solid fa-compass
9
+ - title: Blog
10
+ url: /blog/
11
+ icon: fa-solid fa-newspaper
12
+
13
+ # Left sidebar — grouped. `open: true` forces a group expanded.
14
+ sidebar:
15
+ - title: Getting started
16
+ icon: fa-solid fa-rocket
17
+ open: true
18
+ children:
19
+ - { title: Introduction, url: /docs/introduction/ }
20
+ - { title: Installation, url: /docs/installation/ }
21
+ - { title: Your first docs site, url: /docs/first-docs-site/ }
22
+ - { title: Your first knowledge base, url: /docs/first-knowledge-base/ }
23
+ - { title: Your first FAQ, url: /docs/first-faq/ }
24
+ - { title: Configuration, url: /docs/configuration/ }
25
+
26
+ - title: Customisation
27
+ icon: fa-solid fa-paintbrush
28
+ children:
29
+ - { title: Colour skins, url: /docs/skins/, badge: "6" }
30
+ - { title: Navigation, url: /docs/navigation/ }
31
+ - { title: Writing content, url: /docs/writing-content/ }
32
+
33
+ - title: Features
34
+ icon: fa-solid fa-wand-magic-sparkles
35
+ children:
36
+ - { title: Live search, url: /docs/live-search/ }
37
+ - { title: Image lightbox, url: /docs/lightbox/ }
38
+ - { title: SEO & performance, url: /docs/seo-performance/ }
39
+
40
+ - title: Reference
41
+ icon: fa-solid fa-circle-info
42
+ children:
43
+ - { title: Deploying, url: /docs/deploying/ }
44
+ - { title: FAQ, url: /docs/faq/ }
@@ -0,0 +1,10 @@
1
+ {%- assign bmc = site.docsteer.buy_me_a_coffee -%}
2
+ {%- if bmc.username -%}
3
+ <a class="bmc{% if include.compact %} bmc--compact{% endif %}"
4
+ href="https://www.buymeacoffee.com/{{ bmc.username }}"
5
+ target="_blank" rel="noopener"
6
+ aria-label="{{ bmc.label | default: 'Buy me a coffee' }}">
7
+ <i class="fa-solid fa-mug-hot" aria-hidden="true"></i>
8
+ {%- unless include.compact %}<span>{{ bmc.label | default: "Buy me a coffee" }}</span>{%- endunless -%}
9
+ </a>
10
+ {%- endif -%}
@@ -0,0 +1,38 @@
1
+ {%- comment -%} Prev / next navigation across the sidebar order {%- endcomment -%}
2
+ {%- assign flat = "" | split: "" -%}
3
+ {%- for group in site.data.navigation.sidebar -%}
4
+ {%- for link in group.children -%}
5
+ {%- assign flat = flat | push: link -%}
6
+ {%- endfor -%}
7
+ {%- endfor -%}
8
+ {%- assign idx = -1 -%}
9
+ {%- for link in flat -%}
10
+ {%- if link.url == page.url -%}{%- assign idx = forloop.index0 -%}{%- endif -%}
11
+ {%- endfor -%}
12
+
13
+ {% if idx >= 0 %}
14
+ <nav class="doc-pager" aria-label="Documentation pages">
15
+ {% if idx > 0 %}
16
+ {%- assign prev = flat[idx | minus: 1] -%}
17
+ <a class="doc-pager__link doc-pager__prev" href="{{ prev.url | relative_url }}">
18
+ <span class="doc-pager__dir"><i class="fa-solid fa-arrow-left" aria-hidden="true"></i> Previous</span>
19
+ <span class="doc-pager__title">{{ prev.title }}</span>
20
+ </a>
21
+ {% else %}<span></span>{% endif %}
22
+
23
+ {%- assign last = flat.size | minus: 1 -%}
24
+ {% if idx < last %}
25
+ {%- assign next = flat[idx | plus: 1] -%}
26
+ <a class="doc-pager__link doc-pager__next" href="{{ next.url | relative_url }}">
27
+ <span class="doc-pager__dir">Next <i class="fa-solid fa-arrow-right" aria-hidden="true"></i></span>
28
+ <span class="doc-pager__title">{{ next.title }}</span>
29
+ </a>
30
+ {% endif %}
31
+ </nav>
32
+ {% endif %}
33
+
34
+ {% if page.tags and page.tags.size > 0 %}
35
+ <div class="doc-tags">
36
+ {% for t in page.tags %}<span class="badge badge--soft">#{{ t }}</span>{% endfor %}
37
+ </div>
38
+ {% endif %}
@@ -0,0 +1,52 @@
1
+ {%- comment -%}
2
+ DocSteer — FAQ accordion.
3
+
4
+ Params:
5
+ include.items — array of { q, a, section? }
6
+
7
+ Answers are Markdown. Liquid does not run inside front matter, so a
8
+ root-relative link written as ](/docs/x/) is rewritten through site.baseurl
9
+ here — authors keep writing plain Markdown and the links survive a baseurl.
10
+ {%- endcomment -%}
11
+ {%- assign cfg = site.docsteer.faq -%}
12
+ {%- assign items = include.items -%}
13
+ {%- if items and items.size > 0 -%}
14
+ {%- capture link_prefix -%}]({{ site.baseurl }}/{%- endcapture -%}
15
+ <div class="faq" id="faq">
16
+ {%- if cfg.expand_all_button %}
17
+ <div class="faq__tools">
18
+ <button type="button" class="faq__toggle-all" id="faqToggleAll" data-expanded="false">
19
+ <i class="fa-solid fa-angles-down" aria-hidden="true"></i>
20
+ <span>Expand all</span>
21
+ </button>
22
+ </div>
23
+ {%- endif %}
24
+
25
+ {%- assign groups = items | group_by: "section" -%}
26
+ {%- assign idx = 0 -%}
27
+ {%- for g in groups %}
28
+ {%- if g.name and g.name != "" %}
29
+ <h2 class="faq__section" id="{{ g.name | slugify }}">{{ g.name }}</h2>
30
+ {%- endif %}
31
+ <div class="faq__group">
32
+ {%- for item in g.items %}
33
+ {%- assign idx = idx | plus: 1 -%}
34
+ {%- assign qid = item.q | slugify -%}
35
+ <details class="faq-item" id="{{ qid }}"{% if idx == 1 and cfg.expand_first %} open{% endif %}>
36
+ <summary class="faq-item__q">
37
+ {%- comment -%}Inline Markdown, so a question can carry `code`.{%- endcomment -%}
38
+ <span class="faq-item__text">{{ item.q | markdownify | remove: "<p>" | remove: "</p>" | strip }}</span>
39
+ <i class="fa-solid fa-chevron-down faq-item__chevron" aria-hidden="true"></i>
40
+ </summary>
41
+ <div class="faq-item__a">
42
+ {{ item.a | replace: "](/", link_prefix | markdownify }}
43
+ <a class="faq-item__permalink" href="#{{ qid }}" aria-label="Link to this question">
44
+ <i class="fa-solid fa-link" aria-hidden="true"></i>
45
+ </a>
46
+ </div>
47
+ </details>
48
+ {%- endfor %}
49
+ </div>
50
+ {%- endfor %}
51
+ </div>
52
+ {%- endif -%}
@@ -0,0 +1,43 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <footer class="site-footer">
3
+ <div class="site-footer__inner">
4
+ <div class="site-footer__brand">
5
+ <a class="brand" href="{{ '/' | relative_url }}">
6
+ {% if cfg.logo %}<img class="brand__logo" src="{{ cfg.logo | relative_url }}" alt="{{ site.title }}">
7
+ {% else %}<span class="brand__mark">{{ site.title | slice: 0, 1 | upcase }}</span>{% endif %}
8
+ <span class="brand__name">{{ site.title }}</span>
9
+ </a>
10
+ <p class="site-footer__tag">{{ site.tagline | default: site.description }}</p>
11
+
12
+ <div class="site-footer__social">
13
+ {% if cfg.social.github %}<a href="https://github.com/{{ cfg.social.github }}" rel="noopener" aria-label="GitHub"><i class="fa-brands fa-github" aria-hidden="true"></i></a>{% endif %}
14
+ {% if cfg.social.linkedin %}<a href="{{ cfg.social.linkedin }}" rel="noopener" aria-label="LinkedIn"><i class="fa-brands fa-linkedin-in" aria-hidden="true"></i></a>{% endif %}
15
+ {% if cfg.social.twitter %}<a href="https://twitter.com/{{ cfg.social.twitter }}" rel="noopener" aria-label="Twitter / X"><i class="fa-brands fa-x-twitter" aria-hidden="true"></i></a>{% endif %}
16
+ {% if cfg.social.mastodon %}<a href="{{ cfg.social.mastodon }}" rel="me noopener" aria-label="Mastodon"><i class="fa-brands fa-mastodon" aria-hidden="true"></i></a>{% endif %}
17
+ {% if cfg.social.discord %}<a href="{{ cfg.social.discord }}" rel="noopener" aria-label="Discord"><i class="fa-brands fa-discord" aria-hidden="true"></i></a>{% endif %}
18
+ {% if cfg.social.email %}<a href="mailto:{{ cfg.social.email }}" aria-label="Email"><i class="fa-solid fa-envelope" aria-hidden="true"></i></a>{% endif %}
19
+ {% if cfg.social.rss %}<a href="{{ '/feed.xml' | relative_url }}" aria-label="RSS feed"><i class="fa-solid fa-rss" aria-hidden="true"></i></a>{% endif %}
20
+ </div>
21
+ </div>
22
+
23
+ <nav class="site-footer__nav" aria-label="Footer">
24
+ {% for l in cfg.footer.links %}
25
+ <a href="{{ l.url | relative_url }}">{{ l.label }}</a>
26
+ {% endfor %}
27
+ </nav>
28
+ </div>
29
+
30
+ <div class="site-footer__bar">
31
+ <span>© {{ site.time | date: "%Y" }} {{ cfg.footer.copyright | default: site.title }}. All rights reserved.</span>
32
+ <span class="site-footer__right">
33
+ {% if cfg.buy_me_a_coffee.username and cfg.buy_me_a_coffee.show_in contains "footer" %}
34
+ {% include buy-me-a-coffee.html %}
35
+ {% endif %}
36
+ {% if cfg.footer.show_credit %}
37
+ <span class="site-footer__credit">Built with
38
+ <a href="https://github.com/Skyflash/docsteer" rel="noopener">DocSteer</a>
39
+ </span>
40
+ {% endif %}
41
+ </span>
42
+ </div>
43
+ </footer>
@@ -0,0 +1,4 @@
1
+ {%- comment -%}
2
+ Add your own <meta>, fonts, or verification tags here.
3
+ This file is intentionally empty so upgrades never clobber your changes.
4
+ {%- endcomment -%}
@@ -0,0 +1,61 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <head>
3
+ <meta charset="utf-8">
4
+ <meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover">
5
+ <meta name="theme-color" content="#ffffff" media="(prefers-color-scheme: light)">
6
+ <meta name="theme-color" content="#0d1117" media="(prefers-color-scheme: dark)">
7
+
8
+ {%- comment -%} Set skin / mode before paint to avoid a flash {%- endcomment -%}
9
+ <script>
10
+ (function () {
11
+ try {
12
+ var r = document.documentElement;
13
+ var m = localStorage.getItem('docsteer-mode');
14
+ var s = localStorage.getItem('docsteer-skin');
15
+ if (m) r.setAttribute('data-mode', m);
16
+ if (s) r.setAttribute('data-skin', s);
17
+ } catch (e) {}
18
+ })();
19
+ </script>
20
+
21
+ {% seo %}
22
+
23
+ {% if cfg.favicon %}
24
+ <link rel="icon" href="{{ cfg.favicon | relative_url }}">
25
+ {% else %}
26
+ <link rel="icon" href="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 100 100'%3E%3Crect width='100' height='100' rx='22' fill='%232f81f7'/%3E%3Ctext x='50' y='68' font-size='58' text-anchor='middle' fill='white' font-family='sans-serif' font-weight='700'%3ED%3C/text%3E%3C/svg%3E">
27
+ {% endif %}
28
+
29
+ {% if cfg.fontawesome.enabled %}
30
+ {% if cfg.fontawesome.source == "cdn" %}
31
+ <link rel="preconnect" href="https://cdnjs.cloudflare.com" crossorigin>
32
+ <link rel="stylesheet" href="{{ cfg.fontawesome.cdn_url }}"
33
+ {% if cfg.fontawesome.cdn_integrity and cfg.fontawesome.cdn_integrity != "" %}integrity="{{ cfg.fontawesome.cdn_integrity }}" crossorigin="anonymous" referrerpolicy="no-referrer"{% endif %}>
34
+ {% else %}
35
+ {%- assign fa_css = '/assets/vendor/fontawesome/css/all.min.css' | relative_url -%}
36
+ <link rel="preload" as="font" type="font/woff2" crossorigin
37
+ href="{{ '/assets/vendor/fontawesome/webfonts/fa-solid-900.woff2' | relative_url }}">
38
+ <link rel="stylesheet" href="{{ fa_css }}">
39
+ {% endif %}
40
+ {% endif %}
41
+
42
+ <link rel="stylesheet" href="{{ '/assets/css/main.css' | relative_url }}">
43
+
44
+ {% if site.feed.path %}
45
+ <link rel="alternate" type="application/atom+xml" title="{{ site.title }}" href="{{ '/feed.xml' | relative_url }}">
46
+ {% endif %}
47
+
48
+ {% if cfg.search.enabled %}
49
+ <link rel="preload" as="fetch" href="{{ '/search.json' | relative_url }}" crossorigin>
50
+ {% endif %}
51
+
52
+ {% if cfg.analytics.plausible_domain %}
53
+ <script defer data-domain="{{ cfg.analytics.plausible_domain }}" src="https://plausible.io/js/script.js"></script>
54
+ {% endif %}
55
+ {% if cfg.analytics.ga4_id %}
56
+ <script async src="https://www.googletagmanager.com/gtag/js?id={{ cfg.analytics.ga4_id }}"></script>
57
+ <script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag('js',new Date());gtag('config','{{ cfg.analytics.ga4_id }}');</script>
58
+ {% endif %}
59
+
60
+ {% include head-custom.html %}
61
+ </head>
@@ -0,0 +1,70 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <header class="navbar" id="navbar">
3
+ <div class="navbar__inner">
4
+ <button class="navbar__burger" id="sidebarToggle" aria-label="Open menu" aria-expanded="false">
5
+ <i class="fa-solid fa-bars" aria-hidden="true"></i>
6
+ </button>
7
+
8
+ <a class="brand" href="{{ '/' | relative_url }}">
9
+ {% if cfg.logo %}
10
+ <img class="brand__logo" src="{{ cfg.logo | relative_url }}" alt="{{ site.title }}">
11
+ {% else %}
12
+ <span class="brand__mark">{{ site.title | slice: 0, 1 | upcase }}</span>
13
+ {% endif %}
14
+ <span class="brand__name">{{ site.title }}</span>
15
+ </a>
16
+
17
+ <nav class="navbar__links" aria-label="Primary">
18
+ {% for item in site.data.navigation.main %}
19
+ <a href="{{ item.url | relative_url }}"
20
+ class="navbar__link{% if page.url contains item.url and item.url != '/' %} is-active{% endif %}">
21
+ {% if item.icon %}<i class="{{ item.icon }}" aria-hidden="true"></i>{% endif %}{{ item.title }}
22
+ </a>
23
+ {% endfor %}
24
+ </nav>
25
+
26
+ <div class="navbar__tools">
27
+ {% if cfg.search.enabled %}
28
+ <button class="navbar__icon-btn" data-search-open aria-label="Search"
29
+ title="Search{% if cfg.search.hotkey %} (press /)" data-hotkey="/"{% else %}"{% endif %}>
30
+ <i class="fa-solid fa-magnifying-glass" aria-hidden="true"></i>
31
+ </button>
32
+ {% endif %}
33
+
34
+ {% if cfg.mode_switcher %}
35
+ <button class="navbar__icon-btn" id="modeToggle" aria-label="Toggle dark mode" title="Toggle theme">
36
+ <i class="fa-solid fa-sun icon-light" aria-hidden="true"></i>
37
+ <i class="fa-solid fa-moon icon-dark" aria-hidden="true"></i>
38
+ </button>
39
+ {% endif %}
40
+
41
+ {% if cfg.skin_switcher %}
42
+ <div class="skin-picker" id="skinPicker">
43
+ <button class="navbar__icon-btn" aria-haspopup="true" aria-expanded="false" aria-label="Change colour skin" title="Colour skin">
44
+ <i class="fa-solid fa-palette" aria-hidden="true"></i>
45
+ </button>
46
+ <div class="skin-picker__menu" role="menu">
47
+ {%- assign skin_list = "aqua,violet,mint,ember,graphite,clay" | split: "," -%}
48
+ {% for s in skin_list %}
49
+ <button type="button" role="menuitemradio" aria-checked="false" data-skin-set="{{ s }}" class="skin-picker__opt">
50
+ <span class="skin-dot skin-dot--{{ s }}" aria-hidden="true"></span>
51
+ <span class="skin-picker__label">{{ s | capitalize }}</span>
52
+ </button>
53
+ {% endfor %}
54
+ </div>
55
+ </div>
56
+ {% endif %}
57
+
58
+ {% if cfg.social.github %}
59
+ <a class="navbar__icon-btn" href="https://github.com/{{ cfg.social.github }}" rel="noopener" aria-label="GitHub repository" title="GitHub">
60
+ <i class="fa-brands fa-github" aria-hidden="true"></i>
61
+ </a>
62
+ {% endif %}
63
+
64
+ {% if cfg.buy_me_a_coffee.username and cfg.buy_me_a_coffee.show_in contains "navbar" %}
65
+ {% include buy-me-a-coffee.html compact=true %}
66
+ {% endif %}
67
+ </div>
68
+ </div>
69
+ </header>
70
+ <div class="sidebar-scrim" id="sidebarScrim" hidden></div>
@@ -0,0 +1,22 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <script>
3
+ window.DocSteer = {
4
+ baseurl: "{{ site.baseurl }}",
5
+ search: {
6
+ enabled: {{ cfg.search.enabled | default: false }},
7
+ endpoint: "{{ '/search.json' | relative_url }}",
8
+ max: {{ cfg.search.max_results | default: 8 }},
9
+ hotkey: {{ cfg.search.hotkey | default: false }}
10
+ },
11
+ lightbox: {{ cfg.lightbox.enabled | default: false }},
12
+ faq: {{ cfg.faq.enabled | default: false }},
13
+ codeCopy: {{ cfg.code.copy_button | default: false }},
14
+ toc: {
15
+ enabled: {{ cfg.toc.enabled | default: false }},
16
+ min: {{ cfg.toc.min_headings | default: 2 }}
17
+ }
18
+ };
19
+ </script>
20
+ <script src="{{ '/assets/js/main.js' | relative_url }}" defer></script>
21
+ {% if cfg.search.enabled %}<script src="{{ '/assets/js/search.js' | relative_url }}" defer></script>{% endif %}
22
+ {% if cfg.lightbox.enabled %}<script src="{{ '/assets/js/lightbox.js' | relative_url }}" defer></script>{% endif %}
@@ -0,0 +1,24 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <div class="search-modal" id="searchModal" aria-hidden="true" role="dialog" aria-modal="true" aria-label="Search">
3
+ <div class="search-modal__backdrop" data-search-close></div>
4
+ <div class="search-modal__panel" role="document">
5
+ <div class="search-modal__bar">
6
+ <i class="fa-solid fa-magnifying-glass" aria-hidden="true"></i>
7
+ <input type="search" id="searchInput" class="search-modal__input"
8
+ placeholder="{{ cfg.search.placeholder | default: 'Search the docs…' }}"
9
+ autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"
10
+ aria-controls="searchResults" aria-expanded="false">
11
+ <button class="search-modal__esc" data-search-close aria-label="Close search"><kbd>Esc</kbd></button>
12
+ </div>
13
+
14
+ <div class="search-modal__body">
15
+ <ul class="search-results" id="searchResults" role="listbox"
16
+ data-endpoint="{{ '/search.json' | relative_url }}"
17
+ data-max="{{ cfg.search.max_results | default: 8 }}"></ul>
18
+ <p class="search-modal__empty" id="searchEmpty" hidden>No results. Try another term.</p>
19
+ <p class="search-modal__hint" id="searchHint">
20
+ Type to search &nbsp;·&nbsp; <kbd>↑</kbd><kbd>↓</kbd> to navigate &nbsp;·&nbsp; <kbd>↵</kbd> to open
21
+ </p>
22
+ </div>
23
+ </div>
24
+ </div>
@@ -0,0 +1,48 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <aside class="sidebar{% if cfg.sidebar.sticky %} is-sticky{% endif %}" id="sidebar" aria-label="Documentation navigation">
3
+ <div class="sidebar__inner">
4
+
5
+ {% if cfg.search.enabled %}
6
+ <button class="sidebar__search" data-search-open type="button">
7
+ <i class="fa-solid fa-magnifying-glass" aria-hidden="true"></i>
8
+ <span>{{ cfg.search.placeholder | default: "Search…" }}</span>
9
+ </button>
10
+ {% endif %}
11
+
12
+ <nav class="sidebar__nav">
13
+ {% for group in site.data.navigation.sidebar %}
14
+ {%- assign group_active = false -%}
15
+ {%- for link in group.children -%}
16
+ {%- if page.url == link.url %}{% assign group_active = true %}{% endif -%}
17
+ {%- endfor -%}
18
+
19
+ <div class="sidebar__group{% if cfg.sidebar.collapse_inactive and group_active == false and group.open != true %} is-collapsed{% endif %}">
20
+ {% if group.title %}
21
+ <button class="sidebar__group-title" aria-expanded="{{ group_active | default: false }}">
22
+ {% if group.icon %}<i class="{{ group.icon }}" aria-hidden="true"></i>{% endif %}
23
+ <span>{{ group.title }}</span>
24
+ <i class="fa-solid fa-chevron-right sidebar__chev" aria-hidden="true"></i>
25
+ </button>
26
+ {% endif %}
27
+
28
+ <ul class="sidebar__list">
29
+ {% for link in group.children %}
30
+ <li>
31
+ <a href="{{ link.url | relative_url }}"
32
+ class="sidebar__link{% if page.url == link.url %} is-active{% endif %}"
33
+ {% if page.url == link.url %}aria-current="page"{% endif %}>
34
+ {{ link.title }}
35
+ {% if link.badge %}<span class="badge">{{ link.badge }}</span>{% endif %}
36
+ </a>
37
+ </li>
38
+ {% endfor %}
39
+ </ul>
40
+ </div>
41
+ {% endfor %}
42
+ </nav>
43
+
44
+ {% if cfg.buy_me_a_coffee.username and cfg.buy_me_a_coffee.show_in contains "sidebar" %}
45
+ <div class="sidebar__coffee">{% include buy-me-a-coffee.html %}</div>
46
+ {% endif %}
47
+ </div>
48
+ </aside>
@@ -0,0 +1,11 @@
1
+ {%- assign cfg = site.docsteer -%}
2
+ <aside class="toc" id="toc" aria-label="On this page">
3
+ <p class="toc__title"><i class="fa-solid fa-list-ul" aria-hidden="true"></i> On this page</p>
4
+ <nav class="toc__nav" id="tocNav" data-min-headings="{{ cfg.toc.min_headings | default: 2 }}">
5
+ <!-- built from headings by main.js -->
6
+ </nav>
7
+
8
+ {% if cfg.buy_me_a_coffee.username and cfg.buy_me_a_coffee.show_in contains "toc" %}
9
+ <div class="toc__coffee">{% include buy-me-a-coffee.html %}</div>
10
+ {% endif %}
11
+ </aside>
@@ -0,0 +1,45 @@
1
+ <!DOCTYPE html>
2
+ {%- assign cfg = site.docsteer -%}
3
+ {%- assign skin = cfg.skin | default: "aqua" -%}
4
+ {%- assign mode = cfg.mode | default: "auto" -%}
5
+ <html lang="{{ site.lang | default: 'en' }}"
6
+ data-skin="{{ skin }}"
7
+ {% if mode != "auto" %}data-mode="{{ mode }}"{% endif %}>
8
+ {% include head.html %}
9
+ <body class="layout-{{ page.layout }}{% if page.sidebar == false %} no-sidebar{% endif %}">
10
+ <a class="skip-link" href="#main">Skip to content</a>
11
+
12
+ {% include navbar.html %}
13
+
14
+ {%- comment -%}
15
+ Jekyll reports the layout the PAGE declared, not the chain it renders
16
+ through: a page on `layout: faq` reports "faq" even though faq inherits
17
+ from doc. Testing for "doc" alone silently dropped the sidebar on every
18
+ derived layout, so the set is configurable — add your own doc-shaped
19
+ layouts to `docsteer.doc_layouts`.
20
+ {%- endcomment -%}
21
+ {%- assign doc_layouts = cfg.doc_layouts | default: "doc" -%}
22
+ {%- assign show_sidebar = false -%}
23
+ {%- if cfg.sidebar.enabled and page.sidebar != false and doc_layouts contains page.layout -%}
24
+ {%- assign show_sidebar = true -%}
25
+ {%- endif -%}
26
+
27
+ <div class="page-shell{% if show_sidebar %} has-sidebar{% endif %}">
28
+ {% if show_sidebar %}{% include sidebar.html %}{% endif %}
29
+
30
+ <main id="main" class="page-main{% if show_sidebar %} has-sidebar{% endif %}" tabindex="-1">
31
+ {{ content }}
32
+ </main>
33
+ </div>
34
+
35
+ {% include footer.html %}
36
+ {% if cfg.search.enabled %}{% include search-modal.html %}{% endif %}
37
+ {% if cfg.lightbox.enabled %}<div class="lightbox" id="lightbox" aria-hidden="true"></div>{% endif %}
38
+
39
+ <button class="to-top" id="toTop" aria-label="Back to top" hidden>
40
+ <i class="fa-solid fa-arrow-up" aria-hidden="true"></i>
41
+ </button>
42
+
43
+ {% include scripts.html %}
44
+ </body>
45
+ </html>