|
| 1 | +--- |
| 2 | +summary: Show each docs-site project's lockup as a centered light/dark hero on its docs home page, replacing the plain `# Title` H1. |
| 3 | +--- |
| 4 | + |
| 5 | +# Design: Per-project lockup hero on docs home pages |
| 6 | + |
| 7 | +## Summary |
| 8 | + |
| 9 | +The seven repos with a live docs site (`projects.py::DOCS_REPOS`: `modern-di`, |
| 10 | +`that-depends`, `lite-bootstrap`, `httpware`, `faststream-redis-timers`, |
| 11 | +`faststream-outbox`, `semvertag`) open their docs home page with a plain |
| 12 | +`# <Title>` Markdown heading and no project logo in the page body. This change |
| 13 | +replaces that H1 with a centered hero showing the project's **lockup** (mark + |
| 14 | +project name), theme-aware across light and dark, exactly mirroring the org |
| 15 | +site's own `.mp-hero` wordmark treatment. The lockups already exist in |
| 16 | +`brand/projects/<repo>/`; the rollout vendors two SVGs into each repo, edits |
| 17 | +`docs/index.md`, and adds a small CSS block. Seven repos, one PR each, piloted |
| 18 | +on `that-depends`. |
| 19 | + |
| 20 | +## Motivation |
| 21 | + |
| 22 | +Goal is **brand recognition**: the per-project marks already appear as README |
| 23 | +banners across the org, but a visitor landing on `httpware.modern-python.org` |
| 24 | +(or any project docs site) sees only text — the org mark in the header nav and a |
| 25 | +plain `# httpware` heading. The mark that identifies the project everywhere else |
| 26 | +is absent from the one page most likely to be a visitor's entry point. Putting |
| 27 | +the lockup at the top of each docs home page ties the docs surface to the same |
| 28 | +mark used on GitHub and PyPI, so the mark and the project become associated |
| 29 | +across every surface. |
| 30 | + |
| 31 | +The org home page (`docs/index.md` in this repo) already proves the pattern: its |
| 32 | +H1 is a centered light/dark `<img>` swap of `wordmark.svg` / `wordmark-dark.svg` |
| 33 | +driven by `.mp-hero` CSS. This change is the per-project application of that |
| 34 | +established pattern. |
| 35 | + |
| 36 | +## Non-goals |
| 37 | + |
| 38 | +- No changes to the header nav logo or favicon — those stay the org mark/favicon |
| 39 | + on every site (recognition of the *org*), unchanged. |
| 40 | +- No new brand assets and no regeneration — `lockup-light.svg` / `lockup-dark.svg` |
| 41 | + already exist for all seven repos. |
| 42 | +- No changes to the org home page or to repos without a docs site. |
| 43 | +- Not hiding nav/toc on the docs home pages — these are real docs entry pages, |
| 44 | + unlike the org landing page. |
| 45 | + |
| 46 | +## Design |
| 47 | + |
| 48 | +The change is identical in shape across all seven repos; only three values vary |
| 49 | +per repo: the repo name (lockup `alt` text), the H1 text being removed, and |
| 50 | +the CSS filename the repo's `extra_css` loads. |
| 51 | + |
| 52 | +### 1. Vendor two lockup SVGs into `docs/assets/` |
| 53 | + |
| 54 | +Copy from this repo into each target repo: |
| 55 | + |
| 56 | +``` |
| 57 | +brand/projects/<repo>/lockup-light.svg -> <repo>/docs/assets/lockup-light.svg |
| 58 | +brand/projects/<repo>/lockup-dark.svg -> <repo>/docs/assets/lockup-dark.svg |
| 59 | +``` |
| 60 | + |
| 61 | +Docs sites **vendor** brand assets (each already carries `docs/assets/mark.svg`, |
| 62 | +`favicon.svg`, `social-card.png` as committed copies). Vendoring the lockup is |
| 63 | +consistent with that precedent and keeps `mkdocs build --strict` self-contained |
| 64 | +— see Risk for the rejected hotlink alternative. Asset filenames (`lockup-light.svg`, |
| 65 | +`lockup-dark.svg`) do not collide with the existing `mark.svg`. |
| 66 | + |
| 67 | +### 2. Replace the `# Title` H1 in `docs/index.md` with a hero block |
| 68 | + |
| 69 | +The lockup `<img>` becomes the page's H1, carrying the repo name as its alt text |
| 70 | +— the same accessibility technique the org home page uses. No `title:` front |
| 71 | +matter is added: MkDocs Material derives the home page's browser-tab title from |
| 72 | +`site_name` (the `page.is_homepage` branch), independent of the H1, so the tab |
| 73 | +title stays the bare repo name; the sidebar nav label comes from the `nav:` entry |
| 74 | +(where the home page is listed) or is simply absent (where it is not), never from |
| 75 | +the H1 text. Adding `title:` would instead force Material's `{title} - {site_name}` |
| 76 | +branch and, because `site_name` equals the repo name, duplicate it in the tab |
| 77 | +(`that-depends - that-depends`). The redundant "Welcome to the `<repo>` documentation!" greeting (present |
| 78 | +in most, e.g. `modern-di`, `that-depends`, `lite-bootstrap`, `faststream-redis-timers`) |
| 79 | +is dropped — the lockup already names the project — and the page proceeds |
| 80 | +straight to its substantive first paragraph. Repos whose intro is a single |
| 81 | +blended paragraph (e.g. `httpware`, `faststream-outbox`, `semvertag`, which have |
| 82 | +no separate "Welcome" line) keep that paragraph verbatim. |
| 83 | + |
| 84 | +Before (`that-depends/docs/index.md`): |
| 85 | + |
| 86 | +```markdown |
| 87 | +# That Depends |
| 88 | + |
| 89 | +Welcome to the `that-depends` documentation! |
| 90 | + |
| 91 | +`that-depends` is a python dependency injection framework which ... |
| 92 | +``` |
| 93 | + |
| 94 | +After: |
| 95 | + |
| 96 | +```markdown |
| 97 | +<div class="mp-hero" markdown> |
| 98 | + |
| 99 | +<h1 class="mp-lockup"> |
| 100 | +<img class="mp-logo mp-logo--light" src="assets/lockup-light.svg" alt="that-depends"> |
| 101 | +<img class="mp-logo mp-logo--dark" src="assets/lockup-dark.svg" alt="" aria-hidden="true"> |
| 102 | +</h1> |
| 103 | + |
| 104 | +</div> |
| 105 | + |
| 106 | +`that-depends` is a python dependency injection framework which ... |
| 107 | +``` |
| 108 | + |
| 109 | +The dark `<img>` is `aria-hidden` with empty alt so screen readers announce the |
| 110 | +project name once. Everything below the intro is unchanged. |
| 111 | + |
| 112 | +### 3. Append the hero CSS to the repo's brand stylesheet |
| 113 | + |
| 114 | +Append to whichever file the repo's `extra_css` already lists (`css/brand.css` |
| 115 | +for `modern-di` / `that-depends`; other repos may use `stylesheets/extra.css` — |
| 116 | +match the existing entry). This is the org home page's `.mp-hero` rule, adapted |
| 117 | +for the lockup class name: |
| 118 | + |
| 119 | +```css |
| 120 | +/* Centered project lockup hero on the docs home page */ |
| 121 | +.mp-hero { |
| 122 | + text-align: center; |
| 123 | + margin: 1.5rem 0 2.5rem; |
| 124 | +} |
| 125 | +.mp-hero .mp-lockup { |
| 126 | + margin: 0; |
| 127 | + font-size: 0; /* collapse whitespace between the stacked <img> variants */ |
| 128 | + line-height: 0; |
| 129 | +} |
| 130 | +.mp-hero .mp-logo { |
| 131 | + max-width: 420px; |
| 132 | + width: 70%; |
| 133 | + height: auto; |
| 134 | +} |
| 135 | +/* Light lockup by default; cream lockup in dark (slate) mode. */ |
| 136 | +.mp-hero .mp-logo--dark { display: none; } |
| 137 | +[data-md-color-scheme="slate"] .mp-hero .mp-logo--light { display: none; } |
| 138 | +[data-md-color-scheme="slate"] .mp-hero .mp-logo--dark { display: inline; } |
| 139 | +``` |
| 140 | + |
| 141 | +Lockups have viewBox `0 0 ~280 100` (wide), so `max-width: 420px` caps the |
| 142 | +rendered height near ~150px — a proportionate hero, not an oversized banner. |
| 143 | + |
| 144 | +### 4. Document the convention in this repo |
| 145 | + |
| 146 | +Add a short "docs home page hero" note to `architecture/brand-marks.md` (beside |
| 147 | +the existing README-banner note), recording that docs sites vendor the lockup as |
| 148 | +a centered `.mp-hero` — contrasted with the README `<picture>` hotlink approach — |
| 149 | +and add a one-line pointer in `brand/README.md`'s per-project marks section. This |
| 150 | +promotion rides in the same PR as the planning bundle (this `.github` repo's |
| 151 | +slice of the rollout). |
| 152 | + |
| 153 | +## Rollout |
| 154 | + |
| 155 | +Full lane, executed **pilot then replicate**: |
| 156 | + |
| 157 | +1. **`that-depends`** — pilot end to end (branch, PR, CI, maintainer review, |
| 158 | + merge). Lock the exact three-part diff. |
| 159 | +2. Replicate the identical change to `lite-bootstrap`, `httpware`, |
| 160 | + `faststream-redis-timers`, `faststream-outbox`, `semvertag`. |
| 161 | +3. **`modern-di`** last, once its branch is free. |
| 162 | + |
| 163 | +Each target repo is a separate PR in its own repo. This `.github` repo carries |
| 164 | +its own PR for the planning bundle + architecture/brand-README docs (step 4). |
| 165 | + |
| 166 | +## Testing |
| 167 | + |
| 168 | +Per repo, at the branch HEAD with the repo's pinned docs deps |
| 169 | +(`pip install -r docs/requirements.txt` or the repo's documented docs env): |
| 170 | + |
| 171 | +- `mkdocs build --strict` passes — proves the two `assets/lockup-*.svg` refs and |
| 172 | + the CSS reference resolve with no warnings (strict fails on broken internal links). |
| 173 | +- `mkdocs serve`, open the home page, confirm: the lockup renders centered; the |
| 174 | + light variant shows in default theme and the cream variant after toggling to |
| 175 | + dark (slate); the browser tab title is the project name; no duplicate project |
| 176 | + name remains in the body. |
| 177 | + |
| 178 | +## Risk |
| 179 | + |
| 180 | +- **Hotlink vs vendor (low / decided).** READMEs reference lockups via |
| 181 | + `raw.githubusercontent.com` with no committed assets. Reusing that for docs |
| 182 | + would avoid vendoring, but external URLs are not checked by `mkdocs --strict`, |
| 183 | + are subject to CDN caching lag and CSP, and break offline builds. Docs sites |
| 184 | + already vendor every other brand asset, so vendoring is the consistent, robust |
| 185 | + choice. Rejected hotlinking. |
| 186 | +- **CSS filename drift (low).** Repos differ in the stylesheet `extra_css` loads. |
| 187 | + Mitigation: read each repo's `mkdocs.yml` `extra_css` and append to that exact |
| 188 | + file; the pilot documents the check. |
| 189 | +- **Long project names (low).** The widest lockup still fits under `max-width: |
| 190 | + 420px`; visually verified on the pilot before replicating. |
| 191 | +- **Lost H1 semantics (low).** The lockup `<img>` sits inside an `<h1>` with the |
| 192 | + repo name as alt text, so the page keeps exactly one H1 with an accessible name. |
| 193 | + The browser-tab title is unaffected (Material uses `site_name` on the home page) |
| 194 | + and the sidebar label comes from `nav:`, not the H1 — verified across all seven |
| 195 | + repos: five list the home page in `nav:` (Quick-Start / Overview / Quick Start), |
| 196 | + two do not list it at all (no sidebar entry to break). |
0 commit comments