设计实施的九大原则
已发表: 2022-03-10起初,我很困惑。 我刚刚花了几个小时告诉他们“做正确的事”所需的一切。 但在思考之后,我意识到这个问题的根源在于更深层次的需要,即指导和评估通常是一组主观选择——有时是由很多不同的人在不同时间做出的选择。 最终结果是一致的命名约定和生活风格指南之类的东西,但这些“最佳实践”植根于一组并不总是明确的更深层次的价值观。 例如,如果没有更广泛地了解模块化,诸如“尽量减少与另一个类协作的类的数量”之类的具体建议就没有多大帮助。
我意识到,为了真正了解我们的工作是否好,我们需要更高层次的原则,可以作为实现设计的衡量标准。 我们需要从特定语言(如 CSS)或自以为是的编写方式中删除的东西。 就像设计的普遍原则或尼尔森的可用性启发式一样,我们需要一些东西来指导我们实施设计的方式,而不告诉我们具体如何去做。 为了弥合这一差距,我编制了九个设计实施原则。
构建渐进式单页应用程序
通过仅使用几个 CSS 技巧、不到 0.5 KB 的 JavaScript 以及重要的一些静态 HTML,Heydon Pickering 为逐步增强的单页应用程序引入了一个实验性解决方案。 阅读相关文章 →
这不是一个清单。 相反,它是一套旨在保持潜在价值的广泛指导方针。 它可以用作从事实施工作的人的指南,也可以用作评估现有项目的工具。 因此,无论您是在审查代码、审核 CSS 还是面试团队中某个职位的候选人,这些原则都应该提供一种超越特定技术的结构,并导致实现设计的通用方法。
- 结构化文档按语义和逻辑编写,有或没有样式。
- 高效使用最少的标记和资产来实现设计。
- 通用值的标准化规则被自由存储和使用。
- 抽象的基础元素从特定的上下文中分离出来,形成一个核心框架。
- 模块化公共元素在逻辑上被分解为可重用的部分。
- 可通过可选参数对基本元素进行可配置的自定义。
- 可扩展代码很容易扩展,并且可以预见未来的增强。
- 记录所有元素都被描述为其他人使用和扩展。
- 准确最终输出是对预期设计的适当表示。
为了更容易理解并了解每个原则如何应用于项目,我们将使用我的一个项目中的设计模型作为本文的基础。 这是一个特殊的登陆页面,用于宣传现有电子商务网站上的日常交易。 虽然某些样式将从现有网站继承,但重要的是要注意这些元素中的大多数都是全新的。 我们的目标是利用这些原则将这张静态图片转换成 HTML 和 CSS。

1.结构化
文档是按语义和逻辑编写的,有或没有样式。
这里的原则是,即使没有表现样式 (CSS),我们文档的内容 (HTML) 也有意义。 当然,这意味着我们使用了正确排序的标题级别和无序列表——但也使用了有意义的容器,例如<header>
和<article>
。 我们不应该跳过使用诸如 ARIA 标签、 alt
属性和任何其他我们可能需要的可访问性的东西。
这可能看起来没什么大不了的,但是使用锚标签还是按钮确实很重要——即使它们在视觉上是相同的——因为它们传达不同的含义并提供不同的交互。 语义标记将这种含义传达给搜索引擎和辅助技术,甚至使我们在其他设备上重新调整工作变得更容易。 它使我们的项目更具前瞻性。
创建一个结构良好的文档意味着学习编写语义 HTML,熟悉 W3C 标准,甚至其他专家的一些最佳实践,并花时间让您的代码易于访问。 最简单的测试是在没有样式的浏览器中查看您的 HTML:
- 没有CSS可以使用吗?
- 它是否仍然具有可见的层次结构?
- 原始 HTML 本身是否传达了含义?
要确保结构化文档,您可以做的最好的事情之一就是从 HTML 开始。 在考虑视觉样式之前,请写出纯 HTML 以了解文档的结构以及每个部分的含义。 避免使用div
并考虑合适的包装标签是什么。 仅此基本步骤将大大有助于您创建适当的结构。
<section> <header> <h2>Daily Deals</h2> <strong>Sort</strong> <span class="caret"></span> <ul> <li><a href="#">by ending time</a></li> <li><a href="#">by price</a></li> <li><a href="#">by popularity</a></li> </ul> <hr /> </header> <ul> <li aria-labelledby="prod7364536"> <a href="#"> <img src="prod7364536.jpg" alt="12 Night Therapy Euro Box Top Spring" /> <small>Ends in 9:42:57</small> <h3 id="prod7364536">12" Night Therapy Euro Box Top Spring</h3> <strong>$199.99</strong> <small>List $299</small> <span class="callout">10 Left</span> </a> </li> </ul> </section>
仅从 HTML 开始并仔细考虑每个元素的含义,可以生成更加结构化的文档。 在上面,您可以看到我在不使用单个div
的情况下创建了整个标记。
2.高效
使用最少的标记和资产来实现设计。
我们必须仔细考虑我们的代码,以确保它简洁且不包含不必要的标记或样式。 我div
使用特定于框架的类名来查看在div
中包含div
的代码,以实现与右侧对齐的块级元素。 通常,过度使用 HTML 是不了解 CSS 或底层框架的结果。

