@cogenta/theme-magazine 1.1.3 → 1.3.4

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 (126) hide show
  1. package/dist/src/index.d.ts +3 -0
  2. package/dist/src/index.d.ts.map +1 -1
  3. package/dist/src/index.js +3 -0
  4. package/dist/src/index.js.map +1 -1
  5. package/dist/src/render/article.d.ts +32 -0
  6. package/dist/src/render/article.d.ts.map +1 -0
  7. package/dist/src/render/article.js +137 -0
  8. package/dist/src/render/article.js.map +1 -0
  9. package/dist/src/render/blocks/accordion.d.ts.map +1 -1
  10. package/dist/src/render/blocks/accordion.js +9 -13
  11. package/dist/src/render/blocks/accordion.js.map +1 -1
  12. package/dist/src/render/blocks/collection-list.d.ts.map +1 -1
  13. package/dist/src/render/blocks/collection-list.js +91 -118
  14. package/dist/src/render/blocks/collection-list.js.map +1 -1
  15. package/dist/src/render/blocks/cta.d.ts +4 -4
  16. package/dist/src/render/blocks/cta.d.ts.map +1 -1
  17. package/dist/src/render/blocks/cta.js +7 -9
  18. package/dist/src/render/blocks/cta.js.map +1 -1
  19. package/dist/src/render/blocks/embed.d.ts.map +1 -1
  20. package/dist/src/render/blocks/embed.js +17 -20
  21. package/dist/src/render/blocks/embed.js.map +1 -1
  22. package/dist/src/render/blocks/faq.d.ts.map +1 -1
  23. package/dist/src/render/blocks/faq.js +12 -11
  24. package/dist/src/render/blocks/faq.js.map +1 -1
  25. package/dist/src/render/blocks/feature-grid.d.ts.map +1 -1
  26. package/dist/src/render/blocks/feature-grid.js +13 -20
  27. package/dist/src/render/blocks/feature-grid.js.map +1 -1
  28. package/dist/src/render/blocks/gallery.d.ts +6 -6
  29. package/dist/src/render/blocks/gallery.d.ts.map +1 -1
  30. package/dist/src/render/blocks/gallery.js +15 -13
  31. package/dist/src/render/blocks/gallery.js.map +1 -1
  32. package/dist/src/render/blocks/hero.d.ts +6 -5
  33. package/dist/src/render/blocks/hero.d.ts.map +1 -1
  34. package/dist/src/render/blocks/hero.js +15 -14
  35. package/dist/src/render/blocks/hero.js.map +1 -1
  36. package/dist/src/render/blocks/logo-strip.d.ts.map +1 -1
  37. package/dist/src/render/blocks/logo-strip.js +8 -11
  38. package/dist/src/render/blocks/logo-strip.js.map +1 -1
  39. package/dist/src/render/blocks/logos.d.ts.map +1 -1
  40. package/dist/src/render/blocks/logos.js +16 -16
  41. package/dist/src/render/blocks/logos.js.map +1 -1
  42. package/dist/src/render/blocks/media-figure.d.ts +8 -8
  43. package/dist/src/render/blocks/media-figure.d.ts.map +1 -1
  44. package/dist/src/render/blocks/media-figure.js +23 -19
  45. package/dist/src/render/blocks/media-figure.js.map +1 -1
  46. package/dist/src/render/blocks/pricing-table.d.ts.map +1 -1
  47. package/dist/src/render/blocks/pricing-table.js +19 -22
  48. package/dist/src/render/blocks/pricing-table.js.map +1 -1
  49. package/dist/src/render/blocks/prose.d.ts +6 -10
  50. package/dist/src/render/blocks/prose.d.ts.map +1 -1
  51. package/dist/src/render/blocks/prose.js +8 -11
  52. package/dist/src/render/blocks/prose.js.map +1 -1
  53. package/dist/src/render/blocks/quote.d.ts +6 -9
  54. package/dist/src/render/blocks/quote.d.ts.map +1 -1
  55. package/dist/src/render/blocks/quote.js +11 -13
  56. package/dist/src/render/blocks/quote.js.map +1 -1
  57. package/dist/src/render/blocks/stat-counter.d.ts.map +1 -1
  58. package/dist/src/render/blocks/stat-counter.js +9 -10
  59. package/dist/src/render/blocks/stat-counter.js.map +1 -1
  60. package/dist/src/render/blocks/stats.d.ts.map +1 -1
  61. package/dist/src/render/blocks/stats.js +9 -12
  62. package/dist/src/render/blocks/stats.js.map +1 -1
  63. package/dist/src/render/blocks/testimonial.d.ts +4 -13
  64. package/dist/src/render/blocks/testimonial.d.ts.map +1 -1
  65. package/dist/src/render/blocks/testimonial.js +7 -15
  66. package/dist/src/render/blocks/testimonial.js.map +1 -1
  67. package/dist/src/render/chrome.d.ts.map +1 -1
  68. package/dist/src/render/chrome.js +109 -97
  69. package/dist/src/render/chrome.js.map +1 -1
  70. package/dist/src/render/layout.d.ts +28 -0
  71. package/dist/src/render/layout.d.ts.map +1 -0
  72. package/dist/src/render/layout.js +72 -0
  73. package/dist/src/render/layout.js.map +1 -0
  74. package/dist/src/render/render-block.d.ts +15 -13
  75. package/dist/src/render/render-block.d.ts.map +1 -1
  76. package/dist/src/render/render-block.js +53 -29
  77. package/dist/src/render/render-block.js.map +1 -1
  78. package/dist/src/render/story.d.ts +41 -0
  79. package/dist/src/render/story.d.ts.map +1 -0
  80. package/dist/src/render/story.js +65 -0
  81. package/dist/src/render/story.js.map +1 -0
  82. package/dist/src/render/term-archive.d.ts +0 -10
  83. package/dist/src/render/term-archive.d.ts.map +1 -1
  84. package/dist/src/render/term-archive.js +42 -19
  85. package/dist/src/render/term-archive.js.map +1 -1
  86. package/dist/src/render/widget-areas.d.ts +12 -0
  87. package/dist/src/render/widget-areas.d.ts.map +1 -0
  88. package/dist/src/render/widget-areas.js +19 -0
  89. package/dist/src/render/widget-areas.js.map +1 -0
  90. package/dist/theme.config.js +2 -2
  91. package/dist/theme.config.js.map +1 -1
  92. package/package.json +5 -5
  93. package/src/index.ts +3 -0
  94. package/src/render/article.ts +239 -0
  95. package/src/render/blocks/accordion.ts +23 -30
  96. package/src/render/blocks/collection-list.ts +161 -225
  97. package/src/render/blocks/cta.ts +19 -13
  98. package/src/render/blocks/embed.ts +40 -36
  99. package/src/render/blocks/faq.ts +31 -36
  100. package/src/render/blocks/feature-grid.ts +26 -36
  101. package/src/render/blocks/gallery.ts +24 -18
  102. package/src/render/blocks/hero.ts +32 -32
  103. package/src/render/blocks/logo-strip.ts +17 -17
  104. package/src/render/blocks/logos.ts +23 -31
  105. package/src/render/blocks/media-figure.ts +36 -20
  106. package/src/render/blocks/pricing-table.ts +29 -34
  107. package/src/render/blocks/prose.ts +13 -13
  108. package/src/render/blocks/quote.ts +24 -24
  109. package/src/render/blocks/stat-counter.ts +16 -24
  110. package/src/render/blocks/stats.ts +14 -24
  111. package/src/render/blocks/testimonial.ts +12 -17
  112. package/src/render/chrome.ts +123 -104
  113. package/src/render/layout.ts +105 -0
  114. package/src/render/render-block.ts +61 -33
  115. package/src/render/story.ts +139 -0
  116. package/src/render/term-archive.ts +111 -58
  117. package/src/render/widget-areas.ts +22 -0
  118. package/src/styles/archive.css +114 -17
  119. package/src/styles/article.css +237 -0
  120. package/src/styles/base.css +848 -591
  121. package/src/styles/blocks.css +903 -921
  122. package/src/styles/stories.css +593 -0
  123. package/src/styles/theme.css +28 -9
  124. package/src/styles/tokens.css +200 -185
  125. package/src/styles/widgets.css +614 -0
  126. package/tokens.json +18 -18
@@ -1,8 +1,7 @@
1
1
  /*
2
- * Document, accessibility floor, the masthead/colophon frame, and the
3
- * theme's one control (an action link). Everything here reads the design
4
- * system from `tokens.css`; nothing here reads a `--cogenta-*` token
5
- * directly.
2
+ * Document, accessibility floor, the grid, the actions, the masthead, the
3
+ * colophon, and the utility pages the host renders (search, forms, comments).
4
+ * Everything reads `tokens.css`.
6
5
  */
7
6
 
8
7
  /* --------------------------------------------------------------------------
@@ -15,153 +14,137 @@
15
14
  box-sizing: border-box;
16
15
  }
17
16
 
17
+ html {
18
+ -webkit-text-size-adjust: 100%;
19
+ text-size-adjust: 100%;
20
+ scroll-padding-block-start: var(--cg-s8);
21
+ hanging-punctuation: first allow-end last;
22
+ }
23
+
18
24
  body {
19
25
  margin: 0;
20
- background: var(--cg-paper);
26
+ background: var(--cg-canvas);
21
27
  color: var(--cg-ink);
22
- font-family: var(--cogenta-font-sans);
28
+ font-family: var(--cg-font-text);
23
29
  font-size: var(--cg-text-md);
24
- line-height: var(--cg-leading-normal);
30
+ font-weight: var(--cg-weight-regular);
31
+ line-height: var(--cg-leading-text);
25
32
  font-kerning: normal;
33
+ font-optical-sizing: auto;
26
34
  font-variant-ligatures: common-ligatures;
27
- text-underline-offset: 0.16em;
28
- text-decoration-thickness: from-font;
29
- -webkit-text-size-adjust: 100%;
30
- }
31
-
32
- /* The display serif is the theme's whole typographic identity: every
33
- heading gets it once, here, so no block repeats the family. Blocks only
34
- ever adjust size, weight and spacing on top of this. */
35
- h1,
36
- h2,
37
- h3,
38
- h4,
39
- h5,
40
- h6 {
41
- margin: 0;
42
- font-family: var(--cogenta-font-serif);
43
- font-weight: var(--cg-weight-bold);
44
- letter-spacing: var(--cg-tracking-tight);
45
- line-height: var(--cg-leading-tight);
46
- text-wrap: balance;
35
+ font-synthesis: none;
36
+ text-rendering: optimizeLegibility;
37
+ -webkit-font-smoothing: antialiased;
47
38
  }
