Embla 与 Swiper:按你要构建的东西来选
两者都是出色且维护活跃的轮播引擎,二者之间的选择确实相当接近。归结起来是一个维度:Swiper 内置了所有功能;Embla 提供一个供你在其上构建的小型无头引擎。本页由一个与两者都不构成竞争的库的维护者撰写——而这也正是文末给出的第三个答案,留给那些其实根本算不上轮播图的场景。
| Embla | Swiper | |
|---|---|---|
| 是什么 | 无头轮播引擎 | 完整的滑块/轮播框架 |
| 包体积(核心,min+gzip) | ≈8 kB | ≈40 kB(随模块增加而增长) |
| 样式与标记 | 完全由你自己提供——它本身不带任何样式 | 有自己的 DOM 结构和 CSS,可主题化 |
| 特效(渐隐、立方体、coverflow 等) | 社区插件,或自行实现 | 内置,成熟稳定 |
| 自动播放、分页、缩略图 | 官方插件 | 内置模块 |
| React 集成 | 一等公民 hook(useEmblaCarousel) | 在原生核心之上封装的组件 |
| 生态位置 | shadcn/ui 轮播组件底层使用的引擎 | Web 上使用最广泛的滑块库 |
| 最适合 | 自定义设计的轮播图、设计体系 | 以图片为主的滑块、功能丰富的画廊 |
包体积均为核心部分的近似值——最新数字请查阅 bundlephobia;Swiper 的体积会随你引入的模块增长。
当设计控制权是关键时,选择 Embla
Embla 提供吸附物理效果、拖拽处理和幻灯片模型,仅此而已——没有标记、没有 CSS、没有箭头。这正是它的优势所在:在一个设计体系中,所有可见的东西都由你掌控,引擎也绝不会与你的样式打架。shadcn/ui 的轮播组件正是构建在它之上,这也说明了它的最佳定位:那些希望轮播图看起来像自家产品、而不是像某个轮播库的团队。
代价是,滑动之外的每一项功能都要靠插件或手工实现:自动播放和 class 名由官方插件提供;分页圆点、缩略图和特效都得自己写。
当你想要功能开箱即用时,选择 Swiper
Swiper 是内置一切的答案:渐隐、立方体、coverflow 特效,虚拟幻灯片,缩放,视差,缩略图画廊,a11y 模块,多种样式的分页——只需配置,无需自己构建。如果你的产品这个季度就需要用到其中三项,Swiper 的体积很快就能物有所值。
代价则与 Embla 相反:你会继承 Swiper 的 DOM 结构、需要主题化的 CSS,以及一个为 React 封装的原生 JS 核心——无论是 KB 数还是表面积都更重。
在选择两者之前该先问的问题
这两个库都假定你展示的是幻灯片——一次一个,或一页一组,带有吸附对齐和明确的位置感。而现实中相当一部分“轮播图”根本不是这样:分类行、logo 条、标签栏、筛选标签——这些都是供用户浏览、点选的可点击项目行。它们需要的是原生滚动(免费获得惯性、滚动条、滚轮、无障碍支持),再加上知道哪些项目在屏幕上——而 Embla 和 Swiper 都没有对逐项可见性建模,因为幻灯片不是项目。
对于这种形态,还有第三个选择:react-horizontal-scrolling-menu(≈5.7 kB)依靠原生滚动,并提供 useIsVisible、scrollToItem 和边缘感知箭头。可以在 Netflix 风格行、标签栏 或 筛选标签栏 中看到它的应用,也可以查看与两者的 完整对比表。