为什么选择CSS in JS?
天生的 Scoped 样式
传统基于类选择器的 CSS, 有一个被大家诟病的地方就是没有本地作用域,所有声明的样式都是全局生效的,这让大型项目的 CSS 编写和维护变得异常困难。为了解决这个问题,前端社区花了非常大的精力解决这个问题,比如 BEM/SMACSS/OOCSS 等 CSS 使用方法论,比如 Less/Sass/Stylus 等 CSS 预处理器。
BEM/SMACSS/OOCSS 的问题在于它们只是约定,你很难让团队成员达成这些方法论的共识,并且长期完美的格遵循这些约定。
Less/Sass/Stylus 试图把编程能力带到 CSS,可惜带来的并不是真正的编程能力,反而让工具链变得复杂,而且扩展的语法也并不好用。
CSS-in-JS 呢? 它是天生的 Scoped 样式,它从机制上解决 CSS 作用域问题,而不是一些难以遵守的约定。
消除无用代码
由于 HTML 和 CSS 一般通过类名建立联系, 他们之间存在隐式关系,因此通常很难跟踪未使用的 CSS 样式,删除组件后,很难精确删除对应的 CSS,因为你会害怕其他地方使用了样式,你会没信心删除,而且缺乏安全感。使用 CSS-in-JS,样式和结构的关系是显式的,样式和结构是绑定的,结构和样式的增加、修改、删除是同步,几乎不会出现死代码。
特别是大型前端项目,使用传统的方法很容易让无用的 CSS 膨胀,越来越来越多,并且每人敢动,而使用 CSS-in-JS,不会出现无用代码。
动态样式
根据应用的状态控制组件的样式,我们称之为动态样式。CSS-in-JS 非常强大的特性之一是基于状态的样式。传统的处理方式是,定义多个 CSS 类名,用 JS 根据应用状态改变 CSS 类名。这种处理方式的最大缺点: 样式的状态是脱离应用状态的上下文(Context)的,它通过 CSS 类名钩子关联,另外这种方式代码编写十分繁琐。使用 CSS-in-JS,样式规则直接根据应用状态生产,样式在状态的上下文中,你可以理解为 Style=f(State),不用通过 CSS 类名这些中间人隐式地描述动态样式。
组件化
曾经 Web 应用是基于页面 (Page)的,一个页面的实现通常由 HTML、JS、CSS 3 个文件组成,那时关注点分离是合理的。现在,前端进入了组件化时代,一个页面通常由多个组件组合完成,这时 CSS in JS 更适合组件化的场景。
更好的开发体验
你不需要写 CSS,只需写 JS,心智负担更小,而且可以配合 TypeScript,类型提示更加精准。 CSS-in-JS 使开发人员更具表现力,同时鼓励使用比级联更可维护的模式。在组件体系结构中,将多个组件的关注点放在一个地方就成为了当务之急。
强约束性
多年以来,前端开发人员一直在与 CSS 的各种方法论作斗争,比如 BEM/SMACSS/OOCSS,但在没有严格监督的情况下都很难落实和管理。Fower 提供一种提约束的编写样式方法: Atomic Props,让每个人使用同样的方式编写样式。
支持非浏览器,如 React Native, 小程序