欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

我们如何使用模块组织前端代码

程序员文章站 2022-05-25 23:50:21
...

有没有想过像Tuts +这样的大型网站如何在持续的开发和迭代过程中保持CSS,HTML和JavaScript的顺序? 我将向您展示我们为确保所有内容整洁和可维护而实施的过程。

CSS问题

这个过程的第一步是找到一种方法,以构建我们需要的大量CSS,而这些CSS不可避免地会陷入混乱。

传统上使用CSS,您可以根据需要建立样式,并努力使选择器广泛适用,以便可以在整个站点中重复使用它们。 例如,以下是一些简单CSS规则,这些规则在大多数样式表中都不会错位:

h1 { font-size: 22px; }
.subtitle { font-size: 18px; }

如果需要在页面的特定部分覆盖这些选择器,则可以使用嵌套规则来构造针对更特定元素的选择器:

.site-header h1 { font-size: 40px; }
.site-header .subtitle { font-size: 28px; }
.site-header a.navigation { color: #136FD2 }
...

这种方法在直觉上感觉是正确的,但是一旦您访问的网站有多个页面,并且有多个开发人员正在工作,则可能会遇到一些重大问题。

当我们在全局级别更改h1.subtitle的样式时会发生什么? font-size已经被更特定的样式覆盖,但是如果我们添加font-weightline-height ,则不会。 对全局样式所做的任何更改都可能以不熟悉站点上所有样式的方式无法预测的方式波及并影响更具体的样式。

以这种方式构建的样式越多,交互CSS样式的“副作用”就越明显,需要进行繁琐的反复试验才能纠正,最终导致生产力损失和更多的错误蔓延到生产环境。

BEM模块

为了帮助防止此问题,我们采用了基于BEM方法的 CSS 方法 除了定义适用于全球的样式外,所有样式都通过命名约定隔离为独立的“块”。 “块”或多或少地被定义为潜在的可重用的单个独立的内容单元(尽管并非强制要求实际上可以重用)。

例如,让我们看一下“功能部分”块:

根据我们的命名约定,此块具有根div元素,其类名称featured-sections 它包含具有类名称的元素,例如featured-sections__titlefeatured-sections__section-link

我们为源代码使用了一个匹配的命名约定,因此,这个featured-section块的所有样式都存储在modules/featured_section.sass

.featured-sections
  margin: 0 0 $gutter-width 0
  padding-top: 8px
  border-top: 4px solid #dae1e5

.featured-sections__title
  color: #8fa6b3
  font: bold 14px/1.2em $font

此命名约定确保样式不再冲突和混合。 只要遵循我们的命名约定,并且在每个类名的开头都使用块名,那么样式就不可能影响其自身块外的内容。

它还使在代码库中查找与元素相对应的样式的位置变得非常容易。 您只需查看元素的类名,就知道要打开的样式表的名称。

模块化查看代码

我们还选择了更进一步,并将此命名约定也应用到我们的视图中。 每个块都有一个具有相同名称的局部视图,存储在views/modules 例如,我们的featured-sections块HTML视图位于views/modules/_featured_sections.html.slim

与为我们CSS文件指定命名约定可以很容易地找到CSS样式一样,为我们的视图拥有这种命名约定也可以很容易地找到视图代码。 当您在浏览器中查看页面并注意到需要进行某些更改的特定部分时,这非常方便。 您可以执行“检查元素”,并使用元素CSS类中清晰可见的块名称,以帮助您直接跳至相关的视图文件。

模块化JavaScript

Backbone.js的帮助下,我们还继续为JavaScript代码采用了相同的命名约定。

每个需要应用JavaScript行为的块都使用相同的块名称获取Backbone视图对象:

class window.AccountHeader extends Backbone.View
  events:
    'change .account-header__mobile-menu-select': 'mobileMenuChange'

  mobileMenuChange: ->
    document.location = @_selectedOption().data('url')

  _selectedOption: ->
    @$ 'option:selected'

我们已经编写了一些页面加载时应用的视图加载代码,因此将为每个元素自动使用CSS类自动加载适当的Backbone视图,该CSS类与具有相关JS的块名称列表匹配。

我们也为我们JavaScript代码使用相同的文件命名约定,从而形成功能齐全的块的结构,如下所示:

一般适用性

对于任何项目,我都强烈建议使用此方法。 我认为在处理大型项目时这是无价的,即使您在规模较小的网站上工作,以模块化的方式构造前端代码也没有任何弊端。

也就是说,如果您已经拥有大量的全局CSS样式,或者如果您依赖于Twitter Bootstrap之类CSS库,则尝试使用此策略时可能会遇到问题。 由于BEM样式使用单个类名作为其选择器,因此它们CSS“特殊性”值非常低,并且往往被具有多个嵌套选择器以及标记名和ID的全局CSS样式踩踏。

从全局CSS样式转换为更具模块化的BEM样式绝对仍然可能,并且从长远来看,我认为这是非常值得的。 但是,一定要花一点时间来构建您的BEM样式,并且准备在整个CSS中添加至少一些临时的!important声明,直到您完全摆脱了全局性,才能做好准备。样式。

翻译自: https://code.tutsplus.com/articles/how-were-using-modules-to-organize-our-front-end-code--cms-22702