03510d3940
Il menu in alto si riduce alle voci che servono davvero — Articoli, Contenuti, Utenti, Sito, Esci — con la voce corrente evidenziata; ognuna resta visibile solo a chi ha il ruolo per aprirla, e in pagina di login la barra mostra il solo marchio. "Nuovo" esce dal menu perché il pulsante per creare un articolo è già in cima all'elenco Articoli. Il pannello smette di essere un foglio di stile a sé: adotta i font e la palette del sito, come Campus e Stress Index, con tabelle, pulsanti, campi e pillole di stato riportati allo stesso linguaggio. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
141 lines
6.0 KiB
Plaintext
141 lines
6.0 KiB
Plaintext
---
|
|
// Layout dell'area riservata. Usa i token e i font del sito, come il Campus e Stress Index:
|
|
// il pannello non è più un foglio di stile a sé, così chi passa dal sito all'amministrazione
|
|
// resta nello stesso mondo visivo.
|
|
import '@fontsource/montserrat/400.css';
|
|
import '@fontsource/montserrat/500.css';
|
|
import '@fontsource/montserrat/600.css';
|
|
import '@fontsource/open-sans/400.css';
|
|
import '@fontsource/open-sans/600.css';
|
|
import '../styles/global.css';
|
|
|
|
interface Props { title: string }
|
|
const { title } = Astro.props;
|
|
const user = Astro.locals.user;
|
|
const path = Astro.url.pathname;
|
|
const isManager = user?.role === 'superuser' || user?.role === 'admin';
|
|
|
|
// Voci del menu: ognuna compare solo a chi può davvero aprirla.
|
|
const VOCI = [
|
|
{ href: '/admin', label: 'Articoli', visibile: true, exact: true },
|
|
{ href: '/admin/content', label: 'Contenuti', visibile: isManager },
|
|
{ href: '/admin/users', label: 'Utenti', visibile: user?.role === 'admin' },
|
|
];
|
|
const attiva = (v: { href: string; exact?: boolean }) =>
|
|
v.exact ? path === v.href : path.startsWith(v.href);
|
|
---
|
|
<!doctype html>
|
|
<html lang="it">
|
|
<head>
|
|
<meta charset="utf-8" />
|
|
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
|
<title>{title} — Admin InsanityLab</title>
|
|
<meta name="robots" content="noindex" />
|
|
<link rel="icon" href="/favicon.svg" type="image/svg+xml" />
|
|
</head>
|
|
<body class="ad">
|
|
<header class="abar">
|
|
<a class="abar__brand" href="/admin">
|
|
<span class="abar__eyebrow">InsanityLab</span>
|
|
Area riservata
|
|
</a>
|
|
|
|
{user && (
|
|
<nav class="abar__nav" aria-label="pannello">
|
|
{VOCI.filter((v) => v.visibile).map((v) => (
|
|
<a href={v.href} class:list={['abar__link', { 'is-active': attiva(v) }]}>{v.label}</a>
|
|
))}
|
|
<a class="abar__link" href="/" target="_blank" rel="noopener">Sito</a>
|
|
<a class="abar__link abar__link--out" href="/admin/logout">Esci</a>
|
|
</nav>
|
|
)}
|
|
|
|
{user && <p class="abar__user">{user.username}</p>}
|
|
</header>
|
|
|
|
<main class="awrap"><slot /></main>
|
|
|
|
<style is:global>
|
|
body.ad { background: var(--c-bg-alt); }
|
|
|
|
/* --- barra --- */
|
|
.abar {
|
|
display: flex; align-items: center; gap: 28px; flex-wrap: wrap;
|
|
background: var(--c-dark); color: #cfc6bd; padding: 16px 32px;
|
|
}
|
|
.abar__brand {
|
|
font-family: var(--font-heading); font-size: 1rem; font-weight: 600; letter-spacing: .12em;
|
|
text-transform: uppercase; color: #fff; text-decoration: none; line-height: 1.15;
|
|
}
|
|
.abar__eyebrow { display: block; font-size: .62rem; letter-spacing: .2em; color: var(--c-accent); }
|
|
.abar__nav { display: flex; align-items: center; gap: 26px; flex-wrap: wrap; }
|
|
.abar__link {
|
|
font-family: var(--font-heading); font-size: .72rem; font-weight: 600; letter-spacing: .16em;
|
|
text-transform: uppercase; color: #b6ada3; text-decoration: none; padding: 4px 0;
|
|
border-bottom: 1px solid transparent;
|
|
}
|
|
.abar__link:hover { color: #fff; }
|
|
.abar__link.is-active { color: #fff; border-bottom-color: var(--c-accent); }
|
|
.abar__link--out { color: var(--c-accent); }
|
|
.abar__user {
|
|
margin: 0 0 0 auto; font-size: .74rem; letter-spacing: .12em; text-transform: uppercase; color: #8d8379;
|
|
}
|
|
|
|
/* --- contenuto --- */
|
|
.awrap { max-width: 1080px; margin: 40px auto 80px; padding: 0 24px; }
|
|
.awrap h1 {
|
|
font-size: clamp(1.6rem, 3vw, 2.1rem); text-transform: none; letter-spacing: .02em; margin-bottom: .6em;
|
|
}
|
|
.awrap h2 { font-size: 1.15rem; text-transform: none; letter-spacing: .02em; }
|
|
|
|
/* --- comandi --- */
|
|
.abtn {
|
|
display: inline-block; background: var(--c-dark); color: #fff; border: 1px solid var(--c-dark);
|
|
padding: 10px 20px; cursor: pointer; text-decoration: none; font-family: var(--font-heading);
|
|
font-size: .7rem; font-weight: 600; letter-spacing: .14em; text-transform: uppercase;
|
|
}
|
|
.abtn:hover { background: var(--c-dark-2); border-color: var(--c-dark-2); }
|
|
.abtn--danger { background: none; color: #a4544a; border-color: #ddcfc9; }
|
|
.abtn--danger:hover { background: #a4544a; border-color: #a4544a; color: #fff; }
|
|
|
|
.afield {
|
|
width: 100%; padding: 11px 13px; margin-bottom: 14px; border: 1px solid #ddd6cb;
|
|
box-sizing: border-box; font: inherit; font-size: .92rem; background: #fff; border-radius: 0;
|
|
}
|
|
.afield:focus { outline: 2px solid var(--c-accent); outline-offset: -2px; }
|
|
|
|
/* --- tabelle --- */
|
|
table { width: 100%; border-collapse: collapse; background: #fff; border: 1px solid #e4dfd7; }
|
|
th, td { text-align: left; padding: 12px 14px; border-bottom: 1px solid #efeae2; font-size: .9rem; }
|
|
th {
|
|
font-family: var(--font-heading); font-size: .68rem; font-weight: 600; letter-spacing: .14em;
|
|
text-transform: uppercase; color: var(--c-text-light); background: #faf8f5;
|
|
}
|
|
tbody tr:last-child td { border-bottom: 0; }
|
|
tbody tr:hover { background: #faf8f5; }
|
|
td a { color: var(--c-accent-dark); font-weight: 600; text-decoration: none; }
|
|
td a:hover { text-decoration: underline; }
|
|
|
|
.pill {
|
|
display: inline-block; font-family: var(--font-heading); font-size: .64rem; font-weight: 600;
|
|
letter-spacing: .1em; text-transform: uppercase; padding: 3px 10px;
|
|
background: rgba(111,143,106,.16); color: #5f7c5a;
|
|
}
|
|
.pill--draft { background: rgba(192,138,62,.18); color: #96682a; }
|
|
|
|
.aform { max-width: 380px; background: #fff; border: 1px solid #e4dfd7; padding: 26px 24px; }
|
|
|
|
.form-msg { font-size: .88rem; margin-top: 8px; }
|
|
.form-msg--ok { color: #5f7c5a; }
|
|
.form-msg--err { color: #a4544a; }
|
|
|
|
@media (max-width: 720px) {
|
|
.abar { padding: 14px 20px; gap: 14px; }
|
|
.abar__nav { gap: 16px; width: 100%; }
|
|
.abar__user { margin-left: 0; }
|
|
.awrap { margin-top: 26px; padding: 0 20px; }
|
|
}
|
|
</style>
|
|
</body>
|
|
</html>
|