html本身不支持css-in-js,因其无javascript运行时、模块系统及js表达式执行能力;所谓“html中使用”实指在react等前端框架项目中,通过styled-components或@emotion等库实现样式与组件的动态绑定和作用域隔离。

HTML 本身不支持 CSS-in-JS——它只是静态标记语言,没有运行时、无模块系统、不能执行 JS 表达式。所谓“HTML 做 CSS-in-JS”,实际是指在基于 HTML 的前端项目(如 React/Vite/Next.js)中,如何让 CSS 样式逻辑真正和 JS 组件绑定、具备动态能力、避免全局污染。
React 项目里直接用 style 属性不是 CSS-in-JS
很多人误以为写 style={{ color: 'red', fontSize: '14px' }} 就是 CSS-in-JS,其实这只是 React 的内联样式机制,它缺三样关键东西:伪类(:hover)、媒体查询(@media)、样式复用(无法提取 class 或注入全局规则)。它适合极简状态切换,但撑不起组件级样式封装。
- 不支持
&:hover、&:active,得靠onMouseEnter+ 状态管理模拟,代码冗长 - 响应式要手动监听
window.matchMedia,无法写@media (max-width: 768px) - 每次渲染都生成新对象,可能触发不必要的重排,且无法被 DevTools 识别为真实 CSS 规则
styled-components 和 @emotion/react 是主流落地选择
这两个库在 React 生态中已形成事实标准,API 相近但底层差异明显:前者强依赖运行时注入,后者支持编译期优化(通过 @emotion/babel-plugin 可移除大部分运行时开销)。
文章转信息图。将文章/笔记转化为手机可读的 HTML 信息图,自动匹配视觉风格。触发场景:文章转图、笔记转图、信息图、转小红书图、做张图、可视化这篇文章、文生图。
-
styled-components必须配StyleSheetManager才能在 RSC(React Server Components)中安全使用,否则服务端生成的 class 名和客户端不一致 -
@emotion/react的css函数可直接用于className,配合useInsertionEffect实现更可控的注入时机,更适合混合 RSC/Client Component 架构 - 两者都支持主题(
ThemeProvider)、插值(${props => props.primary && 'blue'})、嵌套写法,但emotion对 TypeScript 类型推导更友好
RSC 场景下必须区分 use client 边界
React Server Components 默认禁止执行 DOM 操作和副作用,而大多数 CSS-in-JS 库需要向 注入 <style></style> 标签。这意味着:所有带样式的组件必须显式标记为 Client Component。
- 哪怕只用
css函数生成 class 字符串,只要用了@emotion/react的默认导出(如import { css } from '@emotion/react'),就隐含依赖运行时注入逻辑 - 错误写法:
export default function Header() { const className = css`color: red`; return <h1 classname="{className}">Hi</h1>; }—— 这会在 RSC 中报错ReferenceError: document is not defined - 正确写法:在文件顶部加
'use client';,或把样式逻辑抽到useEffect/useInsertionEffect安全区
别为了“CSS-in-JS”而放弃 CSS Modules
很多团队过早引入 styled-components,结果发现 80% 的组件根本不需要动态插值——它们只是按钮、卡片、表单字段,样式由 props 控制的只有 2–3 种变体(如 size="sm"、variant="outline")。这种场景下,CSS Modules 更轻、更易调试、构建产物更小。
- CSS Modules 的
.button--primary类名在构建时就确定,不会产生运行时 class 名哈希冲突 - DevTools 里能直接看到原始类名和对应源码位置,而
styled-components生成的sc-bdVaJa类名需点开才能溯源 - 如果你的“动态样式”只是开关几个预设 class(如
className={`${styles.button} ${props.primary ? styles.primary : ''}`),那 CSS-in-JS 带来的复杂度远高于收益
真正需要 CSS-in-JS 的地方很窄:主题实时切换、密度滑块控制、基于数据驱动的色彩映射、高频重绘的动画容器。把这些逻辑锁死在明确的 'use client' 组件里,比全局铺开更可持续。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!










