什么构成了语义化的类名?

Avatar of Chris Coyier
Chris Coyier 发布

DigitalOcean 为您旅程的每个阶段提供云产品。 立即开始使用 $200 免费信用额度!

HTML 中的语义化始终是热门话题。 有些人始终追求它。 有些人批评对它的教条式坚持。 有些人不知道它到底是什么。

我会将语义化描述为与 HTML 相关的标签、类、ID 和属性,它们 **描述但不指定** 它们所包含的内容。 让我们从一个我们可能都同意的例子开始。

不好的语义化

<div class="article">
  <div class="article_title">Smurf Movie Kinda Sucks</div>
  <div class="the_content">Not surprisingly, this weeks release of
     <div class="darkbold">The Smurfs</div> kinda sucks.</div>
</div>

好的语义化

<article>
  <h1>Smurf Movie Kinda Sucks</h1>
  <p>Not surprisingly, this weeks release of
     <b>The Smurfs</b> kinda sucks.</p>
</article>

无论您是否认为 HTML5 已准备好使用,我认为您会同意,当您需要一个 HTML 元素来表示文章时,<article> 标签比具有类名的通用 <div> 更好。 文章的标题变为标题,内容变为段落,粗体但非强调的标题变为粗体标签。

但并非所有内容都能如此干净地映射到 HTML 标签。 让我们看一些类名,我会提供我对它是否语义化的看法。

<div class="column_1"></div>

**非语义化。** 这是一个经典的例子。 世界上所有 CSS 网格框架都使用某种类名来声明网格。 无论是“yui-b”、“grid-4”还是“spanHalf”,所有这些都更接近于指定而不是描述它们的内容。 所以,虽然我坚持认为这些是非语义化类名,但我认为它们在基于浮动的网格系统布局中基本上是不可避免的。

<div class="footer"></div>

**语义化。** 虽然页脚是一个抽象的概念,但在网页设计中已经有了自己的含义。 它是网站的底部,通常包含重复的导航、版权、作者信息等。 此类名声明了所有这些内容的组,而不会描述它。

如果您已经转向 HTML5,<footer> 元素将是更好的选择。 这也适用于所有 HTML5 元素。(标题应该是 <header>,侧边栏应该是 <aside> 等等)如果您还没有使用 HTML5(您最好有一个非常令人信服的理由),我认为等效的类名是可以接受的。

<div class="largeText"></div>

**非语义化。** 这是在指定。 为什么文本应该更大? 为了从其他较小的文本中脱颖而出? “standOut” 或 “callout_text” 在这里可能更好,就像在理论上的重新设计未来中,您可能希望选择不同的样式来突出显示该文本,而与文本的大小无关,并且您不会被尴尬的类名困扰。

<div class="priority-2"></div>

**语义化。** 我与来自 MailChimp 的一些人 (Jason BeairdAarron Walter) 讨论过这个问题,这就是他们在应用程序中声明按钮的相对重要性级别的方式(尽管类名更像是“p1” .. “p5”)。 优先级较高的按钮可能具有更明亮的颜色或更大,而优先级较低的按钮可能与内容更融合。 通过不具体说明这些样式是什么,并抽象到优先级级别,您就可以保持语义化。 这就像将 <h1><h2><h3> 等等的想法应用到按钮上。

<div class="copyright"></div>

**语义化。** 如果每个类名都这么容易就好了! 这适用于任何包含内容的区域,这些内容很容易用一个词来描述,比如 “tweets”“pagination”“admin-bar”。 尽管对于最后一个,您最好将其称为“admin-nav”,因为在理论上的重新设计未来,这个区域可能不再是“bar”了。

<p class="introp"></p>

**非语义化。** 我有一次看到 Dave Rupert 的一个演示,他开玩笑说这是他最喜欢的类名。 我完全能理解,因为它是一个非常常见的场景,即以不同的方式为页面的第一个段落设置样式,比如一个引人注目的概述,让用户进入文章。

如果您绝对需要超级深度的浏览器支持,您可能需要某种类名,在这种情况下,我认为“intro”比“introp”更好(不要在其中包含元素名称)。 但是,更好的方法是直接针对第一个段落,比如 article p:first-of-typeh1 + p

<div class="clearfix"></div>

**非语义化。** 这是一个非常常见的类名,它使用一些技巧让元素包含其所有后代浮动而不是折叠。 但它与它包含的内容无关,因此不可避免地是非语义化的。 Dan Cederholm 建议使用更友好的类名“group”来实现这个目的(在他的书 Handcrafted CSS 中),我认为这仅仅将它带入了语义化的领域,因为这个包装器肯定包含多个其他元素,因此是一个组(描述而不指定)。