div
案例。 想想标记需要是什么,而不是框架可以做什么来实现所需的设计。 (查看大图)除了标记和 CSS 之外,我们可能还需要其他外部资源,例如图标、网络字体和图像。 关于实现这些资产的最佳方式,有很多很棒的方法和意见,从自定义图标字体到 base64 嵌入到外部 SVG。 每个项目都是不同的,但如果你有一个 500 像素的 PNG 用于按钮上的单个图标,那么你很可能不是有意提高效率。

在评估项目的效率时,有两个重要问题要问:
- 我可以用更少的代码完成同样的事情吗?
- 优化资产以实现最小开销的最佳方法是什么?
实施效率也与以下关于标准化和模块化的原则重叠,因为提高效率的一种方法是使用设定的标准实施设计并使其可重用。 为常见的盒子阴影创建一个 mixin 是有效的,同时也创建了一个模块化的标准。
3.标准化
通用值的规则被自由地存储和使用。
为网站或应用程序创建标准通常是关于建立规则来管理诸如每个标题级别的大小、常见的装订线宽度和每个按钮类型的样式等。 在纯 CSS 中,您必须在外部样式指南中维护这些规则并记住正确应用它们,但最好使用 LESS 或 Sass 等预处理器,以便您可以将它们存储在变量和 mixin 中。 这里的主要内容是重视标准而不是像素完美的设计。
所以,当我得到一个装订线宽度为 22 像素的设计模型,而不是我们在其他地方使用的 15 像素时,我会假设这样的精度不值得,而是使用标准的 15 像素装订线. 更进一步,元素之间的所有间距都将使用这个标准的倍数。 额外的宽空间将是$gutter-width * 2
(等于 30 像素),而不是硬编码的值。 通过这种方式,整个应用程序具有一致、一致的感觉。
.product-cards { li { display: inline-block; padding: @gutter-width/4; color: @text-color; text-decoration: none; background-color: @color-white; .border; margin-bottom: @gutter-width/2; margin-right: @gutter-width/2; } } .product-status { font-size: @font-size-small; color: @grey-darker; font-weight: @font-weight-bold; margin-bottom: @gutter-width/4; }
因为我们使用从 LESS 变量或 mixin 派生的标准化值,所以我们的 CSS 没有任何自己的数值。 一切都继承自一个中心化的价值。
要检查标准化,请查看 CSS 并查找任何硬编码单位:像素、十六进制颜色、ems 或几乎任何数值。
- 这些单位是否应该使用现有的标准值或变量?
- 是否重复使用该单元以使其受益于新变量? 也许您已经意识到这是您第二次应用部分不透明的背景,并且两次都需要相同的不透明度。
- 单位可以从现有变量的计算中得出吗? 这对于颜色的变化很有用——例如,使用标准颜色并对其执行计算以使颜色变暗 10%,而不是对生成的 HEX 值进行硬编码。
我尽可能多地使用标准值并创建新值仅作为例外。 如果您发现自己在这里调整了 5 个像素,那里调整了 1 个像素,那么您的标准可能会受到影响。

根据我的经验,大多数预处理 CSS 应该使用集中变量和 mixin,并且您应该在单个组件中几乎看不到数字、像素或 HEX 值。 有时,添加几个像素来调整单个组件的位置可能是合适的——但即使是这种情况也应该很少见,并且会导致您仔细检查您的标准。
4.抽象
基本元素与特定上下文分离并形成核心框架。
我最初将这一原则称为“框架化”,因为除了创建一个您现在正在从事的特定项目之外,您还应该致力于一个可以在原始环境之外使用的设计系统。 这个原则是关于识别需要在整个项目或未来项目中使用的更大的通用元素。 这从排版和表单字段输入开始,一直到不同的导航设计。 可以这样想:如果你的 CSS 将作为一个框架开源,比如 Bootstrap 或 Foundation,你将如何分离设计元素? 你会如何以不同的方式设计它们? 即使您已经在使用 Bootstrap,您的项目也有可能具有 Bootstrap 不提供的基本元素,并且这些元素也需要在项目的设计系统中可用。