48
39
 
49
40
  ::selection {
50
- background: var(--cg-accent-tint);
51
- color: var(--cg-accent-tint-ink);
41
+ background: var(--cg-accent);
42
+ color: var(--cg-accent-fg);
52
43
  }
53
44
 
54
45
  img,
55
46
  video,
56
47
  iframe {
57
- max-width: 100%;
58
- height: auto;
48
+ display: block;
49
+ max-inline-size: 100%;
50
+ block-size: auto;
59
51
  }
60
52
 
61
53
  img {
62
- display: block;
63
54
  object-fit: cover;
64
55
  }
65
56
 
57
+ :where(img, video) {
58
+ filter: brightness(var(--cg-image-brightness));
59
+ }
60
+
61
+ :where(h1, h2, h3, h4, h5, h6) {
62
+ margin: 0;
63
+ font-family: var(--cg-font-display);
64
+ font-weight: var(--cg-weight-semibold);
65
+ line-height: var(--cg-leading-heading);
66
+ letter-spacing: var(--cg-tracking-heading);
67
+ text-wrap: balance;
68
+ }
69
+
70
+ :where(p, li, dd, figcaption, blockquote) {
71
+ text-wrap: pretty;
72
+ }
73
+
66
74
  :where(a) {
67
- color: var(--cg-accent);
68
- text-decoration-color: color-mix(in oklab, var(--cg-accent) 40%, transparent);
75
+ color: var(--cg-ink);
76
+ text-decoration-line: underline;
77
+ text-decoration-thickness: var(--cg-rule);
78
+ text-decoration-color: var(--cg-accent-line);
79
+ text-underline-offset: 0.2em;
69
80
  transition:
70
- color var(--cg-duration-fast) var(--cg-ease),
71
- text-decoration-color var(--cg-duration-fast) var(--cg-ease);
81
+ color var(--cg-duration) var(--cg-ease),
82
+ text-decoration-color var(--cg-duration) var(--cg-ease);
72
83
  }
73
84
 
74
85
  :where(a:hover) {
75
- color: var(--cg-accent-hover);
86
+ color: var(--cg-accent);
76
87
  text-decoration-color: currentColor;
77
88
  }
78
89
 
79
90
  :where(hr) {
80
- block-size: 1px;
91
+ block-size: var(--cg-rule);
81
92
  border: 0;
82
93
  margin-block: var(--cg-s10);
83
- background: var(--cg-rule);
94
+ background: var(--cg-line);
95
+ }
96
+
97
+ :where(code, kbd, samp, pre) {
98
+ font-family: var(--cg-font-code);
99
+ font-size: 0.86em;
84
100
  }
85
101
 
86
- /* `renderSocialLinks` (`@cogenta/theme-kit`) hides each platform's own text
87
- label behind its icon with this class — the standard clip-to-1px
88
- technique, kept the accessible name without duplicating it visibly. */
89
102
  .cg-visually-hidden {
90
103
  position: absolute;
91
104
  inline-size: 1px;
92
105
  block-size: 1px;
106
+ margin: -1px;
107
+ padding: 0;
93
108
  overflow: hidden;
94
- clip: rect(0, 0, 0, 0);
109
+ clip-path: inset(50%);
95
110
  white-space: nowrap;
111
+ border: 0;
96
112
  }
97
113
 
98
114
  /* --------------------------------------------------------------------------
99
- Focus, targets, motion
115
+ Focus, targets, motion. Motion is a colour or an underline changing, in
116
+ under 150 ms; nothing moves in space, nothing fades in on scroll.
100
117
  -------------------------------------------------------------------------- */
101
118
 