<div class="left"></div>

**非语义化。** 也许在理论上的重新设计未来,你会想把这些东西放在右边。 太具体了。

<div class="success"></div>

**语义化。** 我认为这个最适合与其他类名一起使用,这样其中一个描述内容,另一个描述该内容的状态。 比如“success message”,它可以包含一条消息,比如“您的文件已上传!”。 如果该消息是“上传文件时出现问题”,那么类名可以改为“fail message”,并具有相应的样式。

<div class="plain-jane"></div>

**非语义化。** 这是试图指定里面的内容应该以特定方式进行样式设置。 “plain-jane” 与“normal”或“regular”类似。 理想情况下,CSS 应该被编写得这样,您不需要“regular”样式的类名,这应该通过级联默认提供,而任何以不寻常的方式打破这一点的东西都会获得一个类。

<div class="entry-unrelated"></div>

**非语义化。** Readability 是一款用于重新格式化和保存网页以方便以后阅读的网络应用程序,它使用这个类名来指定您不想意外包含在文章的对话/保存中的任何网站元素。 我在这里说它是非语义化的原因是,它描述了它不是什么,而不是它是什么。 我希望除了类名之外,还有其他方法可以用于此目的。 就像链接的 rel=nofollow,但针对内容。

<div class="hyphenate"></div>

**非语义化。** 试图指定里面的内容的行为,而不是描述它实际上是什么。

<a class="link" href="#"></a>

**非语义化。** 虽然链接是描述性的,而不是具体的,但仅仅是锚链接的性质就使其成为一个链接,因此没有必要。 如果类名试图将此链接与其他“普通”链接区分开来,请更详细地说明原因,例如“book-link”或(有争议的)“button”。

但是…

假设您的网站上有两种类型的文章,您想以不同的方式为它们设置样式。 电影评论将具有蓝色背景,突发新闻将具有红色背景和更大的文本。

以下是一种方法

<article class="movie-review">
   ...
</article>

<article class="breaking-news">
   ...
</article>

还有另一种方法

<article class="blueBg">
   ...
</article>

<article class="redBg bigText">
   ...
</article>

我敢打赌,如果我们进行民意调查,问人们他们认为哪个例子更语义化,第一个会获胜。 它符合本文中提出的要求:描述而不指定。 而第二个例子指定了(“blueBg”是一个应用蓝色背景的类名)。 假设理论上的重新设计未来不再是理论,而是正在进行中。 电影评论的设计现在具有绿色背景。 类名“blueBg”在那里相当笨拙。 而类名“movie-review”完全没问题,您只需更改属性/值来使用绿色背景即可。

这并不是说第一个例子总是更好。 假设浅蓝色在网站的很多地方都使用过。 也许它是页脚的某个特定部分和侧边栏框的特定背景颜色。 您最终可能会得到像这样的选择器

.movie-review, 
footer > div:nth-of-type(2),
aside > div:nth-of-type(4) {
   background: #c2fbff;
}

这很有效,因为您只声明了该颜色一次。 但它也是一个相当复杂、难以扫描、笨重的选择器。 更不用说这些不同的选择器可能需要唯一的样式,因此它们以后必须重复。 或者您采取另一种方法,只需将它们分开

.movie-review {
   background: #c2fbff;
   /* Plus other stuff */
}

footer > div:nth-of-type(2) {
   background: #c2fbff;
   /* Plus other stuff */
}

aside > div:nth-of-type(4) {
   background: #c2fbff;
   /* Plus other stuff */
}

这实际上可能会使您的 CSS 文件更井井有条(将网站的不同区域放在不同的部分),但代价是重复声明。 在 Nicole Sullivan 最近在 CSS Summit 上的演讲中,她指出了几家大公司在 CSS 文件中重复声明完全相同的颜色,次数高达数千次。 我想我们都同意这太疯狂了。 可能有各种解决方案,但其中之一可能是使用类似“blueBg”的类名来声明它一次,然后将应用该类名的负担放在 HTML 上,当您想要该设计时。 不过,您最好将其称为“mainBrandColor”或“secondaryFont”,以避免指定。 我理解,这就是 OOCSS。 为了更大的利益牺牲了一点语义化(大大减少资源)。

我很想听听您对这一切的看法。 我相信你们中许多人有其他例子,对什么是语义化或不是语义化有不同的看法,以及它是否重要。