这里的关键是用更通用的术语来考虑每个元素,而不是在项目的特定上下文中。 当您查看特定元素时,将其分解为多个部分,并为每个部分赋予该元素将具有的整体样式,而不管您现在使用的具体实现如何。 最常见的元素是排版(标题样式、行高、大小和字体)、表单元素和按钮。 但是其他元素也应该是“框架化的”,例如标注标签或任何可能为我们的每日优惠设计但在其他地方也有用的特殊价格格式。
在检查您的项目的抽象时,请询问:
- 如果我知道它将在具有不同需求的另一个上下文中重复使用,我将如何构建此元素?
- 我怎样才能把它分解成对整个应用程序有价值的部分?
考虑每个元素的更一般的实现是关键。 这些部分应该存储为完全独立且独立的类,或者更好的是,作为可以使用最终 CSS 编译的单独的 LESS 或 Sass 文件。
这个原则在 web 组件或模块应用程序架构中更容易,因为小部件可能已经以这种方式分离。 但它对我们的思维有着与其他任何事物一样多的影响。 我们应该始终将我们的工作从它所衍生的上下文中抽象出来,以确保我们正在创造一些灵活的东西。
5.模块化
公共元素在逻辑上被分解为可重用的部分。
与“抽象”原则重叠,使我们的设计模块化是建立易于使用和维护的具体设计系统的重要部分。 两者之间有一条细线,但原则上的区别很重要。 细微差别在于,虽然全局基础元素需要从其上下文中抽象出来,但上下文中的各个项目也需要可重用并保持独立的样式。 模块可能是我们的应用程序独有的,而不是我们需要在整个框架中可用的东西——但它们仍然需要可重用,这样我们就不会在每次使用该模块时都重复代码。
例如,如果您正在为 Daily Deals 登录页面实现上一个示例中的产品卡片列表,而不是使用类名(如daily-deal-product
)来制作特定于 Daily Deals 的 HTML 和 CSS,而是创建一个更通用的product-cards
类包含所有抽象类,但也可以在 Daily Deals 页面之外重用。 这可能会导致您的组件在三个不同的位置获取其样式:
- 基础 CSS 。 这是底层框架,包括排版、装订线、颜色等的默认值。
- CSS 组件。 这些是设计的抽象部分,构成整体设计的构建块,但可以在任何情况下使用。
- 父组件。 这些是包含特定于 Daily Deals 的样式或自定义的 Daily
daily-deal
组件(和任何子组件)。 对于许多人来说,这将是一个实际的 JavaScript Web 组件,但它可能只是一个包含呈现整个设计所需的 HTML 的父模板。

当然,您可能会走得太远,因此您必须进行判断。 但在大多数情况下,您创建的所有内容都应尽可能可重复使用,而不会使长期维护过于复杂。
6.可配置
可通过可选参数对基本元素进行自定义。
构建设计系统的一部分是考虑项目现在或将来可能需要的选项。 仅按规定实施设计是不够的。 我们还必须考虑哪些部分可能是可选的,通过不同的配置打开或关闭。
例如,我们设计中的标注标志仅显示三种颜色变化,均指向左侧。 我们将创建一个默认类并添加其他类名作为可选参数,而不是创建三个单独的类。 除此之外,我认为有人可能会出现并希望将旗帜指向不同的背景。 事实上,为这些标注使用我们的默认品牌颜色也很有用,即使设计并没有特别要求它。 我们会专门编写 CSS 来解决这个问题,包括 left 和 right 作为选项。

