feat: 外观支持自定义 CSS/JS,并升级发帖工作台与积分存量看板

后台可注入全站 CSS/JS(SSR 生效,CSS 可热换);发帖/编辑改为锁一屏工作室;经济看板增加存量健康度;主题令牌与弹层误关一并收紧。

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-09-18 04:16:32 +08:00
parent fa713bfc3f
commit 5f7193042f
41 changed files with 2297 additions and 873 deletions

View File

@@ -83,6 +83,8 @@ export default async function RootLayout({
const settings = await getPublicSettingsCached();
const accent = settings.accent;
const accentCSS = accentStyleCSS(accent || "");
const customCSS = (settings.custom_css || "").trim();
const customJS = (settings.custom_js || "").trim();
const motionCfg = motionConfigFromSettings(settings);
const motionHtmlClass = [
!motionCfg.ui_animations ? "j13-reduce-motion" : "",
@@ -117,6 +119,13 @@ export default async function RootLayout({
dangerouslySetInnerHTML={{ __html: accentCSS }}
/>
) : null}
{customCSS ? (
<style
id="j13-custom-css"
data-custom-css-source="ssr"
dangerouslySetInnerHTML={{ __html: customCSS }}
/>
) : null}
<a href="#main" className="skip-link">
跳到主要内容
</a>
@@ -147,9 +156,12 @@ export default async function RootLayout({
<Toaster />
<TipHost />
<AccountGuard />
<ThemeSync initialAccent={accent || ""} />
<ThemeSync initialAccent={accent || ""} initialCustomCSS={customCSS} />
<VisitBeacon />
<RealtimeProvider userId={user ? user.id : null} />
{customJS ? (
<script id="j13-custom-js" dangerouslySetInnerHTML={{ __html: customJS }} />
) : null}
</body>
</html>
);