基础设计系统架构——涵盖令牌层级、主题基础架构、令牌流水线及治理规范。适用于创建设计令牌、实现主题切换、配置 Style Dictionary 或建立多品牌主题。在设计令牌、主题提供者、Style Dictionary、令牌流水线、多品牌主题及 CSS 自定义属性架构时触发。
设计系统模式是一项面向实际任务的技能,主要用于可缩放设计系统的基础架构: 符号等级、主题基础设施、符号管道和治理模式;定义符号弧。
从功能定位来看,该技能强调把分散的操作要求整理成清晰、可复用的处理流程,使用户能够围绕既定目标快速准备输入、选择执行方式并获得结构化结果。实际使用前应先确认任务范围、数据来源、运行环境、必要权限和关键参数,再依据技能说明逐步执行;
若输入条件不完整,应先补齐信息或采用保守配置,避免因错误假设导致结果偏离需求。执行过程中需要关注工具调用是否成功、接口或依赖是否可用、输出格式是否符合预期,并对异常提示、缺失字段和边界情况进行处理;涉及批量任务时,还应保存进度,避免中断后重复操作。
面向可扩展设计系统的底层架构:令牌层级结构、主题化基础设施、令牌流水线及治理模式。
三层式令牌架构将原始值、语义含义与具体使用场景相互分离。
/* 第一层:基础令牌 — 原始值,绝不在组件中直接使用 */
:root {
--color-blue-500: #3b82f6;
--color-blue-600: #2563eb;
--color-gray-50: #fafafa;
--color-gray-900: #171717;
--space-1: 0.25rem;
--space-2: 0.5rem;
--space-4: 1rem;
--font-size-sm: 0.875rem;
--font-size-base: 1rem;
--radius-sm: 0.25rem;
--radius-md: 0.5rem;
}
/* 第二层:语义令牌 — 具备上下文含义,支持主题感知 */
:root {
--text-primary: var(--color-gray-900);
--text-secondary: var(--color-gray-600);
--surface-default: white;
--surface-elevated: var(--color-gray-50);
--border-default: var(--color-gray-200);
--interactive-primary: var(--color-blue-500);
--interactive-primary-hover: var(--color-blue-600);
}
/* 第三层:组件令牌 — 面向特定组件的使用,可选层 */
:root {
--button-bg: var(--interactive-primary);
--button-bg-hover: var(--interactive-primary-hover);
--button-text: white;
--button-radius: var(--radius-md);
--button-padding-x: var(--space-4);
--button-padding-y: var(--space-2);
}
语义令牌是最关键的一层——它使主题化成为可能。组件令牌为可选层,在复杂组件库中尤为有用。
核心能力:theme(用户选择)、resolvedTheme(实际生效的浅色/深色)、setTheme、系统偏好检测、localStorage 持久化、DOM 属性注入。
type Theme = "light" | "dark" | "system";
export function ThemeProvider({ children, defaultTheme = "system", storageKey = "theme",
attribute = "data-theme" }: { children: React.ReactNode; defaultTheme?: Theme;
storageKey?: string; attribute?: "class" | "data-theme" }) {
const [theme, setThemeState] = useState(() =>
typeof window === "undefined" ? defaultTheme
: (localStorage.getItem(storageKey) as Theme) || defaultTheme);
const [resolvedTheme, setResolvedTheme] = useState<"light" | "dark">("light");
const getSystem = useCallback(() =>
matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light" as const, []);
const apply = useCallback((r: "light" | "dark") => {
const root = document.documentElement;
attribute === "class"
? (root.classList.remove("light", "dark"), root.classList.add(r))
: root.setAttribute(attribute, r);
root.style.colorScheme = r;
setResolvedTheme(r);
}, [attribute]);
useEffect(() => { apply(theme === "system" ? getSystem() : theme); }, [theme, apply, getSystem]);
useEffect(() => { // 监听系统偏好变更
if (theme !== "system") return;
const mq = matchMedia("(prefers-color-scheme: dark)");
const handler = () => apply(getSystem());
mq.addEventListener("change", handler);
return () => mq.removeEventListener("change", handler);
}, [theme, apply, getSystem]);
const setTheme = useCallback((t: Theme) => {
localStorage.setItem(storageKey, t); setThemeState(t);
}, [storageKey]);
return
{children}
;
}
完整实现(含 toggleTheme、disableTransitionOnChange 及测试模式)详见 references/theming-architecture.md。
置于 中的内联脚本会在首次绘制前执行:
const themeScript = `(function(){
var t=localStorage.getItem('theme')||'system';
var d=t==='dark'||(t==='system'&&matchMedia('(prefers-color-scheme:dark)').matches);
document.documentElement.setAttribute('data-theme',d?'dark':'light');
document.documentElement.style.colorScheme=d?'dark':'light';
})()`;
// 在 layout.tsx 中
{children}
在语义令牌之上叠加品牌专属令牌,适用于白标产品:
[data-brand="corporate"] {
--brand-primary: #0066cc;
--brand-primary-hover: #0052a3;
--brand-font-heading: "Helvetica Neue", sans-serif;
--brand-radius: 0.25rem;
}
[data-brand="startup"] {
--brand-primary: #7c3aed;
--brand-primary-hover: #6d28d9;
--brand-font-heading: "Poppins", sans-serif;
--brand-radius: 1rem;
}
/* 将品牌令牌映射至语义令牌 */
:root {
--interactive-primary: var(--brand-primary);
--interactive-primary-hover: var(--brand-primary-hover);
}
基于单一 JSON 源生成多平台令牌:
// style-dictionary.config.js — 生成 CSS、iOS Swift 和 Android XML
module.exports = {
source: ["tokens/**/*.json"],
platforms: {
css: {
transformGroup: "css", buildPath: "dist/css/",
files: [{ destination: "variables.css", format: "css/variables",
options: { outputReferences: true } }],
},
ios: {
transformGroup: "ios-swift", buildPath: "dist/ios/",
files: [{ destination: "DesignTokens.swift", format: "ios-swift/class.swift",
className: "DesignTokens" }],
},
android: {
transformGroup: "android", buildPath: "dist/android/",
files: [{ destination: "colors.xml", format: "android/colors",
filter: { attributes: { category: "color" } } }],
},
},
};
详见 references/design-tokens.md,其中包含令牌分类定义、自定义转换逻辑及各平台输出示例。
@media (prefers-reduced-motion: reduce) {
:root {
--duration-fast: 0ms;
--duration-normal: 0ms;
--duration-slow: 0ms;
}
}
@media (prefers-contrast: high) {
:root {
--text-primary: #000000;
--surface-default: #ffffff;
--border-default: #000000;
--interactive-primary: #0000ee;
}
}
@media (forced-colors: active) {
.button { border: 2px solid currentColor; }
.card { border: 1px solid CanvasText; }
}
格式:[类别]-[属性]-[变体]-[状态](例如:color-border-input-focus)
text-primary,而非 textPrimarydanger,而非 red-hover、-focus、-active、-disabledspacing-4、font-size-lg变更管理流程:提出提案 → 评审(设计 + 工程)→ 测试(覆盖全部平台与主题)→ 弃用(提供迁移路径)→ 移除(弃用期结束后)
{
"color.primary": {
"value": "{color.primitive.blue.500}",
"deprecated": true,
"deprecatedMessage": "Use semantic.accent.default instead",
"replacedBy": "semantic.accent.default"
}
}
相关专题
热门下载
相关下载
精品课程
共86课时 | 27.4万人学习
共18课时 | 6.1万人学习
共31课时 | 5万人学习