当您考虑特定的设计元素时,请考虑可能有价值的选项。 理解这一点的一个重要部分是批判性地思考可能重用该元素的其他上下文。
- 哪些部分可以通过外部变量进行配置、可选或启用?
- 能够改变元素的颜色或位置是否有价值?
- 提供小、中、大尺寸会有帮助吗?
使用 BEM、OOCSS 或 SMACSS 等方法来组织 CSS 并建立命名约定可以帮助您做出这些决定。 处理这些用例是构建可配置设计系统的重要组成部分。
7. 可扩展
该代码很容易扩展,并预计将来会有所改进。
本着与“可配置”原则相同的精神,我们的实施也必须期待未来的变化。 虽然构建可选参数很有用,但我们无法预测项目需要的所有内容。 因此,重要的是还要考虑我们正在编写的代码将如何影响未来的变化,并有意识地组织它以便于增强。
构建可扩展的 CSS 通常需要我使用 LESS 和 Sass 的更高级特性来编写 mixins 和函数。 因为除了颜色之外我们所有的调用标志都是相同的,我们可以创建一个 LESS mixin,它将为每个调用生成 CSS,而无需为每个变体复制代码。 该代码旨在扩展并且易于在一处更新。
@angle: 170; .callout { &.qty-left { .callout-generator(@color-deals, @color-white, @angle); } &.qty-sold { .callout-generator(@color-white, @color-deals, @angle, 2px solid @color-deals); } &.qty-out { .callout-generator(@color-grey, darken(@color-grey, 10%), @angle); } }
为了使标注可扩展,我们将创建一个名为.callout-generator
的 LESS mixin,它接受背景颜色、文本颜色、点的角度和边框等值。

.review-flag { .callout-generator(@color-brand, @color-white, 75); }
将来,当一个新需求需要类似的设计模式时,生成新样式将很容易。

要创建可扩展的设计系统,请学会预测项目中常见的更改,并运用这种理解来确保您编写的代码已为这些更改做好准备。 常见的解决方案包括使用变量和 mixin,以及将值存储在数组中并循环遍历它们。 问你自己:
- 这些元素的哪些部分可能会发生变化?
- 您如何编写代码以便将来轻松进行这些更改?
8. 记录在案
描述了所有元素以供其他人使用和扩展。
记录设计被低估了,并且通常是项目中第一个被削减的角落。 但是,创建工作记录不仅仅是帮助下一个人弄清楚你的意图——它实际上是让所有利益相关者参与整个设计系统的好方法,这样你就不会每次都重新发明轮子. 您的文档应该是团队中每个人的参考,从开发人员到高管。
记录您的工作的最佳方式是创建一个实时风格指南,它是直接从您的代码中的注释生成的。 我们使用一种称为样式指南驱动开发的方法,以及 DocumentCSS,它为自己带来了红利。 但是,即使您的项目没有实时风格指南,手动创建一个 HTML 甚至是打印格式的 PDF 也可以。 要记住的原则是我们所做的一切都必须记录在案。
要记录您的设计系统,请编写说明以帮助其他人了解设计是如何实现的,以及他们需要做什么才能自己重新创建它。 此信息可能包括元素背后的特定设计思想、代码示例或实际元素的演示。
- 我将如何告诉其他人如何使用我的代码?
- 如果我是一名新团队成员,我会解释什么以确保他们知道如何使用它?
- 我可以展示每个小部件的哪些变体来展示它的所有使用方式?

9.准确
最终输出是预期设计的适当表示。
最后,我们不能忘记,我们创造的东西必须看起来和它想要反映的原始设计理念一样好。 如果一个设计系统不能满足他们对视觉吸引力的期望,那么没有人会欣赏它。 重要的是要强调,结果只能是设计的适当表示,不会是像素完美的。 我不喜欢“像素完美”这个词,因为建议一个实现必须与模型完全一样,像素对像素,就是忘记任何约束并贬低标准化(不要介意每个浏览器都会渲染一点 CSS不同)。 使准确性复杂化的事实是,响应式应用程序的静态设计很少考虑到所有可能的设备尺寸。 关键是需要一定程度的灵活性。
您必须决定您的项目需要多少适当的表示,但要确保它符合与您一起工作的人的期望。 在我们的项目中,我将与客户一起审查像素完美的主要偏差,以确保我们在同一页面上。 “这些设计显示了带有边框的默认蓝色按钮样式,但我们的标准按钮颜色略有不同并且没有边框,因此我们选择了它。” 设定期望是这里最重要的一步。

思维系统
这九项原则的目标是为在 HTML 和 CSS 中实现设计提供指南。 它不是一套规则或规定性建议,而是一种思考你的工作的方式,以便你可以优化在伟大的设计和伟大的代码之间取得最佳平衡。 在应用这些原则时,给自己一定的灵活性是很重要的。 你不可能每次都做到完美。 他们是理想。 总是有其他干扰、原则和优先事项阻碍我们做好工作。 尽管如此,原则应该是始终努力的东西,不断地检查自己,并在您将设计从绘图板带到最终的体验媒介时积极追求。 我希望他们能帮助您创造更好的产品并构建可以持续多年的设计系统。
我很想听听您在实施设计方面的经验。 发表评论并分享您可能在自己的工作中使用的任何建议或其他原则。