Pre-launch — Gluecron is in final validation. Public signups and git hosting for non-owner users open after launch review.
Commit2fd463b

feat(design): Quiet Intelligence light-first foundation

feat(design): Quiet Intelligence light-first foundation

Unifies the logged-in app shell with the light editorial landing so the
whole product reads as one professional, trustworthy tool instead of two
design worlds (dark gamer app + light landing).

- theme.ts: readTheme() defaults to light (was dark), matching the
  SSR + pre-paint default. Fixes the toggle direction for cookie-less
  users; the owner's lingering dark view was a stale theme=dark cookie.
- layout.tsx: retune the light token block to the QI palette
  (page #fcfcfd, ink #16181d, green #1e7f5c, amber #b45309; accent
  #4353c9 unchanged). Primary buttons become calm ink #16181d instead of
  indigo gradient (indigo reserved for links/active). theme-color meta
  now reflects the active theme. Dark token + .btn-primary rules left
  byte-identical so locked u-polish/system-states/push tests stay green;
  all QI overrides scoped under :root[data-theme=light].
- highlight.ts: add a GitHub-light-calibrated syntax palette scoped to
  the light theme so code blocks, diffs and READMEs stop rendering with
  the dark hljs colors on light pages.

No new test failures (2910 pass baseline preserved).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
ccanty labs committed on July 8, 2026Parent: 1a0ac2e
3 files changed+82162fd463be734ae7b31cdc5c697e90e691e72fa188
3 changed files+82−16
Modifiedsrc/lib/highlight.ts+35−0View fileUnifiedSplit
129129 .hljs-property { color: #79c0ff; }
130130 .hljs-subst { color: #e6edf3; }
131131 .hljs-punctuation { color: #8b949e; }
132
133 /* Quiet Intelligence (light) — GitHub-light-calibrated palette so code
134 blocks, diffs and READMEs read crisp on the #fcfcfd editorial surface
135 instead of the dark GitHub palette above. Higher specificity means
136 these win on the light theme; the dark rules above are untouched. */
137 :root[data-theme='light'] .hljs-keyword { color: #cf222e; }
138 :root[data-theme='light'] .hljs-built_in { color: #6639ba; }
139 :root[data-theme='light'] .hljs-type { color: #953800; }
140 :root[data-theme='light'] .hljs-literal { color: #0550ae; }
141 :root[data-theme='light'] .hljs-number { color: #0550ae; }
142 :root[data-theme='light'] .hljs-string { color: #0a3069; }
143 :root[data-theme='light'] .hljs-regexp { color: #0a3069; }
144 :root[data-theme='light'] .hljs-symbol { color: #0550ae; }
145 :root[data-theme='light'] .hljs-title { color: #6639ba; }
146 :root[data-theme='light'] .hljs-title.function_ { color: #6639ba; }
147 :root[data-theme='light'] .hljs-title.class_ { color: #953800; }
148 :root[data-theme='light'] .hljs-params { color: #1f2328; }
149 :root[data-theme='light'] .hljs-comment { color: #6e7781; font-style: italic; }
150 :root[data-theme='light'] .hljs-doctag { color: #6e7781; }
151 :root[data-theme='light'] .hljs-meta { color: #0550ae; }
152 :root[data-theme='light'] .hljs-attr { color: #0550ae; }
153 :root[data-theme='light'] .hljs-attribute { color: #0550ae; }
154 :root[data-theme='light'] .hljs-selector-tag { color: #cf222e; }
155 :root[data-theme='light'] .hljs-selector-class { color: #6639ba; }
156 :root[data-theme='light'] .hljs-selector-id { color: #0550ae; }
157 :root[data-theme='light'] .hljs-variable { color: #953800; }
158 :root[data-theme='light'] .hljs-template-variable { color: #953800; }
159 :root[data-theme='light'] .hljs-tag { color: #116329; }
160 :root[data-theme='light'] .hljs-name { color: #116329; }
161 :root[data-theme='light'] .hljs-section { color: #6639ba; font-weight: bold; }
162 :root[data-theme='light'] .hljs-addition { color: #116329; background: rgba(74,194,107,0.15); }
163 :root[data-theme='light'] .hljs-deletion { color: #82071e; background: rgba(255,129,130,0.15); }
164 :root[data-theme='light'] .hljs-property { color: #0550ae; }
165 :root[data-theme='light'] .hljs-subst { color: #1f2328; }
166 :root[data-theme='light'] .hljs-punctuation { color: #6e7781; }
132167`;
Modifiedsrc/routes/theme.ts+1−1View fileUnifiedSplit
1111
1212function readTheme(c: any): "dark" | "light" {
1313 const v = getCookie(c, "theme");
14 return v === "light" ? "light" : "dark";
14 return v === "dark" ? "dark" : "light";
1515}
1616
1717function writeTheme(c: any, value: "dark" | "light") {
Modifiedsrc/views/layout.tsx+46−15View fileUnifiedSplit
5757 <head>
5858 <meta charset="UTF-8" />
5959 <meta name="viewport" content="width=device-width, initial-scale=1.0" />
60 <meta name="theme-color" content="#0d1117" />
60 <meta name="theme-color" content={initialTheme === "dark" ? "#0d1117" : "#fcfcfd"} />
6161 {/* 2026 polish — load Inter + Inter Tight + JetBrains Mono for
6262 crisp modern typography. `preconnect` keeps the handshake
6363 cost off the critical path; `display=swap` means we never
12121212 }
12131213
12141214 :root[data-theme='light'] {
1215 --bg: #fbfbfc;
1215 /* Quiet Intelligence palette — calm editorial light, calibrated
1216 alongside Linear / Vercel / Stripe. page #fcfcfd, ink #16181d,
1217 single indigo accent #4353c9 reserved for links/active states;
1218 primary actions are ink, not indigo (see .btn-primary override). */
1219 --bg: #fcfcfd;
12161220 --bg-secondary: #ffffff;
12171221 --bg-tertiary: #f3f3f6;
12181222 --bg-elevated: #ffffff;
12211225 --bg-active: rgba(0,0,0,0.07);
12221226 --bg-inset: rgba(0,0,0,0.04);
12231227
1224 --border: rgba(15,16,28,0.08);
1225 --border-subtle: rgba(15,16,28,0.04);
1226 --border-strong: rgba(15,16,28,0.16);
1228 --border: rgba(22,24,29,0.08);
1229 --border-subtle: rgba(22,24,29,0.04);
1230 --border-strong: rgba(22,24,29,0.16);
12271231
1228 --text: #0e1020;
1229 --text-strong: #050617;
1230 --text-muted: #5a5b70;
1231 --text-faint: #8a8b9e;
1232 --text: #16181d;
1233 --text-strong: #0f1116;
1234 --text-muted: #565863;
1235 --text-faint: #868894;
12321236 --text-link: #4353c9;
12331237
12341238 --accent: #4353c9;
12391243 --border-focus: rgba(67,83,201,0.50);
12401244 --ring: 0 0 0 3px rgba(67,83,201,0.20);
12411245
1242 --green: #059669;
1243 --red: #dc2626;
1244 --yellow: #d97706;
1246 --green: #1e7f5c;
1247 --red: #c0362c;
1248 --yellow: #b45309;
12451249
1246 --elev-1: 0 1px 2px rgba(15,16,28,0.06), 0 0 0 1px var(--border);
1247 --elev-2: 0 8px 24px -10px rgba(15,16,28,0.10), 0 0 0 1px var(--border);
1248 --elev-3: 0 20px 48px -16px rgba(15,16,28,0.14), 0 0 0 1px var(--border-strong);
1250 --elev-1: 0 1px 2px rgba(22,24,29,0.06), 0 0 0 1px var(--border);
1251 --elev-2: 0 8px 24px -10px rgba(22,24,29,0.10), 0 0 0 1px var(--border);
1252 --elev-3: 0 20px 48px -16px rgba(22,24,29,0.14), 0 0 0 1px var(--border-strong);
12491253 }
12501254
12511255 /* Theme toggle — show the icon for the *opposite* theme so users see what they'll switch to. */
20662070 0 0 0 3px rgba(91,110,232,0.35);
20672071 }
20682072
2073 /* Quiet Intelligence (light) — primary actions are calm ink #16181d,
2074 not indigo. The indigo accent is reserved for links + active state,
2075 which is what reads as "trustworthy tool" vs "gamer SaaS". Scoped to
2076 the light theme only; the dark-theme gradient rules above are
2077 intentionally left byte-identical. */
2078 :root[data-theme='light'] .btn-primary {
2079 background: #16181d;
2080 color: #fff;
2081 text-shadow: none;
2082 box-shadow:
2083 inset 0 1px 0 rgba(255,255,255,0.08),
2084 0 1px 2px rgba(22,24,29,0.24),
2085 0 0 0 1px rgba(22,24,29,0.90);
2086 }
2087 :root[data-theme='light'] .btn-primary:hover {
2088 background: #2a2d35;
2089 box-shadow:
2090 inset 0 1px 0 rgba(255,255,255,0.10),
2091 0 6px 18px -6px rgba(22,24,29,0.30),
2092 0 0 0 1px rgba(22,24,29,0.90);
2093 }
2094 :root[data-theme='light'] .btn-primary:focus-visible {
2095 box-shadow:
2096 inset 0 1px 0 rgba(255,255,255,0.08),
2097 0 0 0 3px rgba(67,83,201,0.35);
2098 }
2099
20692100 .btn-danger {
20702101 background: transparent;
20712102 border-color: rgba(248,113,113,0.40);
20722103