设计系统搭建构建一致的 UI 语言引言作为一名把代码当散文写的 UI 匠人我始终认为优秀的设计不是偶然的而是系统的。设计系统Design System就是这样一种将设计标准化、组件化的方法论。它不仅可以提高设计和开发效率还能确保产品在不同平台和场景下的一致性。今天我想和你分享如何搭建一个完整的设计系统。一、设计系统的核心概念1. 什么是设计系统设计系统是一套包含设计原则、组件库、样式指南和最佳实践的完整体系它定义了产品的视觉语言和交互规范。2. 设计系统的组成部分设计原则指导设计决策的核心价值观设计令牌Design Tokens可重用的设计变量组件库标准化的 UI 组件样式指南设计规范和最佳实践文档使用指南和示例二、设计令牌Design Tokens1. 色彩系统:root { /* 主色调 */ --color-primary: #3498db; --color-primary-light: #5dade2; --color-primary-dark: #2980b9; /* 辅助色 */ --color-secondary: #e74c3c; --color-accent: #f39c12; --color-success: #27ae60; --color-warning: #f1c40f; --color-error: #e74c3c; --color-info: #3498db; /* 中性色 */ --color-white: #ffffff; --color-gray-100: #f8f9fa; --color-gray-200: #e9ecef; --color-gray-300: #dee2e6; --color-gray-400: #ced4da; --color-gray-500: #adb5bd; --color-gray-600: #6c757d; --color-gray-700: #495057; --color-gray-800: #343a40; --color-gray-900: #212529; --color-black: #000000; }2. 排版系统:root { /* 字体家族 */ --font-family-sans: Inter, -apple-system, BlinkMacSystemFont, Segoe UI, Roboto, sans-serif; --font-family-mono: Fira Code, Consolas, Monaco, monospace; --font-family-serif: Georgia, Times New Roman, serif; /* 字体大小 */ --font-size-xs: 0.75rem; /* 12px */ --font-size-sm: 0.875rem; /* 14px */ --font-size-base: 1rem; /* 16px */ --font-size-lg: 1.125rem; /* 18px */ --font-size-xl: 1.25rem; /* 20px */ --font-size-2xl: 1.5rem; /* 24px */ --font-size-3xl: 1.875rem; /* 30px */ --font-size-4xl: 2.25rem; /* 36px */ --font-size-5xl: 3rem; /* 48px */ /* 字重 */ --font-weight-light: 300; --font-weight-normal: 400; --font-weight-medium: 500; --font-weight-semibold: 600; --font-weight-bold: 700; /* 行高 */ --line-height-tight: 1.25; --line-height-normal: 1.5; --line-height-relaxed: 1.75; }3. 间距系统:root { /* 间距单位 */ --spacing-0: 0; --spacing-1: 0.25rem; /* 4px */ --spacing-2: 0.5rem; /* 8px */ --spacing-3: 0.75rem; /* 12px */ --spacing-4: 1rem; /* 16px */ --spacing-5: 1.25rem; /* 20px */ --spacing-6: 1.5rem; /* 24px */ --spacing-8: 2rem; /* 32px */ --spacing-10: 2.5rem; /* 40px */ --spacing-12: 3rem; /* 48px */ --spacing-16: 4rem; /* 64px */ --spacing-20: 5rem; /* 80px */ --spacing-24: 6rem; /* 96px */ --spacing-32: 8rem; /* 128px */ }4. 圆角和阴影:root { /* 圆角 */ --radius-none: 0; --radius-sm: 0.125rem; /* 2px */ --radius-base: 0.25rem; /* 4px */ --radius-md: 0.375rem; /* 6px */ --radius-lg: 0.5rem; /* 8px */ --radius-xl: 0.75rem; /* 12px */ --radius-2xl: 1rem; /* 16px */ --radius-3xl: 1.5rem; /* 24px */ --radius-full: 9999px; /* 阴影 */ --shadow-sm: 0 1px 2px 0 rgba(0, 0, 0, 0.05); --shadow-base: 0 1px 3px 0 rgba(0, 0, 0, 0.1), 0 1px 2px 0 rgba(0, 0, 0, 0.06); --shadow-md: 0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06); --shadow-lg: 0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05); --shadow-xl: 0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04); --shadow-2xl: 0 25px 50px -12px rgba(0, 0, 0, 0.25); }三、组件库的构建1. 基础组件按钮组件button classbtn btn-primaryPrimary Button/button button classbtn btn-secondarySecondary Button/button button classbtn btn-outlineOutline Button/button button classbtn btn-linkLink Button/button.btn { display: inline-flex; align-items: center; justify-content: center; padding: var(--spacing-3) var(--spacing-6); font-family: var(--font-family-sans); font-size: var(--font-size-base); font-weight: var(--font-weight-medium); line-height: 1; border-radius: var(--radius-base); transition: all 0.2s ease; cursor: pointer; border: none; outline: none; text-decoration: none; } .btn:hover { transform: translateY(-1px); box-shadow: var(--shadow-md); } .btn:active { transform: translateY(0); box-shadow: var(--shadow-sm); } .btn-primary { background-color: var(--color-primary); color: var(--color-white); } .btn-primary:hover { background-color: var(--color-primary-dark); } .btn-secondary { background-color: var(--color-gray-200); color: var(--color-gray-800); } .btn-secondary:hover { background-color: var(--color-gray-300); } .btn-outline { background-color: transparent; color: var(--color-primary); border: 1px solid var(--color-primary); } .btn-outline:hover { background-color: var(--color-primary); color: var(--color-white); } .btn-link { background-color: transparent; color: var(--color-primary); padding: 0; } .btn-link:hover { text-decoration: underline; }输入框组件input typetext classinput placeholderEnter text input typeemail classinput placeholderEnter email input typepassword classinput placeholderEnter password.input { width: 100%; padding: var(--spacing-3) var(--spacing-4); font-family: var(--font-family-sans); font-size: var(--font-size-base); line-height: 1.5; color: var(--color-gray-900); background-color: var(--color-white); border: 1px solid var(--color-gray-300); border-radius: var(--radius-base); transition: all 0.2s ease; outline: none; } .input:focus { border-color: var(--color-primary); box-shadow: 0 0 0 3px rgba(52, 152, 219, 0.1); } .input::placeholder { color: var(--color-gray-500); } .input:disabled { background-color: var(--color-gray-100); border-color: var(--color-gray-200); cursor: not-allowed; }2. 复合组件卡片组件div classcard div classcard-header h3 classcard-titleCard Title/h3 /div div classcard-body p classcard-textThis is a card component with some text content./p /div div classcard-footer button classbtn btn-primaryAction/button /div /div.card { background-color: var(--color-white); border-radius: var(--radius-lg); box-shadow: var(--shadow-base); overflow: hidden; transition: all 0.3s ease; } .card:hover { box-shadow: var(--shadow-lg); transform: translateY(-2px); } .card-header { padding: var(--spacing-4); border-bottom: 1px solid var(--color-gray-200); } .card-title { font-size: var(--font-size-lg); font-weight: var(--font-weight-semibold); color: var(--color-gray-900); margin: 0; } .card-body { padding: var(--spacing-4); } .card-text { color: var(--color-gray-700); margin: 0; } .card-footer { padding: var(--spacing-4); border-top: 1px solid var(--color-gray-200); display: flex; justify-content: flex-end; gap: var(--spacing-3); }导航组件nav classnav div classnav-brand a href# classnav-logoLogo/a /div div classnav-links a href# classnav-link activeHome/a a href# classnav-linkAbout/a a href# classnav-linkServices/a a href# classnav-linkContact/a /div /nav.nav { display: flex; align-items: center; justify-content: space-between; padding: var(--spacing-4) var(--spacing-6); background-color: var(--color-white); box-shadow: var(--shadow-sm); } .nav-brand { display: flex; align-items: center; } .nav-logo { font-size: var(--font-size-xl); font-weight: var(--font-weight-bold); color: var(--color-primary); text-decoration: none; } .nav-links { display: flex; gap: var(--spacing-6); } .nav-link { font-size: var(--font-size-base); font-weight: var(--font-weight-medium); color: var(--color-gray-700); text-decoration: none; transition: all 0.2s ease; position: relative; } .nav-link:hover { color: var(--color-primary); } .nav-link.active { color: var(--color-primary); } .nav-link.active::after { content: ; position: absolute; bottom: -2px; left: 0; width: 100%; height: 2px; background-color: var(--color-primary); border-radius: 1px; }四、设计系统的实现工具1. 样式预处理器Sass/Less增强 CSS 功能支持变量、嵌套、混合等PostCSS使用插件扩展 CSS 功能CSS-in-JS在 JavaScript 中编写 CSS2. 组件库工具React使用 Storybook 构建组件库Vue使用 VuePress 或 Storybook 构建组件库Flutter使用 Flutter Widgets 构建组件库3. 设计工具Figma协作设计工具支持设计系统管理Sketch矢量设计工具Adobe XD设计和原型工具五、设计系统的维护与迭代1. 版本管理使用语义化版本控制Semantic Versioning维护变更日志Changelog提供迁移指南2. 文档维护保持文档与代码同步提供详细的使用示例定期更新文档3. 社区反馈建立反馈机制收集用户意见持续改进设计系统六、实战经验分享1. 从原子设计开始我在搭建设计系统时采用了原子设计Atomic Design方法原子基础元素按钮、输入框、标签等分子由原子组成的简单组件表单、卡片等有机体由分子组成的复杂组件导航栏、页脚等模板页面布局结构页面最终的页面实例2. 设计与开发的协作设计系统需要设计和开发的紧密协作设计师负责定义设计令牌和组件规范开发者负责实现组件和维护代码定期同步会议确保设计和开发的一致性3. 性能优化设计系统的性能优化按需加载组件优化 CSS 体积使用 CSS 变量减少重复代码避免过度使用复杂的 CSS 选择器七、设计系统的未来趋势1. AI 辅助设计AI 技术正在改变设计系统的构建智能生成设计令牌自动生成组件代码基于用户反馈优化设计2. 跨平台设计系统跨平台设计系统成为趋势统一 Web、移动应用和桌面应用的设计使用 Flutter 等跨平台框架实现一致性共享设计令牌和组件逻辑3. 可访问性可访问性成为设计系统的重要组成部分符合 WCAG 标准支持屏幕阅读器提供键盘导航确保色彩对比度八、总结设计系统是构建一致、高效 UI 的基础。通过标准化设计令牌、组件库和样式指南我们可以提高设计和开发效率确保产品的一致性和可维护性。作为一名 UI 匠人我相信设计系统不仅仅是工具更是一种思维方式。它要求我们将设计视为一个系统工程注重细节和一致性。通过搭建和维护设计系统我们可以创造出更加专业、用户友好的产品。记住像素不能偏差 1px设计要有系统性这就是我们作为 UI 匠人的追求。希望这篇文章能为你带来一些启发让你开始构建或优化自己的设计系统。作者leopold_man把代码当散文写的 UI 匠人CSS 在我眼里是流动的韵律动画是页面呼吸的节拍把像素级还原当信仰口头禅「CSS 是流动的韵律JS 是叙事的节奏。」「像素不能偏差 1px。」