feat: content-UX — header search, metadata de-noise, icon/microcopy coherence, article composition
This commit is contained in:
+62
-19
@@ -11,12 +11,15 @@ const ogImage = new URL(image || '/brand/og-card.jpg', site);
|
||||
const path = Astro.url.pathname;
|
||||
const isActive = (href) => (href === '/' ? path === '/' : path.startsWith(href));
|
||||
// Navigation = services from the Science Portal spec (REQUIREMENTS.md §2/§5).
|
||||
// External systems built by other teams are links out, clearly marked.
|
||||
// Order: serial-position effect (NN/g) — News (universal entry) first, Support
|
||||
// (help convention) last; Data/Proposals by task frequency; Dashboard is the
|
||||
// personal area, placed late next to the Sign-in cluster. External systems
|
||||
// built by other teams are links out, clearly marked.
|
||||
const links = [
|
||||
{ href: '/news', label: 'News' },
|
||||
{ href: 'https://padc-ctao-data-explorer.obspm.fr/', label: 'Data', ext: true },
|
||||
{ href: '/proposals', label: 'Proposals' },
|
||||
{ href: '/dashboard', label: 'Dashboard' },
|
||||
{ href: 'https://padc-ctao-data-explorer.obspm.fr/', label: 'Data', ext: true },
|
||||
{ href: '/support', label: 'Support' },
|
||||
];
|
||||
---
|
||||
@@ -45,6 +48,15 @@ const links = [
|
||||
</head>
|
||||
<body class={ambient ? 'has-ambient' : undefined}>
|
||||
<a class="skip" href="#main">Skip to content</a>
|
||||
{/* Demo disclosure — GOV.UK phase-banner pattern: one slim, honest banner
|
||||
instead of implementation talk scattered through the UI. Not sticky;
|
||||
it scrolls away and the header sticks below it. */}
|
||||
<div class="phase-banner">
|
||||
<div class="container">
|
||||
<strong class="phase-tag">Demo</strong>
|
||||
<span>This is a demonstration of the CTAO Science Portal — content is sample data.</span>
|
||||
</div>
|
||||
</div>
|
||||
<header class="site-header">
|
||||
<div class="container nav">
|
||||
<a class="brand" href="/" aria-label="CTAO Science Portal — home">
|
||||
@@ -59,17 +71,37 @@ const links = [
|
||||
))}
|
||||
</nav>
|
||||
<span class="spacer"></span>
|
||||
<a class="navlink" href="/search">Search</a>
|
||||
<a class="navlink navlink--edit" href="/admin" title="Content editor (demo CMS)">
|
||||
<svg class="ico" aria-hidden="true" viewBox="0 0 24 24"><path d="M17 3l4 4L8 20l-5 1 1-5L17 3z" /></svg>
|
||||
Editor
|
||||
</a>
|
||||
{/* Site search lives in the header (desktop: compact field; ≤1024px: the
|
||||
magnifier <details> below). Plain GET form — works without JS; with JS
|
||||
the shared suggest dropdown appears (search-client.js). */}
|
||||
<form class="nav-search" role="search" aria-label="Site search" action="/search" method="get">
|
||||
<label class="sr-only" for="hdr-q">Search news</label>
|
||||
<svg class="ico search-ico" aria-hidden="true" viewBox="0 0 24 24"><circle cx="11" cy="11" r="7" /><path d="m20 20-4.3-4.3" /></svg>
|
||||
<input id="hdr-q" name="q" type="search" placeholder="Search…" autocomplete="off" />
|
||||
<ul class="suggest" id="hdr-suggest"></ul>
|
||||
<p class="sr-only" id="hdr-suggest-status" role="status" aria-live="polite"></p>
|
||||
</form>
|
||||
<a class="login-mock" href="/login">Sign in</a>
|
||||
{/* ≤1024px: magnifier button reveals a full-width search row. name="header-panel"
|
||||
pairs it with the menu as a native exclusive group — opening one closes
|
||||
the other, no JS (exclusive-accordion behavior of <details name>). */}
|
||||
<details class="search-pop" name="header-panel">
|
||||
<summary aria-label="Search">
|
||||
<svg class="ico" aria-hidden="true" viewBox="0 0 24 24"><circle cx="11" cy="11" r="7" /><path d="m20 20-4.3-4.3" /></svg>
|
||||
</summary>
|
||||
<form role="search" aria-label="Site search" action="/search" method="get">
|
||||
<label class="sr-only" for="pop-q">Search news</label>
|
||||
<input id="pop-q" name="q" type="search" placeholder="Search news…" autocomplete="off" />
|
||||
<button class="btn" type="submit">Search</button>
|
||||
<ul class="suggest" id="pop-suggest"></ul>
|
||||
<p class="sr-only" id="pop-suggest-status" role="status" aria-live="polite"></p>
|
||||
</form>
|
||||
</details>
|
||||
{/* Mobile disclosure menu — native <details>/<summary>, no JS; desktop hides it via CSS */}
|
||||
<details class="menu">
|
||||
<summary>
|
||||
<details class="menu" name="header-panel">
|
||||
<summary aria-label="Menu">
|
||||
<svg class="ico" aria-hidden="true" viewBox="0 0 24 24"><path class="i-menu" d="M3 6h18M3 12h18M3 18h18" /><path class="i-close" d="M5 5l14 14M19 5 5 19" /></svg>
|
||||
Menu
|
||||
<span class="menu-label">Menu</span>
|
||||
</summary>
|
||||
<nav aria-label="Main navigation">
|
||||
{links.map((l) => l.ext ? (
|
||||
@@ -77,12 +109,21 @@ const links = [
|
||||
) : (
|
||||
<a href={l.href} aria-current={isActive(l.href) ? 'page' : undefined}>{l.label}</a>
|
||||
))}
|
||||
<a href="/search">Search</a>
|
||||
<a href="/admin">Editor</a>
|
||||
</nav>
|
||||
</details>
|
||||
</div>
|
||||
</header>
|
||||
<script is:inline src="/search-client.js"></script>
|
||||
<script is:inline>
|
||||
// Header search suggestions (desktop field + mobile reveal); the forms are
|
||||
// plain GET /search, so everything below is progressive enhancement.
|
||||
newsSearch({ input: 'hdr-q', list: 'hdr-suggest', status: 'hdr-suggest-status', limit: 6, unit: 'suggestion' });
|
||||
newsSearch({ input: 'pop-q', list: 'pop-suggest', status: 'pop-suggest-status', limit: 6, unit: 'suggestion' });
|
||||
var pop = document.querySelector('.search-pop');
|
||||
pop.addEventListener('toggle', function () {
|
||||
if (pop.open) document.getElementById('pop-q').focus();
|
||||
});
|
||||
</script>
|
||||
<main id="main">
|
||||
<slot />
|
||||
</main>
|
||||
@@ -92,23 +133,25 @@ const links = [
|
||||
<div class="container">
|
||||
<div class="foot-top">
|
||||
<img src="/brand/AAFF_CTAO_Logo_RGB_Monochrome-negative.svg" alt="CTAO" />
|
||||
<p>Science Portal — news, observation proposals, data and user services of the
|
||||
Cherenkov Telescope Array Observatory.</p>
|
||||
<p>CTAO Science Portal — demo by Cyfronet (SUSS-PORT team).</p>
|
||||
</div>
|
||||
{/* Order: action/utility first, legal middle, meta last (GOV.UK/NN-g
|
||||
footer anatomy). Spec §3.3.1 requires the five items, not an order. */}
|
||||
<nav class="foot-links" aria-label="Footer">
|
||||
<a href="/pages/contact">Contact</a>
|
||||
<a href="/search">Search</a>
|
||||
<a href="/pages/disclaimer">Disclaimer</a>
|
||||
<a href="/pages/privacy">Privacy</a>
|
||||
<a href="/pages/contact">Contact</a>
|
||||
<a>Site settings</a>
|
||||
<a href="/search">Search</a>
|
||||
{/* Internal tooling stays out of the main nav (NN/g: navigation reflects
|
||||
user tasks); the editor is a discreet utility link for the demo. */}
|
||||
<a href="/admin">Content editor</a>
|
||||
</nav>
|
||||
<div class="foot-note">
|
||||
{/* The real brand flash — path taken from the official logo SVG (BRAND D.4).
|
||||
Sole decorative accent in this view; static by design. */}
|
||||
<svg class="flash" viewBox="85.3 15 15 15" aria-hidden="true"><path fill="currentColor" d="M94.7,23.8c1-1.4,3.3-2.1,5.2-2.7c-2,0.1-4.4,0.3-5.8-0.6c-1.4-1-2.1-3.3-2.7-5.2c0.1,2,0.3,4.4-0.6,5.8c-1,1.4-3.3,2.1-5.2,2.7c2-0.1,4.4-0.3,5.8,0.6c1.4,1,2.1,3.3,2.7,5.2C93.9,27.6,93.7,25.2,94.7,23.8z"/></svg>
|
||||
<span>Science Portal Core demo (Cyfronet / SUSS-PORT team). Sample content
|
||||
imported from ctao.org; the Site settings link is a placeholder. Statically
|
||||
generated from Markdown (git-based CMS).</span>
|
||||
<span>© 2026 CTAO — demonstration, not an official service.</span>
|
||||
</div>
|
||||
</div>
|
||||
</footer>
|
||||
|
||||
Reference in New Issue
Block a user