102
- :where(a, button, summary, [tabindex]):focus-visible {
103
- outline: 2px solid var(--cg-accent);
119
+ :where(a, button, summary, input, select, textarea, [tabindex]):focus-visible {
120
+ outline: var(--cg-rule-strong) solid var(--cg-accent);
104
121
  outline-offset: 3px;
105
- border-radius: var(--cg-radius-sm);
106
122
  }
107
123
 
108
- :where(.cg-action, .cg-mailbag__question, .cg-press__link, .cg-sidenote__link) {
124
+ :where(.cg-action, .cg-nav-toggle-label, .cg-theme-toggle, summary) {
109
125
  min-block-size: 44px;
110
- min-inline-size: 44px;
111
- }
112
-
113
- /*
114
- * The one entrance the theme allows: a restrained fade, no translate — a
115
- * magazine reader scrolling a long feature should not feel the page moving
116
- * under them. Scroll-driven and wrapped in a feature query, since the
117
- * starting state is `opacity: 0` and a browser without
118
- * `animation-timeline` must never be left holding an invisible page.
119
- */
120
- @supports (animation-timeline: view()) {
121
- @media (prefers-reduced-motion: no-preference) {
122
- @keyframes cg-fade-in {
123
- from {
124
- opacity: 0;
125
- }
126
-
127
- to {
128
- opacity: 1;
129
- }
130
- }
131
-
132
- .cg-block {
133
- animation: cg-fade-in linear both;
134
- animation-timeline: view();
135
- animation-range: entry 0% cover 18%;
136
- }
137
- }
138
126
  }
139
127
 
128
+ /* Every transition in this theme reads `--cg-duration`, so reduced motion is
129
+ one declaration rather than an `!important` sweep over every element. */
140
130
  @media (prefers-reduced-motion: reduce) {
141
- *,
142
- *::before,
143
- *::after {
144
- animation-duration: 1ms !important;
145
- animation-iteration-count: 1 !important;
146
- transition-duration: 1ms !important;
147
- scroll-behavior: auto !important;
131
+ :root {
132
+ --cg-duration: 0ms;
148
133
  }
149
134
  }
150
135
 
151
136
  .cg-skip-link {
152
137
  position: absolute;
153
138
  inset-inline-start: var(--cg-s3);
154
- inset-block-start: calc(var(--cg-s3) * -8);
155
- z-index: 10;
139
+ inset-block-start: calc(var(--cg-s16) * -1);
140
+ z-index: 20;
156
141
  padding: var(--cg-s2) var(--cg-s4);
157
- background: var(--cg-accent);
158
- color: var(--cg-accent-ink);
159
- border-radius: var(--cg-radius-sm);
160
- box-shadow: var(--cg-elevation-2);
161
- font-family: var(--cogenta-font-sans);
142
+ background: var(--cg-action);
143
+ color: var(--cg-action-fg);
144
+ font-family: var(--cg-font-ui);
145
+ font-size: var(--cg-text-ui);
162
146
  font-weight: var(--cg-weight-semibold);
163
147
  text-decoration: none;
164
- transition: inset-block-start var(--cg-duration) var(--cg-ease);
165
148
  }
166
149
 
167
150
  .cg-skip-link:focus-visible {
@@ -169,64 +152,86 @@ img {
169
152
  }
170
153
 
171
154
  /* --------------------------------------------------------------------------
172
- Page frame
155
+ The grid. Every block is a section around a twelve-column container; the
156
+ section rhythm is one variable, applied to all of them.
173
157
  -------------------------------------------------------------------------- */
174
158
 
175
159
  .cg-main {
176
160
  display: flow-root;
161
+ overflow-x: clip;
162
+ padding-block-end: calc(var(--cg-section) / 2);
177
163
  }
178
164
 
179
- .cg-block {
180
- max-inline-size: var(--cg-page);
165
+ .cg-container {
166
+ display: grid;
167
+ grid-template-columns: repeat(var(--cg-columns), minmax(0, 1fr));
168
+ column-gap: var(--cg-col-gap);
169
+ align-items: start;
170
+ inline-size: 100%;
171
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
181
172
  margin-inline: auto;
182
- margin-block: var(--cg-section-y);
183
173
  padding-inline: var(--cg-gutter);
184
174
  }
185
175
 
186
- /* --- per-block visual variant (blocks@2.0, RFC 0002) ----------------------
187
- `withBlockVariant` (`@cogenta/theme-kit`) stamps one `data-variant-<axis>`
188
- attribute per axis an author actually set — never all four, never one this
189
- theme does not resolve. Two attribute selectors give every rule here the
190
- same specificity, (0,2,0), which is what lets it override `.cg-block`
191
- above regardless of source order, without `!important` anywhere.
176
+ /* Below the wide breakpoint twelve columns only make slivers: every child
177
+ takes the full row, and each block redistributes from there. */
178
+ .cg-container > * {
179
+ grid-column: 1 / -1;
180
+ min-inline-size: 0;
181
+ }
192
182
 
193
- `background: 'image'` has no theme mechanism to attach an actual image to
194
- a block instance (RFC 0002 adds only the semantic token, not a media
195
- field) — resolved to the same tinted surface as the closest honest
196
- approximation this theme has, rather than silently doing nothing with a
197
- stated author intent. "muted" resolves to `--cg-paper-panel`, the boxed-note
198
- surface this theme already uses for a pull quote's rule background.
199
- ------------------------------------------------------------------------- */
183
+ .cg-section {
184
+ padding-block: calc(var(--cg-section) / 2);
185
+ }
200
186
 
201
- [data-block][data-variant-background="muted"],
202
- [data-block][data-variant-background="image"] {
203
- padding-block: var(--cg-s10);
204
- border-radius: var(--cg-radius-lg);
187
+ :is(.cg-main, .cg-sidebar-layout__content) > .cg-section:first-child {
188
+ padding-block-start: calc(var(--cg-section) * 0.5);
189
+ }
190
+
191
+ /* --- section heads ----------------------------------------------------------
192
+ One head for every titled block: a heavy rule in ink across the grid and
193
+ the title under it in the display face, the way a newspaper labels a
194
+ section of its front page. */
195
+
196
+ .cg-head {
197
+ display: flex;
198
+ align-items: baseline;
199
+ gap: var(--cg-s4);
200
+ padding-block-start: var(--cg-s3);
201
+ border-block-start: var(--cg-rule-heavy) solid var(--cg-line-ink);
202
+ margin-block-end: var(--cg-s6);
203
+ }
204
+
205
+ .cg-head__title {
206
+ font-size: var(--cg-size-heading);
207
+ font-weight: var(--cg-weight-bold);
208
+ line-height: var(--cg-leading-heading);
209
+ letter-spacing: var(--cg-tracking-heading);
205
210
  }
206
211
 
207
- [data-block][data-variant-background="muted"] {
208
- background: var(--cg-paper-panel);
212
+ .cg-empty {
213
+ margin: 0;
214
+ padding-block: var(--cg-s6);
215
+ border-block-start: var(--cg-rule) solid var(--cg-line);
216
+ color: var(--cg-ink-muted);
217
+ font-family: var(--cg-font-ui);
218
+ font-size: var(--cg-text-ui);
209
219
  }
210
220
 
221
+ /* --- per-block variants (blocks@2.0, RFC 0002) --------------------------- */
222
+
223
+ [data-block][data-variant-background="muted"],
211
224
  [data-block][data-variant-background="image"] {
212
- background: var(--cg-paper-tint);
225
+ background: var(--cg-surface-sunken);
226
+ padding-block: calc(var(--cg-section) * 0.75);
213
227
  }
214
228
 
215
229
  [data-block][data-variant-spacing="compact"] {
216
- margin-block: calc(var(--cg-section-y) / 2);
230
+ padding-block: calc(var(--cg-section) / 4);
217
231
  }
218
232
 
219
- /* No rule for "comfortable": it names this theme's existing default, so an
220
- author who picks it explicitly gets exactly what an absent `variant`
221
- already gave them — the whole point of "theme default" being a real,
222
- selectable option and not only the absence of a choice. */
223
-
224
233
  [data-block][data-variant-spacing="spacious"] {
225
- margin-block: calc(var(--cg-section-y) * 1.6);
226
- }
227
-
228
- [data-block][data-variant-align="start"] {
229
- text-align: start;
234
+ padding-block: calc(var(--cg-section) * 0.85);
230
235
  }
231
236
 
232
237
  [data-block][data-variant-align="center"] {
@@ -237,187 +242,244 @@ img {
237
242
  text-align: end;
238
243
  }
239
244
 
240
- [data-block][data-variant-width="full"] {
245
+ [data-block][data-variant-width="full"] > .cg-container {
241
246
  max-inline-size: none;
242
- padding-inline: 0;
243
247
  }
244
248
 
245
- .cg-page__title {
246
- max-inline-size: var(--cg-page);
247
- margin-inline: auto;
248
- margin-block: var(--cg-section-y) var(--cg-s6);
249
- padding-inline: var(--cg-gutter);
250
- font-size: var(--cg-text-3xl);
251
- text-wrap: balance;
249
+ /* --- the title of a page that is not an article ---------------------------- */
250
+
251
+ .cg-page-head {
252
+ padding-block: calc(var(--cg-section) * 0.6) 0;
252
253
  }
253
254
 
254
- /* --------------------------------------------------------------------------
255
- The article header — `renderEntryHeader` (`@cogenta/theme-kit`): a
256
- classification eyebrow set in the masthead's own journal-red accent, the
257
- big serif headline, a dek, an editorial meta line (date, byline, reading
258
- time) between two hairlines, and the cover last, full-bleed.
259
- -------------------------------------------------------------------------- */
255
+ .cg-page-head__inner {
256
+ row-gap: 0;
257
+ }
260
258
 
261
- .cg-entry-header {
262
- max-inline-size: var(--cg-page);
263
- margin-inline: auto;
264
- margin-block: var(--cg-section-y) var(--cg-s10);
265
- padding-inline: var(--cg-gutter);
259
+ .cg-page-head__title {
260
+ padding-block: var(--cg-s4) var(--cg-s5);
261
+ border-block-start: var(--cg-rule-heavy) solid var(--cg-line-ink);
262
+ border-block-end: var(--cg-rule) solid var(--cg-line);
263
+ font-size: var(--cg-size-title);
264
+ font-weight: var(--cg-weight-bold);
265
+ line-height: var(--cg-leading-display);
266
+ letter-spacing: var(--cg-tracking-display);
267
+ }
268
+
269
+ /* A page of running text: the title over the reading column, a hairline
270
+ under it, and the text straight after. */
271
+ .cg-page-head[data-layout="text"] .cg-page-head__title {
272
+ padding-block: 0 var(--cg-s6);
273
+ border-block-start: 0;
274
+ font-size: var(--cg-size-headline);
275
+ font-weight: var(--cg-weight-semibold);
276
+ }
277
+
278
+ @media (min-width: 64rem) {
279
+ .cg-page-head[data-layout="text"] .cg-page-head__title {
280
+ grid-column: var(--cg-col-headline);
281
+ }
266
282
  }
267
283
 
268
- .cg-entry-header__terms {
284
+ .cg-page-head[data-layout="text"] + .cg-prose {
285
+ padding-block-start: var(--cg-s8);
286
+ }
287
+
288
+ /* --------------------------------------------------------------------------
289
+ Actions: a filled rectangle in ink for the primary intent, and for the rest
290
+ the words underlined with an arrow after them. Square corners, no lift, no
291
+ shadow.
292
+ -------------------------------------------------------------------------- */
293
+
294
+ .cg-actions {
269
295
  display: flex;
270
296
  flex-wrap: wrap;
271
- gap: var(--cg-s2) var(--cg-s5);
272
- margin: 0 0 var(--cg-s3);
297
+ align-items: center;
298
+ gap: var(--cg-s3) var(--cg-s8);
299
+ margin: 0;
273
300
  padding: 0;
274
301
  list-style: none;
275
- color: var(--cg-accent);
276
- font-family: var(--cogenta-font-sans);
277
- font-size: var(--cg-text-sm);
278
- font-weight: var(--cg-weight-bold);
279
- letter-spacing: var(--cg-tracking-wider);
280
- text-transform: uppercase;
281
302
  }
282
303
 
283
- .cg-entry-header__terms a {
284
- color: inherit;
304
+ .cg-action {
305
+ font-family: var(--cg-font-ui);
306
+ font-size: var(--cg-text-ui);
307
+ font-weight: var(--cg-weight-semibold);
308
+ line-height: 1.2;
285
309
  text-decoration: none;
310
+ transition:
311
+ background-color var(--cg-duration) var(--cg-ease),
312
+ color var(--cg-duration) var(--cg-ease),
313
+ border-color var(--cg-duration) var(--cg-ease),
314
+ text-decoration-color var(--cg-duration) var(--cg-ease);
286
315
  }
287
316
 
288
- .cg-entry-header__terms a:hover {
289
- text-decoration: underline;
290
- }
291
-
292
- .cg-entry-header__title {
293
- font-size: var(--cg-text-3xl);
294
- text-wrap: balance;
317
+ .cg-action[data-emphasis="primary"] {
318
+ display: inline-flex;
319
+ align-items: center;
320
+ justify-content: center;
321
+ padding: var(--cg-s3) var(--cg-s6);
322
+ border: var(--cg-rule) solid var(--cg-action);
323
+ border-radius: var(--cg-radius-control);
324
+ background: var(--cg-action);
325
+ color: var(--cg-action-fg);
326
+ white-space: nowrap;
295
327
  }
296
328
 
297
- @media (min-width: 48rem) {
298
- .cg-entry-header__title {
299
- font-size: calc(var(--cg-text-3xl) * 1.15);
300
- }
329
+ .cg-action[data-emphasis="primary"]:hover {
330
+ background: var(--cg-action-hover);
331
+ border-color: var(--cg-action-hover);
332
+ color: var(--cg-action-hover-fg);
301
333
  }
302
334
 
303
- .cg-entry-header__excerpt {
304
- margin: var(--cg-s5) 0 0;
305
- max-inline-size: var(--cg-measure);
306
- color: var(--cg-ink-soft);
307
- font-family: var(--cogenta-font-serif);
308
- font-style: italic;
309
- font-size: var(--cg-text-lg);
310
- line-height: var(--cg-leading-relaxed);
311
- text-wrap: pretty;
335
+ /* A text link with an arrow after it. Not a flex container: in one, the
336
+ words and the arrow are two flex items and each gets its own underline.
337
+ As inline content the words carry one continuous underline, and the
338
+ arrow, an inline-block, inherits none (CSS Text Decoration: decorations do
339
+ not propagate to atomic inlines). The same rule draws every arrow link of
340
+ the theme, so a lone arrow cannot exist anywhere. */
341
+ .cg-action[data-emphasis="secondary"],
342
+ .cg-arrow-link {
343
+ display: inline-block;
344
+ color: var(--cg-ink);
345
+ text-decoration-line: underline;
346
+ text-decoration-thickness: var(--cg-rule);
347
+ text-decoration-color: var(--cg-line-strong);
348
+ text-underline-offset: 0.3em;
312
349
  }
313
350
 
314
- .cg-entry-header__meta {
315
- display: flex;
316
- flex-wrap: wrap;
317
- align-items: center;
318
- gap: var(--cg-s2) var(--cg-s5);
319
- margin: var(--cg-s6) 0 0;
351
+ .cg-action[data-emphasis="secondary"] {
320
352
  padding-block: var(--cg-s3);
321
- border-block: 1px solid var(--cg-rule-soft);
322
- color: var(--cg-ink-faint);
323
- font-family: var(--cogenta-font-sans);
324
- font-size: var(--cg-text-sm);
325
- }
326
-
327
- .cg-entry-header__author {
328
- font-weight: var(--cg-weight-semibold);
329
- color: var(--cg-ink-soft);
330
353
  }
331
354
 
332
- .cg-entry-header__cover {
333
- margin: var(--cg-s8) 0 0;
355
+ .cg-action[data-emphasis="secondary"]::after,
356
+ .cg-arrow-link::after {
357
+ content: "\2192" / "";
358
+ display: inline-block;
359
+ margin-inline-start: 0.35em;
334
360
  }
335
361
 
336
- .cg-entry-header__cover img {
337
- inline-size: 100%;
338
- aspect-ratio: 16 / 9;
339
- object-fit: cover;
340
- box-shadow: var(--cg-elevation-2);
362
+ .cg-action[data-emphasis="secondary"]:hover,
363
+ .cg-arrow-link:hover {
364
+ color: var(--cg-accent);
365
+ text-decoration-color: currentColor;
341
366
  }
342
367
 
343
368
  /* --------------------------------------------------------------------------
344
- The masthead — a nameplate row, then a quiet rubric row beneath it, the
345
- way a print front page separates the title from the contents strip.
346
-
347
- L25 pro pass: the rubric row is a real desktop `<nav>` above `56rem` and a
348
- CSS-only `<details>` disclosure below it — never one `<details>` forced
349
- open at width (see `chrome.ts`'s file-level comment for why that fails in
350
- a real browser).
369
+ Masthead: a thin bar, the nameplate, the sections between rules. Not
370
+ sticky: a newspaper's nameplate belongs to the top of the page.
351
371
  -------------------------------------------------------------------------- */
352
372
 
353
373
  .cg-masthead {
354
- position: sticky;
355
- inset-block-start: 0;
356
- z-index: 5;
357
- border-block-end: 3px double var(--cg-rule-heavy);
358
- background: var(--cg-paper);
374
+ position: relative;
375
+ z-index: 10;
376
+ background: var(--cg-canvas);
377
+ font-family: var(--cg-font-ui);
359
378
  }
360
379
 
361
- .cg-masthead__top {
362
- position: relative;
363
- padding-block: var(--cg-s2);
364
- text-align: center;
365
- border-block-end: 1px solid var(--cg-rule-soft);
380
+ .cg-masthead__bar {
381
+ border-block-end: var(--cg-rule) solid var(--cg-line);
382
+ }
383
+
384
+ .cg-masthead__bar-inner {
385
+ display: grid;
386
+ grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr);
387
+ align-items: center;
388
+ gap: var(--cg-s4);
389
+ min-block-size: 3rem;
390
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
391
+ margin-inline: auto;
392
+ padding-inline: var(--cg-gutter);
366
393
  }
367
394
 
368
395
  .cg-masthead__date {
369
- font-family: var(--cogenta-font-sans);
370
- font-size: var(--cg-text-xs);
396
+ margin: 0;
397
+ color: var(--cg-ink);
398
+ font-size: var(--cg-text-label);
371
399
  font-weight: var(--cg-weight-semibold);
372
- letter-spacing: var(--cg-tracking-wider);
400
+ letter-spacing: 0.04em;
401
+ font-variant-numeric: lining-nums tabular-nums;
402
+ }
403
+
404
+ .cg-masthead__date-short {
405
+ display: none;
406
+ }
407
+
408
+ .cg-masthead__tagline {
409
+ margin: 0;
410
+ color: var(--cg-ink-muted);
411
+ font-family: var(--cg-font-text);
412
+ font-size: var(--cg-text-sm);
413
+ font-style: italic;
414
+ text-align: center;
415
+ }
416
+
417
+ .cg-masthead__tools {
418
+ grid-column: 3;
419
+ display: flex;
420
+ align-items: center;
421
+ justify-content: flex-end;
422
+ gap: var(--cg-s2);
423
+ }
424
+
425
+ .cg-action[data-emphasis="masthead"] {
426
+ display: inline-flex;
427
+ align-items: center;
428
+ min-block-size: 2.25rem;
429
+ padding: 0 var(--cg-s4);
430
+ border-radius: var(--cg-radius-control);
431
+ background: var(--cg-accent);
432
+ color: var(--cg-accent-fg);
433
+ font-size: var(--cg-text-label);
434
+ font-weight: var(--cg-weight-bold);
435
+ letter-spacing: var(--cg-tracking-caps);
373
436
  text-transform: uppercase;
374
- color: var(--cg-ink-faint);
375
437
  }
376
438
 
377
- /* The manual light/dark/system control (`renderThemeToggle`, `@cogenta/
378
- theme-kit`) — a small outlined icon button pinned to the end of the top
379
- strip, next to today's date, so it renders on every page regardless of
380
- whether the rubric row below it has a nav or a header action (see
381
- `chrome.ts`'s file-level comment). A plain outline, not `.cg-action`'s
382
- underlined-link style, so it never reads as a navigation item. */
439
+ /* The 44 px target is kept by the bar's own height: the button is drawn
440
+ smaller than the row it sits in, and the row is what a finger aims at. */
441
+ .cg-masthead__tools .cg-action[data-emphasis="masthead"] {
442
+ min-block-size: 2.25rem;
443
+ }
444
+
445
+ .cg-action[data-emphasis="masthead"]:hover {
446
+ background: var(--cg-accent-hover);
447
+ color: var(--cg-accent-fg);
448
+ }
449
+
383
450
  .cg-theme-toggle {
384
- position: absolute;
385
- inset-inline-end: var(--cg-gutter);
386
- inset-block-start: 50%;
387
- transform: translateY(-50%);
388
451
  display: inline-flex;
389
452
  align-items: center;
390
453
  justify-content: center;
391
- inline-size: 1.5rem;
392
- block-size: 1.5rem;
393
- border-radius: var(--cg-radius-sm);
394
- border: 1px solid var(--cg-rule-soft);
454
+ flex: none;
455
+ inline-size: 2.75rem;
456
+ margin-inline-end: calc(var(--cg-s3) * -1);
457
+ padding: 0;
458
+ border: 0;
395
459
  background: transparent;
396
- color: var(--cg-ink-faint);
460
+ color: var(--cg-ink-muted);
397
461
  cursor: pointer;
462
+ transition: color var(--cg-duration) var(--cg-ease);
398
463
  }
399
464
 
400
465
  .cg-theme-toggle:hover {
401
- color: var(--cg-accent);
402
- border-color: var(--cg-accent);
466
+ color: var(--cg-ink);
403
467
  }
404
468
 
405
469
  .cg-theme-toggle__icon {
406
- inline-size: 0.85rem;
407
- block-size: 0.85rem;
470
+ inline-size: 1.05rem;
471
+ block-size: 1.05rem;
408
472
  }
409
473
 
410
474
  .cg-theme-toggle__icon--moon {
411
475
  display: none;
412
476
  }
413
477
 
414
- /* Icon reflects the *current* effective appearance — sun while light, moon
415
- while dark — from the same `[data-theme]`/`prefers-color-scheme` signals
416
- `tokens.css` already keys the whole palette on. */
417
478
  @media (prefers-color-scheme: dark) {
418
479
  :where(:root:not([data-theme="light"])) .cg-theme-toggle__icon--sun {
419
480
  display: none;
420
481
  }
482
+
421
483
  :where(:root:not([data-theme="light"])) .cg-theme-toggle__icon--moon {
422
484
  display: block;
423
485
  }
@@ -431,483 +493,619 @@ img {
431
493
  display: block;
432
494
  }
433
495
 
434
- .cg-masthead__nameplate {
496
+ .cg-masthead__plate {
435
497
  display: flex;
436
- align-items: center;
437
498
  justify-content: center;
438
- gap: var(--cg-s4);
439
- padding: var(--cg-s4) var(--cg-gutter);
499
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
500
+ margin-inline: auto;
501
+ padding: var(--cg-s5) var(--cg-gutter) var(--cg-s4);
440
502
  }
441
503
 
442
- .cg-masthead__wordmark {
443
- display: inline-block;
504
+ .cg-masthead__home {
505
+ display: inline-flex;
506
+ align-items: center;
444
507
  color: var(--cg-ink);
445
- font-family: var(--cogenta-font-serif);
446
- font-weight: var(--cg-weight-black);
447
- font-size: var(--cg-text-2xl);
448
- letter-spacing: var(--cg-tracking-tight);
449
- line-height: 1;
450
508
  text-decoration: none;
451
509
  }
452
510
 
453
- @media (min-width: 32rem) {
454
- .cg-masthead__wordmark {
455
- font-size: var(--cg-text-3xl);
456
- }
511
+ .cg-masthead__home:hover {
512
+ color: var(--cg-ink);
513
+ }
514
+
515
+ .cg-masthead__name {
516
+ font-family: var(--cg-font-display);
517
+ font-size: var(--cg-size-nameplate);
518
+ font-weight: var(--cg-weight-heavy);
519
+ font-variation-settings: "opsz" 144;
520
+ line-height: 1;
521
+ letter-spacing: -0.03em;
522
+ white-space: nowrap;
457
523
  }
458
524
 
459
- /* The uploaded site logo, set at nameplate scale — a masthead's logo is the
460
- nameplate, so it gets the height the wordmark had rather than a header-bar
461
- height borrowed from another theme. */
462
525
  .cg-masthead__logo {
463
526
  display: block;
464
- block-size: 2.5rem;
527
+ block-size: clamp(2.5rem, 6vw, 4.5rem);
465
528
  inline-size: auto;
466
- max-inline-size: min(60vw, 22rem);
529
+ max-inline-size: min(28rem, 80vw);
467
530
  object-fit: contain;
531
+ filter: none;
468
532
  }
469
533
 
470
- @media (min-width: 32rem) {
471
- .cg-masthead__logo {
472
- block-size: 3rem;
473
- }
534
+ .cg-nav-toggle-input {
535
+ position: absolute;
536
+ inline-size: 1px;
537
+ block-size: 1px;
538
+ overflow: hidden;
539
+ clip-path: inset(50%);
540
+ white-space: nowrap;
474
541
  }
475
542
 
476
- .cg-masthead__wordmark:hover {
477
- color: var(--cg-accent);
543
+ .cg-nav-toggle-label {
544
+ display: none;
545
+ flex-direction: column;
546
+ justify-content: center;
547
+ gap: 0.42rem;
548
+ inline-size: 2.75rem;
549
+ padding: 0.7rem;
550
+ cursor: pointer;
478
551
  }
479
552
 
480
- .cg-masthead__nav {
481
- display: none;
482
- border-block-start: 1px solid var(--cg-rule-soft);
483
- padding-block: var(--cg-s3);
553
+ .cg-nav-toggle-input:focus-visible ~ .cg-nav-toggle-label {
554
+ outline: var(--cg-rule-strong) solid var(--cg-accent);
555
+ outline-offset: 2px;
484
556
  }
485
557
 
486
- @media (min-width: 56rem) {
487
- .cg-masthead__nav {
488
- display: block;
489
- }
558
+ .cg-nav-toggle-bar {
559
+ display: block;
560
+ inline-size: 100%;
561
+ block-size: 2px;
562
+ background: var(--cg-ink);
490
563
  }
491
564
 
492
- .cg-masthead__nav-inner {
493
- display: flex;
494
- align-items: center;
495
- justify-content: center;
496
- gap: var(--cg-s6);
497
- max-inline-size: var(--cg-page);
565
+ /* The sections sit between a double rule (a heavy rule over a hairline, two
566
+ pixels apart) and a hairline. */
567
+ .cg-masthead__nav {
568
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
498
569
  margin-inline: auto;
499
570
  padding-inline: var(--cg-gutter);
500
571
  }
501
572
 
502
- .cg-masthead__menu {
573
+ .cg-masthead__sections {
503
574
  display: flex;
504
575
  flex-wrap: wrap;
505
576
  justify-content: center;
506
- gap: var(--cg-s6);
507
- margin: 0;
508
- padding: 0;
577
+ gap: 0 var(--cg-s8);
578
+ position: relative;
579
+ margin: calc(var(--cg-rule-heavy) + var(--cg-rule-strong)) 0 0;
580
+ padding: var(--cg-s1) 0;
581
+ border-block-start: var(--cg-rule) solid var(--cg-line-ink);
582
+ border-block-end: var(--cg-rule) solid var(--cg-line-ink);
509
583
  list-style: none;
510
- font-family: var(--cogenta-font-sans);
511
- font-size: var(--cg-text-sm);
512
- font-weight: var(--cg-weight-semibold);
513
- letter-spacing: var(--cg-tracking-wide);
514
- text-transform: uppercase;
515
- white-space: nowrap;
516
584
  }
517
585
 
518
- .cg-masthead__menu a,
519
- .cg-masthead__menu span {
520
- color: var(--cg-ink-soft);
521
- text-decoration: none;
586
+ /* The heavy half of the double rule, drawn two pixels above the hairline. */
587
+ .cg-masthead__sections::before,
588
+ .cg-colophon__plate::before {
589
+ content: "";
590
+ position: absolute;
591
+ inset-inline: 0;
592
+ inset-block-start: calc((var(--cg-rule-heavy) + var(--cg-rule-strong) + var(--cg-rule)) * -1);
593
+ block-size: var(--cg-rule-heavy);
594
+ background: var(--cg-line-ink);
522
595
  }
523
596
 
524
- .cg-masthead__menu a:hover {
525
- color: var(--cg-accent);
597
+ .cg-masthead__sections a,
598
+ .cg-masthead__sections span {
599
+ display: inline-flex;
600
+ align-items: center;
601
+ min-block-size: 2.75rem;
602
+ color: var(--cg-ink);
603
+ font-size: var(--cg-text-label);
604
+ font-weight: var(--cg-weight-bold);
605
+ letter-spacing: var(--cg-tracking-nav);
606
+ text-transform: uppercase;
607
+ text-decoration-line: underline;
608
+ text-decoration-color: transparent;
609
+ text-decoration-thickness: var(--cg-rule-strong);
610
+ text-underline-offset: 0.5em;
526
611
  }
527
612
 
528
- /*
529
- * Higher specificity than the shared `.cg-action[data-emphasis="primary"]`
530
- * rule below (Actions section, which sets `color: var(--cg-accent)` — a
531
- * text-forward link on the page's own paper background) is required here,
532
- * not optional: this button sits on a solid accent fill, so it needs the
533
- * *foreground* token instead. Without the extra specificity the shared rule
534
- * wins regardless of source order (both are 0,2,0) — confirmed live: the
535
- * button rendered as a solid red rectangle with its own "Subscribe" label
536
- * painted the same red as the fill, and the shared rule's arrow glyph showed
537
- * through a `content: none` that lost the same tie.
538
- */
539
- .cg-masthead__action.cg-action[data-emphasis="primary"] {
540
- color: var(--cg-accent-ink);
541
- background: var(--cg-accent);
542
- padding: var(--cg-s2) var(--cg-s4);
543
- border-block-end-width: 0;
613
+ .cg-masthead__sections a:hover {
614
+ color: var(--cg-ink);
615
+ text-decoration-color: var(--cg-accent);
544
616
  }
545
617
 
546
- .cg-masthead__action.cg-action::after {
547
- content: none;
618
+ .cg-masthead[data-nav="none"] .cg-masthead__plate {
619
+ border-block-end: var(--cg-rule) solid var(--cg-line-ink);
548
620
  }
549
621
 
550
- .cg-masthead__action.cg-action[data-emphasis="primary"]:hover {
551
- background: var(--cg-accent-hover);
552
- color: var(--cg-accent-ink);
553
- }
622
+ @media (max-width: 47.99rem) {
623
+ .cg-masthead__bar-inner {
624
+ grid-template-columns: minmax(0, 1fr) auto;
625
+ min-block-size: 2.75rem;
626
+ }
554
627
 
555
- /* The mobile disclosure — hidden above the desktop breakpoint, shown below it. */
556
- .cg-masthead__disclosure {
557
- display: block;
558
- }
628
+ .cg-masthead__tagline {
629
+ display: none;
630
+ }
631
+
632
+ .cg-masthead__tools {
633
+ grid-column: 2;
634
+ }
635
+
636
+ .cg-masthead__date-long {
637
+ position: absolute;
638
+ inline-size: 1px;
639
+ block-size: 1px;
640
+ overflow: hidden;
641
+ clip-path: inset(50%);
642
+ white-space: nowrap;
643
+ }
559
644
 
560
- @media (min-width: 56rem) {
561
- .cg-masthead__disclosure {
645
+ .cg-masthead__date-short {
646
+ display: inline;
647
+ }
648
+
649
+ .cg-masthead__plate {
650
+ justify-content: flex-start;
651
+ padding-block: var(--cg-s4);
652
+ padding-inline-end: calc(var(--cg-gutter) + 3rem);
653
+ border-block-end: var(--cg-rule-heavy) solid var(--cg-line-ink);
654
+ }
655
+
656
+ .cg-masthead__name {
657
+ font-size: clamp(var(--cg-text-2xl), 9vw, var(--cg-text-3xl));
658
+ }
659
+
660
+ .cg-nav-toggle-label {
661
+ display: flex;
662
+ position: absolute;
663
+ inset-inline-end: calc(var(--cg-gutter) - 0.7rem);
664
+ inset-block-start: calc(2.75rem + var(--cg-rule) + var(--cg-s3));
665
+ }
666
+
667
+ /* The open panel covers the rest of the viewport under the nameplate's
668
+ rule, so the page never shows through beneath the menu. */
669
+ .cg-masthead__nav {
562
670
  display: none;
671
+ position: absolute;
672
+ inset-inline: 0;
673
+ inset-block-start: 100%;
674
+ block-size: calc(100dvh - 100%);
675
+ max-inline-size: none;
676
+ overflow-y: auto;
677
+ overscroll-behavior: contain;
678
+ padding: 0 var(--cg-gutter) var(--cg-s12);
679
+ background: var(--cg-canvas);
680
+ }
681
+
682
+ .cg-nav-toggle-input:checked ~ .cg-masthead__nav {
683
+ display: block;
684
+ }
685
+
686
+ :root:has(.cg-nav-toggle-input:checked) {
687
+ overflow: hidden;
688
+ }
689
+
690
+ .cg-nav-toggle-input:checked ~ .cg-nav-toggle-label .cg-nav-toggle-bar:nth-child(1) {
691
+ transform: translateY(0.3rem) rotate(45deg);
692
+ }
693
+
694
+ .cg-nav-toggle-input:checked ~ .cg-nav-toggle-label .cg-nav-toggle-bar:nth-child(2) {
695
+ transform: translateY(-0.3rem) rotate(-45deg);
696
+ }
697
+
698
+ .cg-masthead__sections {
699
+ flex-direction: column;
700
+ flex-wrap: nowrap;
701
+ gap: 0;
702
+ margin: 0;
703
+ padding: 0;
704
+ border: 0;
705
+ }
706
+
707
+ .cg-masthead__sections::before {
708
+ display: none;
709
+ }
710
+
711
+ .cg-masthead__sections li {
712
+ border-block-end: var(--cg-rule) solid var(--cg-line);
713
+ }
714
+
715
+ .cg-masthead__sections a,
716
+ .cg-masthead__sections span {
717
+ display: flex;
718
+ min-block-size: 3.5rem;
719
+ font-family: var(--cg-font-display);
720
+ font-size: var(--cg-text-xl);
721
+ font-weight: var(--cg-weight-semibold);
722
+ letter-spacing: var(--cg-tracking-heading);
723
+ text-transform: none;
563
724
  }
564
725
  }
565
726
 
566
- .cg-masthead__toggle {
567
- display: flex;
568
- align-items: center;
569
- justify-content: center;
570
- inline-size: 44px;
571
- block-size: 44px;
572
- border: 1px solid var(--cg-rule);
573
- border-radius: var(--cg-radius-sm);
574
- cursor: pointer;
575
- list-style: none;
727
+ /* --------------------------------------------------------------------------
728
+ Colophon: the nameplate again, four dense columns, the legal line.
729
+ -------------------------------------------------------------------------- */
730
+
731
+ .cg-colophon {
732
+ margin-block-start: calc(var(--cg-section) / 2);
733
+ background: var(--cg-canvas);
734
+ color: var(--cg-ink-muted);
735
+ font-family: var(--cg-font-ui);
736
+ font-size: var(--cg-text-sm);
737
+ line-height: var(--cg-leading-ui);
576
738
  }
577
739
 
578
- .cg-masthead__toggle::-webkit-details-marker {
579
- display: none;
740
+ .cg-colophon__inner {
741
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
742
+ margin-inline: auto;
743
+ padding: 0 var(--cg-gutter) var(--cg-s8);
580
744
  }
581
745
 
582
- .cg-masthead__bars {
746
+ .cg-colophon__plate {
583
747
  position: relative;
584
- display: block;
585
- inline-size: 18px;
586
- block-size: 2px;
587
- background: var(--cg-ink);
748
+ margin-block-start: calc(var(--cg-rule-heavy) + var(--cg-rule-strong));
749
+ padding-block: var(--cg-s5) var(--cg-s4);
750
+ border-block-start: var(--cg-rule) solid var(--cg-line-ink);
588
751
  }
589
752
 
590
- .cg-masthead__bars::before,
591
- .cg-masthead__bars::after {
592
- content: "";
593
- position: absolute;
594
- inset-inline-start: 0;
595
- inline-size: 18px;
596
- block-size: 2px;
597
- background: var(--cg-ink);
753
+ .cg-colophon__name {
754
+ font-family: var(--cg-font-display);
755
+ font-size: var(--cg-text-2xl);
756
+ font-weight: var(--cg-weight-heavy);
757
+ letter-spacing: -0.015em;
758
+ line-height: 1;
759
+ color: var(--cg-ink);
760
+ text-decoration: none;
598
761
  }
599
762
 
600
- .cg-masthead__bars::before {
601
- inset-block-start: -6px;
763
+ .cg-colophon__name:hover {
764
+ color: var(--cg-ink);
602
765
  }
603
766
 
604
- .cg-masthead__bars::after {
605
- inset-block-start: 6px;
767
+ .cg-colophon__grid {
768
+ display: grid;
769
+ grid-template-columns: repeat(var(--cg-columns), minmax(0, 1fr));
770
+ column-gap: var(--cg-col-gap);
771
+ row-gap: var(--cg-s8);
772
+ padding-block: var(--cg-s6) var(--cg-s10);
773
+ border-block-start: var(--cg-rule) solid var(--cg-line);
606
774
  }
607
775
 
608
- .cg-masthead__panel {
609
- position: absolute;
610
- inset-inline: var(--cg-gutter);
611
- margin-block-start: var(--cg-s3);
612
- padding: var(--cg-s5);
613
- background: var(--cg-paper-raised);
614
- border: 1px solid var(--cg-rule);
615
- box-shadow: var(--cg-elevation-3);
616
- border-radius: var(--cg-radius-md);
776
+ .cg-colophon__grid > * {
777
+ grid-column: 1 / -1;
617
778
  }
618
779
 
619
- .cg-masthead__panel .cg-masthead__menu {
620
- flex-direction: column;
621
- align-items: flex-start;
622
- gap: var(--cg-s3);
623
- }
780
+ @media (min-width: 48rem) {
781
+ .cg-colophon__about {
782
+ grid-column: 1 / span 5;
783
+ }
624
784
 
625
- .cg-masthead__panel .cg-masthead__action {
626
- display: inline-flex;
627
- margin-block-start: var(--cg-s3);
785
+ .cg-colophon__nav {
786
+ grid-column: 6 / span 5;
787
+ }
788
+
789
+ .cg-colophon__follow {
790
+ grid-column: 11 / span 2;
791
+ }
628
792
  }
629
793
 
630
- /* --------------------------------------------------------------------------
631
- The colophon — the print magazine's inside-back-cover imprint, in a dense
632
- four-column layout: brand + tagline, a section index, social icons, and
633
- a closing note with the branding fragment last, never dropped, never
634
- restyled beyond the theme's palette.
635
- -------------------------------------------------------------------------- */
794
+ @media (min-width: 64rem) {
795
+ .cg-colophon__about {
796
+ grid-column: 1 / span 4;
797
+ }
636
798
 
637
- .cg-colophon {
638
- margin-block-start: var(--cg-section-y);
639
- padding: var(--cg-s16) var(--cg-gutter) var(--cg-s10);
640
- background: var(--cg-paper-panel);
641
- color: var(--cg-ink-soft);
642
- border-block-start: 3px double var(--cg-rule-heavy);
643
- font-family: var(--cogenta-font-sans);
644
- font-size: var(--cg-text-sm);
645
- }
799
+ .cg-colophon__nav {
800
+ grid-column: 6 / span 5;
801
+ }
646
802
 
647
- .cg-colophon__grid {
648
- display: grid;
649
- gap: var(--cg-s10);
650
- max-inline-size: var(--cg-page);
651
- margin-inline: auto;
652
- grid-template-columns: 1fr;
653
- }
803
+ /* Without an about column (a host that passes no tagline and no note) the
804
+ links take its place, and the rule before them goes with it. */
805
+ .cg-colophon__nav:first-child {
806
+ grid-column: 1 / span 6;
807
+ }
654
808
 
655
- @media (min-width: 40rem) {
656
- .cg-colophon__grid {
657
- grid-template-columns: 1fr 1fr;
809
+ .cg-colophon__nav:first-child::before {
810
+ content: none;
658
811
  }
659
- }
660
812
 
661
- @media (min-width: 68rem) {
662
- .cg-colophon__grid {
663
- grid-template-columns: 1.3fr 1fr 0.8fr 1fr;
664
- align-items: start;
813
+ /* A column rule in the middle of each gutter between the columns. */
814
+ .cg-colophon__nav,
815
+ .cg-colophon__follow {
816
+ position: relative;
817
+ }
818
+
819
+ .cg-colophon__nav::before,
820
+ .cg-colophon__follow::before {
821
+ content: "";
822
+ position: absolute;
823
+ inset-block: 0;
824
+ inset-inline-start: calc(var(--cg-col-gap) / -2);
825
+ inline-size: var(--cg-rule);
826
+ background: var(--cg-line);
665
827
  }
666
828
  }
667
829
 
668
- .cg-colophon__wordmark {
669
- display: inline-block;
830
+ .cg-colophon__tagline {
831
+ margin: 0;
832
+ max-inline-size: var(--cg-measure-short);
670
833
  color: var(--cg-ink);
671
- font-family: var(--cogenta-font-serif);
672
- font-weight: var(--cg-weight-bold);
673
- font-size: var(--cg-text-lg);
674
- text-decoration: none;
834
+ font-family: var(--cg-font-text);
835
+ font-size: var(--cg-text-md);
836
+ font-style: italic;
837
+ line-height: var(--cg-leading-snug);
675
838
  }
676
839
 
677
- .cg-colophon__tagline {
678
- margin: var(--cg-s3) 0 0;
679
- max-inline-size: 28ch;
680
- line-height: var(--cg-leading-relaxed);
840
+ .cg-colophon__note {
841
+ margin-block-start: var(--cg-s3);
842
+ max-inline-size: var(--cg-measure-short);
681
843
  }
682
844
 
683
- .cg-colophon__heading {
684
- margin: 0 0 var(--cg-s3);
685
- font-family: var(--cogenta-font-sans);
686
- font-size: var(--cg-text-xs);
687
- font-weight: var(--cg-weight-bold);
688
- letter-spacing: var(--cg-tracking-wider);
689
- text-transform: uppercase;
690
- color: var(--cg-ink-faint);
845
+ .cg-colophon__note p {
846
+ margin: 0;
847
+ }
848
+
849
+ .cg-colophon__note p + p {
850
+ margin-block-start: var(--cg-s2);
691
851
  }
692
852
 
693
- .cg-colophon__menu {
853
+ .cg-colophon__links {
854
+ columns: 2;
855
+ column-gap: var(--cg-col-gap);
694
856
  margin: 0;
695
857
  padding: 0;
696
858
  list-style: none;
697
859
  }
698
860
 
699
- .cg-colophon__menu li {
700
- margin-block-end: var(--cg-s2);
861
+ .cg-colophon__links li {
862
+ break-inside: avoid;
701
863
  }
702
864
 
703
- .cg-colophon__menu a,
704
- .cg-colophon__menu span {
705
- color: var(--cg-ink-soft);
706
- text-decoration: none;
865
+ .cg-colophon__links a,
866
+ .cg-colophon__links span {
867
+ display: inline-flex;
868
+ align-items: center;
869
+ min-block-size: 2.25rem;
870
+ color: var(--cg-ink);
871
+ font-weight: var(--cg-weight-medium);
872
+ text-decoration-color: transparent;
873
+ text-underline-offset: 0.3em;
707
874
  }
708
875
 
709
- .cg-colophon__menu a:hover {
710
- color: var(--cg-accent);
876
+ .cg-colophon__links a:hover {
877
+ color: var(--cg-ink);
878
+ text-decoration-color: var(--cg-accent);
711
879
  }
712
880
 
713
- /* The social-icon column — `renderSocialLinks` (`@cogenta/theme-kit`) emits
714
- a bare `<ul>`; this theme styles the icons into a quiet row of circles. */
881
+ /* The profiles are listed with their names: the column has no heading, so
882
+ the names are what tell a reader what the column is. */
715
883
  .cg-colophon__social {
716
884
  display: flex;
717
- flex-wrap: wrap;
718
- gap: var(--cg-s3);
885
+ flex-direction: column;
886
+ gap: 0;
719
887
  margin: 0;
720
888
  padding: 0;
721
889
  list-style: none;
722
890
  }
723
891
 
724
892
  .cg-colophon__social-item a {
725
- display: flex;
893
+ display: inline-flex;
726
894
  align-items: center;
727
- justify-content: center;
728
- inline-size: 2.25rem;
729
- block-size: 2.25rem;
730
- border: 1px solid var(--cg-rule);
731
- border-radius: 50%;
732
- color: var(--cg-ink-soft);
733
- transition:
734
- color var(--cg-duration) var(--cg-ease),
735
- border-color var(--cg-duration) var(--cg-ease);
895
+ gap: var(--cg-s3);
896
+ min-block-size: 2.25rem;
897
+ color: var(--cg-ink);
898
+ font-weight: var(--cg-weight-medium);
899
+ text-decoration: none;
900
+ transition: color var(--cg-duration) var(--cg-ease);
736
901
  }
737
902
 
738
903
  .cg-colophon__social-item a:hover {
739
904
  color: var(--cg-accent);
740
- border-color: var(--cg-accent);
741
- }
742
-
743
- .cg-social__icon {
744
- inline-size: 1.1rem;
745
- block-size: 1.1rem;
746
905
  }
747
906
 
748
- .cg-colophon__note {
749
- margin: 0 0 var(--cg-s4);
750
- max-inline-size: 32ch;
751
- line-height: var(--cg-leading-relaxed);
907
+ .cg-colophon__social .cg-visually-hidden {
908
+ position: static;
909
+ inline-size: auto;
910
+ block-size: auto;
911
+ margin: 0;
912
+ overflow: visible;
913
+ clip-path: none;
914
+ white-space: normal;
752
915
  }
753
916
 
754
- .cg-colophon__branding {
755
- display: flex;
756
- align-items: flex-start;
917
+ .cg-social__icon {
918
+ inline-size: 1rem;
919
+ block-size: 1rem;
920
+ flex: none;
757
921
  }
758
922
 
759
- /* The fixed branding fragment (`cg-site-footer__branding`, emitted by
760
- `cogenta serve` itself, never by this theme) — restyled to the palette
761
- without touching its markup. */
762
- .cg-site-footer__branding a {
923
+ .cg-colophon__legal {
763
924
  display: flex;
925
+ flex-wrap: wrap;
764
926
  align-items: center;
765
- gap: 0.4em;
766
- color: var(--cg-ink-faint);
767
- opacity: 0.8;
768
- transition: opacity var(--cg-duration) var(--cg-ease);
769
- }
770
-
771
- .cg-site-footer__branding a:hover,
772
- .cg-site-footer__branding a:focus-visible {
773
- opacity: 1;
774
- }
775
-
776
- .cg-site-footer__brand-logo {
777
- display: block;
778
- /* Explicit pixels, not `em`: relative sizing cascaded from the footer's
779
- own small font-size and made the credit mark unreadably tiny. */
780
- block-size: 25px;
781
- inline-size: auto;
782
- }
783
-
784
- .cg-site-footer__version {
785
- font-variant-numeric: tabular-nums;
786
- font-size: 0.9em;
927
+ justify-content: space-between;
928
+ gap: var(--cg-s3) var(--cg-s8);
929
+ padding-block-start: var(--cg-s4);
930
+ border-block-start: var(--cg-rule) solid var(--cg-line-ink);
931
+ font-size: var(--cg-text-xs);
932
+ letter-spacing: 0.02em;
787
933
  }
788
934
 
789
- /* --------------------------------------------------------------------------
790
- Actions — the theme's only control, a text-forward link rather than a
791
- filled button, in keeping with a page whose whole vocabulary is type and
792
- rules rather than UI chrome.
793
- -------------------------------------------------------------------------- */
794
-
795
- .cg-actions {
796
- display: flex;
797
- flex-wrap: wrap;
798
- gap: var(--cg-s5);
799
- margin: var(--cg-s8) 0 0;
800
- padding: 0;
801
- list-style: none;
935
+ .cg-colophon__copyright {
936
+ margin: 0;
937
+ font-variant-numeric: lining-nums tabular-nums;
802
938
  }
803
939
 
804
- .cg-action {
940
+ .cg-colophon__branding a {
805
941
  display: inline-flex;
806
942
  align-items: center;
807
- gap: var(--cg-s2);
808
- padding-block: var(--cg-s2);
809
- border: 0;
810
- border-block-end: 2px solid transparent;
811
- font-family: var(--cogenta-font-sans);
812
- font-size: var(--cg-text-sm);
813
- font-weight: var(--cg-weight-bold);
814
- letter-spacing: var(--cg-tracking-wide);
815
- text-transform: uppercase;
943
+ gap: 0.5em;
944
+ color: var(--cg-ink-subtle);
816
945
  text-decoration: none;
817
- white-space: nowrap;
818
- transition:
819
- color var(--cg-duration) var(--cg-ease),
820
- border-color var(--cg-duration) var(--cg-ease);
821
- }
822
-
823
- .cg-action::after {
824
- content: "\2192";
825
- transition: transform var(--cg-duration) var(--cg-ease);
826
- }
827
-
828
- .cg-action[data-emphasis="primary"] {
829
- color: var(--cg-accent);
830
- border-block-end-color: var(--cg-accent);
831
946
  }
832
947
 
833
- .cg-action[data-emphasis="secondary"] {
948
+ .cg-colophon__branding a:hover {
834
949
  color: var(--cg-ink);
835
- border-block-end-color: var(--cg-rule-heavy);
836
950
  }
837
951
 
838
- .cg-action:hover {
839
- color: var(--cg-accent-hover);
840
- border-block-end-color: var(--cg-accent-hover);
952
+ .cg-site-footer__brand-logo {
953
+ display: block;
954
+ block-size: 18px;
955
+ inline-size: auto;
841
956
  }
842
957
 
843
- .cg-action:hover::after {
844
- transform: translateX(0.2em);
958
+ .cg-site-footer__version {
959
+ font-variant-numeric: tabular-nums;
845
960
  }
846
961
 
847
962
  /* --------------------------------------------------------------------------
848
- Search, forms, comments — public utility pages and post-content furniture.
849
- `/search`, `/forms/{name}` and the comment thread appended after an entry
850
- page all render real markup with fixed `cg-*` classes from
851
- `@cogenta/theme-kit`; this theme styles them to the same measure the page
852
- title uses, rather than leaving them to run edge to edge unstyled.
963
+ Search, forms and comments: the utility pages, in the same register.
853
964
  -------------------------------------------------------------------------- */
854
965
 
966
+ /* The results page is set like a section front: the query very large on the
967
+ page's own left edge, a heavy rule, then the results in one column held to
968
+ a reading width. The host renders it in a bare `<main class="cg-main">`. */
969
+ :is(.cg-main, .cg-sidebar-layout__content) > .cg-page__title,
855
970
  .cg-search__form,
856
971
  .cg-search__results,
857
972
  .cg-search__empty,
858
- .cg-search__error,
973
+ .cg-search__error {
974
+ box-sizing: border-box;
975
+ inline-size: 100%;
976
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
977
+ margin-inline: auto;
978
+ padding-inline: var(--cg-gutter) max(var(--cg-gutter), calc(100% - var(--cg-gutter) - 46rem));
979
+ }
980
+
859
981
  .cg-form,
860
- .cg-form__confirmation,
861
- .cg-comments {
862
- max-inline-size: var(--cg-page);
982
+ .cg-form__confirmation {
983
+ max-inline-size: calc(var(--cg-measure) + var(--cg-gutter) * 2);
863
984
  margin-inline: auto;
864
985
  padding-inline: var(--cg-gutter);
865
986
  }
866
987
 
988
+ :is(.cg-main, .cg-sidebar-layout__content) > .cg-page__title {
989
+ margin-block: calc(var(--cg-section) * 0.55) 0;
990
+ padding-block-end: var(--cg-s5);
991
+ font-size: var(--cg-size-headline);
992
+ font-weight: var(--cg-weight-bold);
993
+ line-height: var(--cg-leading-display);
994
+ letter-spacing: var(--cg-tracking-display);
995
+ position: relative;
996
+ }
997
+
998
+ /* The rule runs the page's width even though the title is held narrower. */
999
+ :is(.cg-main, .cg-sidebar-layout__content) > .cg-page__title::after {
1000
+ content: "";
1001
+ position: absolute;
1002
+ inset-inline: var(--cg-gutter);
1003
+ inset-block-end: 0;
1004
+ border-block-end: var(--cg-rule-heavy) solid var(--cg-line-ink);
1005
+ }
1006
+
867
1007
  .cg-search__form {
868
1008
  display: flex;
869
1009
  flex-wrap: wrap;
870
1010
  align-items: end;
871
- gap: var(--cg-s3);
872
- margin-block-end: var(--cg-s8);
1011
+ gap: var(--cg-s3) var(--cg-s4);
1012
+ margin-block: var(--cg-s8) var(--cg-s10);
873
1013
  }
874
1014
 
875
1015
  .cg-search__form label,
876
1016
  .cg-form__field label,
877
1017
  .cg-comment__form label {
878
1018
  display: block;
879
- font-family: var(--cogenta-font-sans);
880
- font-size: var(--cg-text-sm);
881
- font-weight: var(--cg-weight-semibold);
882
1019
  margin-block-end: var(--cg-s2);
1020
+ font-family: var(--cg-font-ui);
1021
+ font-size: var(--cg-text-label);
1022
+ font-weight: var(--cg-weight-bold);
1023
+ letter-spacing: var(--cg-tracking-caps);
1024
+ text-transform: uppercase;
1025
+ color: var(--cg-ink-muted);
1026
+ }
1027
+
1028
+ .cg-search__form label {
1029
+ flex-basis: 100%;
1030
+ margin-block-end: 0;
883
1031
  }
884
1032
 
885
1033
  .cg-search__form input[type="search"] {
886
- flex: 1 1 16rem;
1034
+ flex: 1 1 18rem;
1035
+ }
1036
+
1037
+ /* The host sets the count inside the title. */
1038
+ .cg-search__count {
1039
+ display: block;
1040
+ margin-block: var(--cg-s4) 0;
1041
+ line-height: 1.2;
1042
+ color: var(--cg-ink-muted);
1043
+ font-family: var(--cg-font-ui);
1044
+ font-size: var(--cg-text-label);
1045
+ font-weight: var(--cg-weight-bold);
1046
+ letter-spacing: var(--cg-tracking-caps);
1047
+ text-transform: uppercase;
887
1048
  }
888
1049
 
889
1050
  .cg-search__results {
890
- margin: 0 auto;
891
1051
  display: grid;
892
- gap: var(--cg-s5);
1052
+ gap: 0;
1053
+ margin-block: 0 var(--cg-section);
1054
+ list-style: none;
1055
+ }
1056
+
1057
+ .cg-search__hit {
893
1058
  padding-block: var(--cg-s5);
894
- border-block-start: 1px solid var(--cg-rule);
1059
+ border-block-start: var(--cg-rule) solid var(--cg-line);
1060
+ }
1061
+
1062
+ .cg-search__title {
1063
+ color: var(--cg-ink);
1064
+ font-family: var(--cg-font-display);
1065
+ font-size: var(--cg-size-story);
1066
+ font-weight: var(--cg-weight-semibold);
1067
+ line-height: var(--cg-leading-heading);
1068
+ text-decoration-color: transparent;
1069
+ text-wrap: balance;
1070
+ }
1071
+
1072
+ a.cg-search__title:hover {
1073
+ color: var(--cg-ink);
1074
+ text-decoration-color: var(--cg-accent);
1075
+ }
1076
+
1077
+ .cg-search__excerpt {
1078
+ margin: var(--cg-s2) 0 0;
1079
+ color: var(--cg-ink-muted);
1080
+ font-family: var(--cg-font-text);
1081
+ font-size: var(--cg-text-sm);
1082
+ line-height: var(--cg-leading-snug);
1083
+ }
1084
+
1085
+ .cg-search__meta {
1086
+ margin: var(--cg-s2) 0 0;
1087
+ color: var(--cg-ink-muted);
1088
+ font-family: var(--cg-font-ui);
1089
+ font-size: var(--cg-text-xs);
1090
+ font-variant-numeric: lining-nums tabular-nums;
895
1091
  }
896
1092
 
897
1093
  .cg-search__empty,
898
1094
  .cg-comments__empty,
899
- .cg-comments__closed {
900
- color: var(--cg-ink-faint);
901
- font-family: var(--cogenta-font-sans);
1095
+ .cg-comments__closed,
1096
+ .cg-form__help {
1097
+ color: var(--cg-ink-muted);
902
1098
  }
903
1099
 
904
1100
  .cg-search__error,
905
1101
  .cg-form__error,
906
1102
  .cg-form__field-error {
907
1103
  color: var(--cg-ink);
908
- font-weight: var(--cg-weight-bold);
1104
+ font-weight: var(--cg-weight-semibold);
909
1105
  }
910
1106
 
1107
+ /* Fields are a baseline, not a box: a rule under the words, darkening to ink
1108
+ on focus. */
911
1109
  .cg-search__form input,
912
1110
  .cg-form__field input,
913
1111
  .cg-form__field select,
@@ -915,55 +1113,78 @@ img {
915
1113
  .cg-comment__form input,
916
1114
  .cg-comment__form textarea {
917
1115
  inline-size: 100%;
918
- padding: var(--cg-s3) var(--cg-s4);
919
- border: 1px solid var(--cg-rule);
920
- border-radius: var(--cg-radius-sm);
921
- background: var(--cg-paper);
1116
+ min-block-size: 44px;
1117
+ padding: var(--cg-s2) 0;
1118
+ border: 0;
1119
+ border-block-end: var(--cg-rule) solid var(--cg-line-strong);
1120
+ border-radius: 0;
1121
+ background: transparent;
922
1122
  color: var(--cg-ink);
923
- font: inherit;
924
- font-family: var(--cogenta-font-sans);
1123
+ font-family: var(--cg-font-text);
1124
+ font-size: var(--cg-text-md);
1125
+ line-height: var(--cg-leading-snug);
1126
+ transition: border-color var(--cg-duration) var(--cg-ease);
1127
+ }
1128
+
1129
+ .cg-form__field textarea,
1130
+ .cg-comment__form textarea {
1131
+ padding: var(--cg-s3);
1132
+ border: var(--cg-rule) solid var(--cg-line-strong);
1133
+ border-radius: var(--cg-radius);
1134
+ resize: vertical;
1135
+ }
1136
+
1137
+ .cg-search__form input:focus-visible,
1138
+ .cg-form__field :is(input, select, textarea):focus-visible,
1139
+ .cg-comment__form :is(input, textarea):focus-visible {
1140
+ outline: none;
1141
+ border-color: var(--cg-ink);
1142
+ box-shadow: inset 0 calc(var(--cg-rule) * -1) 0 var(--cg-ink);
925
1143
  }
926
1144
 
927
1145
  .cg-form__field input[aria-invalid="true"],
928
1146
  .cg-form__field select[aria-invalid="true"],
929
1147
  .cg-form__field textarea[aria-invalid="true"] {
930
- border-width: 2px;
931
- border-color: var(--cg-rule-heavy);
1148
+ border-color: var(--cg-ink);
1149
+ border-block-end-width: var(--cg-rule-strong);
932
1150
  }
933
1151
 
934
1152
  .cg-search__form button,
935
1153
  .cg-form button[type="submit"],
936
1154
  .cg-comment__form button[type="submit"] {
1155
+ min-block-size: 44px;
937
1156
  padding: var(--cg-s3) var(--cg-s6);
938
- border: 0;
939
- border-block-end: 2px solid var(--cg-accent-ink);
940
- background: var(--cg-accent);
941
- color: var(--cg-accent-ink);
942
- font-family: var(--cogenta-font-sans);
943
- font-weight: var(--cg-weight-bold);
944
- letter-spacing: var(--cg-tracking-wide);
945
- text-transform: uppercase;
1157
+ border: var(--cg-rule) solid var(--cg-action);
1158
+ border-radius: var(--cg-radius-control);
1159
+ background: var(--cg-action);
1160
+ color: var(--cg-action-fg);
1161
+ font-family: var(--cg-font-ui);
1162
+ font-size: var(--cg-text-ui);
1163
+ font-weight: var(--cg-weight-semibold);
946
1164
  cursor: pointer;
947
- transition: background-color var(--cg-duration) var(--cg-ease);
1165
+ transition:
1166
+ background-color var(--cg-duration) var(--cg-ease),
1167
+ border-color var(--cg-duration) var(--cg-ease),
1168
+ color var(--cg-duration) var(--cg-ease);
948
1169
  }
949
1170
 
950
1171
  .cg-search__form button:hover,
951
1172
  .cg-form button[type="submit"]:hover,
952
1173
  .cg-comment__form button[type="submit"]:hover {
953
- background: var(--cg-accent-hover);
1174
+ background: var(--cg-action-hover);
1175
+ border-color: var(--cg-action-hover);
1176
+ color: var(--cg-action-hover-fg);
954
1177
  }
955
1178
 
956
- .cg-form__field,
957
- .cg-comment__form p {
1179
+ .cg-form__field {
958
1180
  display: block;
959
- margin-block-end: var(--cg-s5);
1181
+ margin-block-end: var(--cg-s6);
960
1182
  }
961
1183
 
962
1184
  .cg-form__help {
963
1185
  margin: var(--cg-s2) 0 0;
964
- font-family: var(--cogenta-font-sans);
1186
+ font-family: var(--cg-font-ui);
965
1187
  font-size: var(--cg-text-sm);
966
- color: var(--cg-ink-faint);
967
1188
  }
968
1189
 
969
1190
  .cg-form__choice {
@@ -971,7 +1192,7 @@ img {
971
1192
  align-items: center;
972
1193
  gap: var(--cg-s2);
973
1194
  margin-inline-end: var(--cg-s4);
974
- font-weight: normal;
1195
+ font-weight: var(--cg-weight-regular);
975
1196
  }
976
1197
 
977
1198
  .cg-form__honeypot,
@@ -983,17 +1204,34 @@ img {
983
1204
  inset-inline-start: -9999px;
984
1205
  }
985
1206
 
1207
+ /* Comments: letters under the article, on the same twelve columns and the
1208
+ same centred reading column as the text above them. */
986
1209
  .cg-comments {
987
- margin-block-start: var(--cg-section-y);
988
- padding-block-start: var(--cg-s8);
989
- padding-block-end: var(--cg-section-y);
990
- border-block-start: 3px double var(--cg-rule-heavy);
991
- font-family: var(--cogenta-font-sans);
1210
+ display: grid;
1211
+ grid-template-columns: repeat(var(--cg-columns), minmax(0, 1fr));
1212
+ column-gap: var(--cg-col-gap);
1213
+ max-inline-size: calc(var(--cg-page) + var(--cg-gutter) * 2);
1214
+ margin: 0 auto var(--cg-section);
1215
+ padding: var(--cg-s5) var(--cg-gutter) 0;
1216
+ }
1217
+
1218
+ .cg-comments > * {
1219
+ grid-column: 1 / -1;
1220
+ min-inline-size: 0;
1221
+ }
1222
+
1223
+ @media (min-width: 64rem) {
1224
+ .cg-comments > * {
1225
+ grid-column: var(--cg-col-reading);
1226
+ }
992
1227
  }
993
1228
 
994
1229
  .cg-comments > h2 {
1230
+ padding-block-start: var(--cg-s3);
1231
+ border-block-start: var(--cg-rule-heavy) solid var(--cg-line-ink);
1232
+ margin-block-end: var(--cg-s5);
995
1233
  font-size: var(--cg-text-xl);
996
- margin-block-end: var(--cg-s6);
1234
+ font-weight: var(--cg-weight-bold);
997
1235
  }
998
1236
 
999
1237
  .cg-comments__list,
@@ -1005,33 +1243,52 @@ img {
1005
1243
 
1006
1244
  .cg-comment {
1007
1245
  padding-block: var(--cg-s5);
1008
- border-block-end: 1px solid var(--cg-rule-soft);
1246
+ border-block-start: var(--cg-rule) solid var(--cg-line);
1009
1247
  }
1010
1248
 
1011
1249
  .cg-comment__replies {
1012
- padding-block-start: var(--cg-s5);
1013
- }
1014
-
1015
- .cg-comment__replies .cg-comment {
1250
+ margin-block-start: var(--cg-s4);
1016
1251
  padding-inline-start: var(--cg-s6);
1017
- border-inline-start: 2px solid var(--cg-rule-soft);
1018
- border-block-end: 0;
1252
+ border-inline-start: var(--cg-rule) solid var(--cg-line);
1019
1253
  }
1020
1254
 
1021
1255
  .cg-comment__meta {
1022
1256
  display: flex;
1023
- gap: var(--cg-s3);
1024
- align-items: baseline;
1257
+ flex-wrap: wrap;
1258
+ gap: var(--cg-s1) var(--cg-s3);
1259
+ margin: 0 0 var(--cg-s2);
1260
+ font-family: var(--cg-font-ui);
1025
1261
  font-size: var(--cg-text-sm);
1026
- color: var(--cg-ink-faint);
1027
- margin-block-end: var(--cg-s2);
1028
1262
  }
1029
1263
 
1030
1264
  .cg-comment__author {
1031
- font-weight: var(--cg-weight-semibold);
1032
1265
  color: var(--cg-ink);
1266
+ font-weight: var(--cg-weight-bold);
1033
1267
  }
1034
1268
 
1035
- .cg-comment__body {
1269
+ .cg-comment__date {
1270
+ color: var(--cg-ink-muted);
1271
+ font-variant-numeric: lining-nums tabular-nums;
1272
+ }
1273
+
1274
+ .cg-comment__body p {
1036
1275
  margin: 0;
1037
1276
  }
1277
+
1278
+ .cg-comment__body p + p {
1279
+ margin-block-start: var(--cg-s3);
1280
+ }
1281
+
1282
+ .cg-comment__form {
1283
+ display: grid;
1284
+ gap: var(--cg-s3);
1285
+ margin-block-start: var(--cg-s6);
1286
+ }
1287
+
1288
+ .cg-comment__form > * {
1289
+ margin: 0;
1290
+ }
1291
+
1292
+ .cg-comment__form button[type="submit"] {
1293
+ justify-self: start;
1294
+ }