remarque-tokens 0.3.0 → 0.4.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.
- package/AGENT_RULES.md +1 -0
- package/CHANGELOG.md +22 -0
- package/README.md +1 -0
- package/package.json +7 -3
- package/prose.css +139 -0
- package/scripts/audit.mjs +5 -51
- package/scripts/lib/css-tokens.mjs +51 -0
- package/scripts/tokens-json.mjs +4 -45
- package/tokens-core.css +0 -129
- package/tokens.css +1 -0
- package/tokens.json +1 -1
package/AGENT_RULES.md
CHANGED
|
@@ -138,6 +138,7 @@ project/
|
|
|
138
138
|
├── tokens.css # Aggregator — imports the two tiers below
|
|
139
139
|
├── tokens-core.css # CORE tier: type scale, spacing, widths, radius, motion, prose machinery. NEVER override
|
|
140
140
|
├── tokens-palette.css # PALETTE tier: font slots, colors, accent, reading measure. Override freely, then run the audit
|
|
141
|
+
├── prose.css # .remarque-prose long-form styling (aggregated by tokens.css; own subpath for opt-out)
|
|
141
142
|
├── theme.css # Tailwind v4 adapter (@theme inline) — import after tailwindcss + tokens
|
|
142
143
|
├── tailwind.config.js # Tailwind v3 ONLY — v4 projects use theme.css instead
|
|
143
144
|
├── public/
|
package/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,28 @@ All notable changes to `remarque-tokens` are documented here. Token value
|
|
|
4
4
|
changes always state the design rationale — downstream sites pin against
|
|
5
5
|
these entries when syncing.
|
|
6
6
|
|
|
7
|
+
## 0.4.0 — 2026-07-20
|
|
8
|
+
|
|
9
|
+
### Added
|
|
10
|
+
- **`remarque-tokens/prose`** subpath: `.remarque-prose` split out of
|
|
11
|
+
`tokens-core.css` into `prose.css`, so consumers with their own prose
|
|
12
|
+
system (e.g. the reference consumer's `.prose`) can import the core
|
|
13
|
+
structural tokens without it.
|
|
14
|
+
|
|
15
|
+
### Changed
|
|
16
|
+
- **Breaking for `/core` importers:** `remarque-tokens/core` no longer
|
|
17
|
+
includes `.remarque-prose` — import `remarque-tokens/prose` alongside
|
|
18
|
+
it, or use the aggregator (`remarque-tokens`), which now includes all
|
|
19
|
+
three files and is unchanged for consumers.
|
|
20
|
+
- Demo pages exercise the Tailwind v4 adapter utilities directly
|
|
21
|
+
(`pt-remarque-10`, `rounded-sm`) instead of arbitrary-value escapes —
|
|
22
|
+
same computed styles, real coverage of the theme.css surface.
|
|
23
|
+
- Internals: the brace-aware CSS token parser previously duplicated in
|
|
24
|
+
`audit.mjs` and `tokens-json.mjs` now lives once in
|
|
25
|
+
`scripts/lib/css-tokens.mjs` (shipped with the package for the bin).
|
|
26
|
+
|
|
27
|
+
No token values changed in this release.
|
|
28
|
+
|
|
7
29
|
## 0.3.0 — 2026-07-20
|
|
8
30
|
|
|
9
31
|
### Added
|
package/README.md
CHANGED
|
@@ -67,6 +67,7 @@ The agent rules define build order, non-negotiable rules, disallowed patterns, a
|
|
|
67
67
|
| `tokens.css` | Aggregator importing the two token tiers below |
|
|
68
68
|
| `tokens-core.css` | Core tier — type scale, spacing, widths, radius, motion, prose styling. Never overridden |
|
|
69
69
|
| `tokens-palette.css` | Palette tier — font slots, colors, accent, reading measure. The sanctioned personalization surface |
|
|
70
|
+
| `prose.css` | `.remarque-prose` long-form styling — own subpath so sites with their own prose system can skip it |
|
|
70
71
|
| `scripts/audit.mjs` | `npm run audit` — enforces the spec's contrast/gamut/font-floor/no-hardcoded-color checklist |
|
|
71
72
|
| `fonts.css` + `fonts/` | Self-hosted @font-face declarations and woff2 files (no CDN requests) |
|
|
72
73
|
| `tailwind.config.js` | Tailwind CSS **v3** configuration (v4 projects use an `@theme` block instead) |
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "remarque-tokens",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.4.0",
|
|
4
4
|
"engines": {
|
|
5
5
|
"node": ">=18"
|
|
6
6
|
},
|
|
@@ -40,7 +40,9 @@
|
|
|
40
40
|
"./tailwind": "./tailwind.config.js",
|
|
41
41
|
"./theme.css": "./theme.css",
|
|
42
42
|
"./theme": "./theme.css",
|
|
43
|
-
"./tokens.json": "./tokens.json"
|
|
43
|
+
"./tokens.json": "./tokens.json",
|
|
44
|
+
"./prose": "./prose.css",
|
|
45
|
+
"./prose.css": "./prose.css"
|
|
44
46
|
},
|
|
45
47
|
"files": [
|
|
46
48
|
"tokens.css",
|
|
@@ -56,6 +58,8 @@
|
|
|
56
58
|
"CHANGELOG.md",
|
|
57
59
|
"theme.css",
|
|
58
60
|
"tokens.json",
|
|
59
|
-
"scripts/tokens-json.mjs"
|
|
61
|
+
"scripts/tokens-json.mjs",
|
|
62
|
+
"prose.css",
|
|
63
|
+
"scripts/lib/css-tokens.mjs"
|
|
60
64
|
]
|
|
61
65
|
}
|
package/prose.css
ADDED
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Remarque — Prose Styling (core tier)
|
|
3
|
+
* ─────────────────────────────────────
|
|
4
|
+
* .remarque-prose: all typographic details for long-form reading.
|
|
5
|
+
* Split from tokens-core.css as its own subpath (remarque-tokens/prose)
|
|
6
|
+
* so consumers with their own prose systems can import the core
|
|
7
|
+
* structural tokens without it. The tokens.css aggregator includes it.
|
|
8
|
+
* Values consumed here come from the core + palette tiers.
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
/* ─── Prose Styling ─────────────────────────────────────── */
|
|
12
|
+
/*
|
|
13
|
+
* Apply .remarque-prose to any container with article/essay content.
|
|
14
|
+
* Handles all typographic details for long-form reading.
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
.remarque-prose {
|
|
18
|
+
font-family: var(--font-body);
|
|
19
|
+
font-size: var(--text-body);
|
|
20
|
+
line-height: var(--leading-body);
|
|
21
|
+
color: var(--color-fg);
|
|
22
|
+
max-width: var(--content-reading);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
.remarque-prose > * + * {
|
|
26
|
+
margin-top: var(--space-5);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
.remarque-prose > :first-child {
|
|
30
|
+
margin-top: 0;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
.remarque-prose h2 {
|
|
34
|
+
font-family: var(--font-display);
|
|
35
|
+
font-size: var(--text-section);
|
|
36
|
+
line-height: var(--leading-section);
|
|
37
|
+
letter-spacing: var(--tracking-title);
|
|
38
|
+
font-weight: var(--weight-medium);
|
|
39
|
+
margin-top: var(--space-7);
|
|
40
|
+
margin-bottom: var(--space-3);
|
|
41
|
+
color: var(--color-fg);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
.remarque-prose h3 {
|
|
45
|
+
font-family: var(--font-body);
|
|
46
|
+
font-size: var(--text-body-lg);
|
|
47
|
+
line-height: var(--leading-title);
|
|
48
|
+
font-weight: var(--weight-semibold);
|
|
49
|
+
margin-top: var(--space-6);
|
|
50
|
+
margin-bottom: var(--space-2);
|
|
51
|
+
color: var(--color-fg);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
.remarque-prose a {
|
|
55
|
+
color: var(--color-link);
|
|
56
|
+
text-decoration: underline;
|
|
57
|
+
text-underline-offset: 0.2em;
|
|
58
|
+
text-decoration-thickness: 1px;
|
|
59
|
+
transition: color var(--motion-fast) var(--motion-easing);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
.remarque-prose a:hover {
|
|
63
|
+
color: var(--color-link-hover);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
.remarque-prose strong {
|
|
67
|
+
font-weight: var(--weight-semibold);
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
.remarque-prose em {
|
|
71
|
+
font-style: italic;
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
.remarque-prose blockquote {
|
|
75
|
+
border-left: 2px solid var(--color-border-bold);
|
|
76
|
+
padding-left: var(--space-5);
|
|
77
|
+
margin-left: 0;
|
|
78
|
+
color: var(--color-fg-muted);
|
|
79
|
+
font-style: italic;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
.remarque-prose ul,
|
|
83
|
+
.remarque-prose ol {
|
|
84
|
+
padding-left: var(--space-5);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
.remarque-prose li + li {
|
|
88
|
+
margin-top: var(--space-2);
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
.remarque-prose code {
|
|
92
|
+
font-family: var(--font-mono);
|
|
93
|
+
font-size: 0.9em;
|
|
94
|
+
background-color: var(--color-code-bg);
|
|
95
|
+
padding: 0.15em 0.35em;
|
|
96
|
+
border-radius: var(--radius-sm);
|
|
97
|
+
color: var(--color-code-fg);
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
.remarque-prose pre {
|
|
101
|
+
font-family: var(--font-mono);
|
|
102
|
+
font-size: var(--text-meta);
|
|
103
|
+
line-height: 1.6;
|
|
104
|
+
background-color: var(--color-code-bg);
|
|
105
|
+
border: var(--border-width) var(--border-style) var(--color-border);
|
|
106
|
+
border-radius: var(--radius-md);
|
|
107
|
+
padding: var(--space-5);
|
|
108
|
+
overflow-x: auto;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
.remarque-prose pre code {
|
|
112
|
+
background: none;
|
|
113
|
+
padding: 0;
|
|
114
|
+
border-radius: 0;
|
|
115
|
+
font-size: inherit;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
.remarque-prose hr {
|
|
119
|
+
border: none;
|
|
120
|
+
border-top: var(--border-width) var(--border-style) var(--color-border);
|
|
121
|
+
margin: var(--space-8) 0;
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
.remarque-prose img {
|
|
125
|
+
max-width: 100%;
|
|
126
|
+
height: auto;
|
|
127
|
+
border: var(--border-width) var(--border-style) var(--color-border);
|
|
128
|
+
border-radius: var(--radius-sm);
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
.remarque-prose figcaption {
|
|
132
|
+
font-family: var(--font-mono);
|
|
133
|
+
font-size: var(--text-meta);
|
|
134
|
+
line-height: var(--leading-meta);
|
|
135
|
+
letter-spacing: var(--tracking-meta);
|
|
136
|
+
color: var(--color-muted);
|
|
137
|
+
margin-top: var(--space-2);
|
|
138
|
+
}
|
|
139
|
+
|
package/scripts/audit.mjs
CHANGED
|
@@ -22,7 +22,9 @@
|
|
|
22
22
|
*/
|
|
23
23
|
|
|
24
24
|
import { readFileSync, readdirSync, statSync, existsSync } from 'node:fs';
|
|
25
|
-
import { join, relative } from 'node:path';
|
|
25
|
+
import { join, relative, dirname } from 'node:path';
|
|
26
|
+
import { fileURLToPath } from 'node:url';
|
|
27
|
+
import { extractBlocks, declsOf, isLightRoot, isDarkBlock } from './lib/css-tokens.mjs';
|
|
26
28
|
|
|
27
29
|
const args = process.argv.slice(2);
|
|
28
30
|
function argOf(flag, dflt) {
|
|
@@ -75,57 +77,9 @@ function ratio(c1, c2) {
|
|
|
75
77
|
return (hi + 0.05) / (lo + 0.05);
|
|
76
78
|
}
|
|
77
79
|
|
|
78
|
-
/* ── Brace-aware CSS block extraction ───────────────────── */
|
|
79
|
-
/* Returns [{ prelude, body, context }] where context is the enclosing
|
|
80
|
-
at-rule prelude ('' at top level). One level of at-rule nesting is
|
|
81
|
-
supported — enough for token files; deeper nesting is flattened with
|
|
82
|
-
its outermost context. Comments are stripped first. */
|
|
83
|
-
|
|
84
|
-
function extractBlocks(css) {
|
|
85
|
-
const src = css.replace(/\/\*[\s\S]*?\*\//g, '');
|
|
86
|
-
const blocks = [];
|
|
87
|
-
function scan(text, context) {
|
|
88
|
-
let i = 0;
|
|
89
|
-
while (i < text.length) {
|
|
90
|
-
const open = text.indexOf('{', i);
|
|
91
|
-
if (open === -1) break;
|
|
92
|
-
const prelude = text.slice(i, open).trim().replace(/^[;\s]+/, '');
|
|
93
|
-
let depth = 1, j = open + 1;
|
|
94
|
-
while (j < text.length && depth > 0) {
|
|
95
|
-
if (text[j] === '{') depth++;
|
|
96
|
-
else if (text[j] === '}') depth--;
|
|
97
|
-
j++;
|
|
98
|
-
}
|
|
99
|
-
const body = text.slice(open + 1, j - 1);
|
|
100
|
-
if (prelude.startsWith('@')) {
|
|
101
|
-
scan(body, prelude);
|
|
102
|
-
} else {
|
|
103
|
-
blocks.push({ prelude, body, context });
|
|
104
|
-
}
|
|
105
|
-
i = j;
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
scan(src, '');
|
|
109
|
-
return blocks;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
function declsOf(blocks, filterFn) {
|
|
113
|
-
const decls = {};
|
|
114
|
-
for (const b of blocks) {
|
|
115
|
-
if (!filterFn(b)) continue;
|
|
116
|
-
for (const m of b.body.matchAll(/--([a-z0-9-]+)\s*:\s*([^;]+);/g)) {
|
|
117
|
-
decls[m[1]] = m[2].trim();
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
return decls;
|
|
121
|
-
}
|
|
122
|
-
|
|
123
80
|
const blocks = extractBlocks(readFileSync(PALETTE, 'utf8'));
|
|
124
|
-
const lightDecls = declsOf(blocks,
|
|
125
|
-
const darkOverrides = declsOf(blocks,
|
|
126
|
-
(b.context.includes('prefers-color-scheme') && b.context.includes('dark') && b.prelude.includes(':root')) ||
|
|
127
|
-
b.prelude.includes('[data-theme="dark"]')
|
|
128
|
-
);
|
|
81
|
+
const lightDecls = declsOf(blocks, isLightRoot);
|
|
82
|
+
const darkOverrides = declsOf(blocks, isDarkBlock);
|
|
129
83
|
if (Object.keys(lightDecls).length === 0) fail(`no top-level :root declarations found in ${PALETTE}`);
|
|
130
84
|
if (Object.keys(darkOverrides).length === 0) fail(`no dark-theme declarations found in ${PALETTE} (@media prefers-color-scheme: dark or [data-theme="dark"])`);
|
|
131
85
|
// CSS cascade: dark blocks override light; unset dark tokens inherit light values.
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
/*
|
|
2
|
+
* Shared CSS token extraction for scripts/audit.mjs and
|
|
3
|
+
* scripts/tokens-json.mjs (previously duplicated in both).
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
/* Brace-aware CSS block extraction. Returns [{ prelude, body, context }]
|
|
7
|
+
where context is the enclosing at-rule prelude ('' at top level).
|
|
8
|
+
One level of at-rule nesting is supported — enough for token files;
|
|
9
|
+
deeper nesting is flattened with its outermost context. Comments are
|
|
10
|
+
stripped first. */
|
|
11
|
+
export function extractBlocks(css) {
|
|
12
|
+
const src = css.replace(/\/\*[\s\S]*?\*\//g, '');
|
|
13
|
+
const blocks = [];
|
|
14
|
+
function scan(text, context) {
|
|
15
|
+
let i = 0;
|
|
16
|
+
while (i < text.length) {
|
|
17
|
+
const open = text.indexOf('{', i);
|
|
18
|
+
if (open === -1) break;
|
|
19
|
+
const prelude = text.slice(i, open).trim().replace(/^[;\s]+/, '');
|
|
20
|
+
let depth = 1, j = open + 1;
|
|
21
|
+
while (j < text.length && depth > 0) {
|
|
22
|
+
if (text[j] === '{') depth++;
|
|
23
|
+
else if (text[j] === '}') depth--;
|
|
24
|
+
j++;
|
|
25
|
+
}
|
|
26
|
+
const body = text.slice(open + 1, j - 1);
|
|
27
|
+
if (prelude.startsWith('@')) scan(body, prelude);
|
|
28
|
+
else blocks.push({ prelude, body, context });
|
|
29
|
+
i = j;
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
scan(src, '');
|
|
33
|
+
return blocks;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
export function declsOf(blocks, filterFn) {
|
|
37
|
+
const decls = {};
|
|
38
|
+
for (const b of blocks) {
|
|
39
|
+
if (!filterFn(b)) continue;
|
|
40
|
+
for (const m of b.body.matchAll(/--([a-z0-9-]+)\s*:\s*([^;]+);/g)) {
|
|
41
|
+
decls[m[1]] = m[2].trim();
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
return decls;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/* Standard tier filters */
|
|
48
|
+
export const isLightRoot = (b) => b.context === '' && b.prelude.includes(':root');
|
|
49
|
+
export const isDarkBlock = (b) =>
|
|
50
|
+
(b.context.includes('prefers-color-scheme') && b.context.includes('dark') && b.prelude.includes(':root')) ||
|
|
51
|
+
b.prelude.includes('[data-theme="dark"]');
|
package/scripts/tokens-json.mjs
CHANGED
|
@@ -13,45 +13,7 @@
|
|
|
13
13
|
*/
|
|
14
14
|
|
|
15
15
|
import { readFileSync, writeFileSync, existsSync } from 'node:fs';
|
|
16
|
-
|
|
17
|
-
/* Brace-aware block extraction — kept in sync with scripts/audit.mjs
|
|
18
|
-
(duplicated deliberately: audit.mjs is a CLI whose import would run
|
|
19
|
-
its main; unifying them is tracked under issue #48's follow-ups). */
|
|
20
|
-
function extractBlocks(css) {
|
|
21
|
-
const src = css.replace(/\/\*[\s\S]*?\*\//g, '');
|
|
22
|
-
const blocks = [];
|
|
23
|
-
function scan(text, context) {
|
|
24
|
-
let i = 0;
|
|
25
|
-
while (i < text.length) {
|
|
26
|
-
const open = text.indexOf('{', i);
|
|
27
|
-
if (open === -1) break;
|
|
28
|
-
const prelude = text.slice(i, open).trim().replace(/^[;\s]+/, '');
|
|
29
|
-
let depth = 1, j = open + 1;
|
|
30
|
-
while (j < text.length && depth > 0) {
|
|
31
|
-
if (text[j] === '{') depth++;
|
|
32
|
-
else if (text[j] === '}') depth--;
|
|
33
|
-
j++;
|
|
34
|
-
}
|
|
35
|
-
const body = text.slice(open + 1, j - 1);
|
|
36
|
-
if (prelude.startsWith('@')) scan(body, prelude);
|
|
37
|
-
else blocks.push({ prelude, body, context });
|
|
38
|
-
i = j;
|
|
39
|
-
}
|
|
40
|
-
}
|
|
41
|
-
scan(src, '');
|
|
42
|
-
return blocks;
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
function declsOf(blocks, filterFn) {
|
|
46
|
-
const decls = {};
|
|
47
|
-
for (const b of blocks) {
|
|
48
|
-
if (!filterFn(b)) continue;
|
|
49
|
-
for (const m of b.body.matchAll(/--([a-z0-9-]+)\s*:\s*([^;]+);/g)) {
|
|
50
|
-
decls[m[1]] = m[2].trim();
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
return decls;
|
|
54
|
-
}
|
|
16
|
+
import { extractBlocks, declsOf, isLightRoot, isDarkBlock } from './lib/css-tokens.mjs';
|
|
55
17
|
|
|
56
18
|
function typeOf(name, value) {
|
|
57
19
|
if (name.startsWith('color-')) return 'color';
|
|
@@ -74,13 +36,10 @@ function valueFor(type, value) {
|
|
|
74
36
|
}
|
|
75
37
|
|
|
76
38
|
const version = JSON.parse(readFileSync('package.json', 'utf8')).version;
|
|
77
|
-
const coreDecls = declsOf(extractBlocks(readFileSync('tokens-core.css', 'utf8')),
|
|
39
|
+
const coreDecls = declsOf(extractBlocks(readFileSync('tokens-core.css', 'utf8')), isLightRoot);
|
|
78
40
|
const paletteBlocks = extractBlocks(readFileSync('tokens-palette.css', 'utf8'));
|
|
79
|
-
const lightDecls = declsOf(paletteBlocks,
|
|
80
|
-
const darkOverrides = declsOf(paletteBlocks,
|
|
81
|
-
(b.context.includes('prefers-color-scheme') && b.context.includes('dark') && b.prelude.includes(':root')) ||
|
|
82
|
-
b.prelude.includes('[data-theme="dark"]')
|
|
83
|
-
);
|
|
41
|
+
const lightDecls = declsOf(paletteBlocks, isLightRoot);
|
|
42
|
+
const darkOverrides = declsOf(paletteBlocks, isDarkBlock);
|
|
84
43
|
|
|
85
44
|
const out = {
|
|
86
45
|
$description: 'Remarque design tokens — GENERATED from tokens-core.css + tokens-palette.css by scripts/tokens-json.mjs. Do not edit; the CSS is the source of truth.',
|
package/tokens-core.css
CHANGED
|
@@ -191,135 +191,6 @@ html {
|
|
|
191
191
|
margin-inline: auto;
|
|
192
192
|
}
|
|
193
193
|
|
|
194
|
-
/* ─── Prose Styling ─────────────────────────────────────── */
|
|
195
|
-
/*
|
|
196
|
-
* Apply .remarque-prose to any container with article/essay content.
|
|
197
|
-
* Handles all typographic details for long-form reading.
|
|
198
|
-
*/
|
|
199
|
-
|
|
200
|
-
.remarque-prose {
|
|
201
|
-
font-family: var(--font-body);
|
|
202
|
-
font-size: var(--text-body);
|
|
203
|
-
line-height: var(--leading-body);
|
|
204
|
-
color: var(--color-fg);
|
|
205
|
-
max-width: var(--content-reading);
|
|
206
|
-
}
|
|
207
|
-
|
|
208
|
-
.remarque-prose > * + * {
|
|
209
|
-
margin-top: var(--space-5);
|
|
210
|
-
}
|
|
211
|
-
|
|
212
|
-
.remarque-prose > :first-child {
|
|
213
|
-
margin-top: 0;
|
|
214
|
-
}
|
|
215
|
-
|
|
216
|
-
.remarque-prose h2 {
|
|
217
|
-
font-family: var(--font-display);
|
|
218
|
-
font-size: var(--text-section);
|
|
219
|
-
line-height: var(--leading-section);
|
|
220
|
-
letter-spacing: var(--tracking-title);
|
|
221
|
-
font-weight: var(--weight-medium);
|
|
222
|
-
margin-top: var(--space-7);
|
|
223
|
-
margin-bottom: var(--space-3);
|
|
224
|
-
color: var(--color-fg);
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
.remarque-prose h3 {
|
|
228
|
-
font-family: var(--font-body);
|
|
229
|
-
font-size: var(--text-body-lg);
|
|
230
|
-
line-height: var(--leading-title);
|
|
231
|
-
font-weight: var(--weight-semibold);
|
|
232
|
-
margin-top: var(--space-6);
|
|
233
|
-
margin-bottom: var(--space-2);
|
|
234
|
-
color: var(--color-fg);
|
|
235
|
-
}
|
|
236
|
-
|
|
237
|
-
.remarque-prose a {
|
|
238
|
-
color: var(--color-link);
|
|
239
|
-
text-decoration: underline;
|
|
240
|
-
text-underline-offset: 0.2em;
|
|
241
|
-
text-decoration-thickness: 1px;
|
|
242
|
-
transition: color var(--motion-fast) var(--motion-easing);
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
.remarque-prose a:hover {
|
|
246
|
-
color: var(--color-link-hover);
|
|
247
|
-
}
|
|
248
|
-
|
|
249
|
-
.remarque-prose strong {
|
|
250
|
-
font-weight: var(--weight-semibold);
|
|
251
|
-
}
|
|
252
|
-
|
|
253
|
-
.remarque-prose em {
|
|
254
|
-
font-style: italic;
|
|
255
|
-
}
|
|
256
|
-
|
|
257
|
-
.remarque-prose blockquote {
|
|
258
|
-
border-left: 2px solid var(--color-border-bold);
|
|
259
|
-
padding-left: var(--space-5);
|
|
260
|
-
margin-left: 0;
|
|
261
|
-
color: var(--color-fg-muted);
|
|
262
|
-
font-style: italic;
|
|
263
|
-
}
|
|
264
|
-
|
|
265
|
-
.remarque-prose ul,
|
|
266
|
-
.remarque-prose ol {
|
|
267
|
-
padding-left: var(--space-5);
|
|
268
|
-
}
|
|
269
|
-
|
|
270
|
-
.remarque-prose li + li {
|
|
271
|
-
margin-top: var(--space-2);
|
|
272
|
-
}
|
|
273
|
-
|
|
274
|
-
.remarque-prose code {
|
|
275
|
-
font-family: var(--font-mono);
|
|
276
|
-
font-size: 0.9em;
|
|
277
|
-
background-color: var(--color-code-bg);
|
|
278
|
-
padding: 0.15em 0.35em;
|
|
279
|
-
border-radius: var(--radius-sm);
|
|
280
|
-
color: var(--color-code-fg);
|
|
281
|
-
}
|
|
282
|
-
|
|
283
|
-
.remarque-prose pre {
|
|
284
|
-
font-family: var(--font-mono);
|
|
285
|
-
font-size: var(--text-meta);
|
|
286
|
-
line-height: 1.6;
|
|
287
|
-
background-color: var(--color-code-bg);
|
|
288
|
-
border: var(--border-width) var(--border-style) var(--color-border);
|
|
289
|
-
border-radius: var(--radius-md);
|
|
290
|
-
padding: var(--space-5);
|
|
291
|
-
overflow-x: auto;
|
|
292
|
-
}
|
|
293
|
-
|
|
294
|
-
.remarque-prose pre code {
|
|
295
|
-
background: none;
|
|
296
|
-
padding: 0;
|
|
297
|
-
border-radius: 0;
|
|
298
|
-
font-size: inherit;
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
.remarque-prose hr {
|
|
302
|
-
border: none;
|
|
303
|
-
border-top: var(--border-width) var(--border-style) var(--color-border);
|
|
304
|
-
margin: var(--space-8) 0;
|
|
305
|
-
}
|
|
306
|
-
|
|
307
|
-
.remarque-prose img {
|
|
308
|
-
max-width: 100%;
|
|
309
|
-
height: auto;
|
|
310
|
-
border: var(--border-width) var(--border-style) var(--color-border);
|
|
311
|
-
border-radius: var(--radius-sm);
|
|
312
|
-
}
|
|
313
|
-
|
|
314
|
-
.remarque-prose figcaption {
|
|
315
|
-
font-family: var(--font-mono);
|
|
316
|
-
font-size: var(--text-meta);
|
|
317
|
-
line-height: var(--leading-meta);
|
|
318
|
-
letter-spacing: var(--tracking-meta);
|
|
319
|
-
color: var(--color-muted);
|
|
320
|
-
margin-top: var(--space-2);
|
|
321
|
-
}
|
|
322
|
-
|
|
323
194
|
/* ─── Focus Styles ──────────────────────────────────────── */
|
|
324
195
|
|
|
325
196
|
:focus-visible {
|
package/tokens.css
CHANGED
package/tokens.json
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"$description": "Remarque design tokens — GENERATED from tokens-core.css + tokens-palette.css by scripts/tokens-json.mjs. Do not edit; the CSS is the source of truth.",
|
|
3
3
|
"$extensions": {
|
|
4
4
|
"remarque": {
|
|
5
|
-
"version": "0.
|
|
5
|
+
"version": "0.4.0",
|
|
6
6
|
"tiers": {
|
|
7
7
|
"core": "immutable identity — overriding forks the system",
|
|
8
8
|
"palette": "sanctioned personalization surface — override freely, then run remarque-audit"
|