资讯动态

Varlet 轮播组件 Swipe 完全指南:从基本使用到源码级原理剖析

发布时间:2026/10/14 17:17:33 来源:尧图企业网站定制
UI组件前端【免费下载链接】varletA Vue3 component library based on Material Design 2 and 3, supporting mobile and desktop.项目地址https://gitcode.com/gh_mirrors/va/varlet点击查看免费下载导读本文围绕 Vue3 移动端组件库 Varlet 中的 Swipe轮播组件展开系统讲解var-swipe与var-swipe-item的配置参数、方法、事件、插槽与样式变量并结合仓库内组件源码与测试用例深入剖析循环播放、自动播放、触摸滑动、方向判定等底层实现原理。读完本文你将能够在自己的项目中快速搭建横/纵向轮播、自定义指示器与导航按钮并理解其背后的滑动机制。Swipe 组件是什么Swipe 是 Varlet 提供的一个基于触摸滑动与 CSS Transform 实现的轮播容器组件用于显示可以在屏幕上滚动和滑动的项目集合。它由两个配套组件组成var-swipe轮播容器负责触摸事件监听、自动播放、循环逻辑、指示器与导航渲染var-swipe-item单个轮播项每个项占据容器的一屏宽度或高度。在仓库中两者分别位于 swipe 与 swipe-item 目录均通过withInstall注册为可全局使用的组件。基本使用最简单的轮播只需要在var-swipe中放入若干var-swipe-itemtemplate var-swipe classswipe-example var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /style使用时有两点需要注意var-swipe自身的宽度为 100%高度需要开发者显式指定示例中通过.swipe-example { height: 160px }设置否则轮播容器将没有高度示例中的图片素材cat.jpg、cat2.jpg、cat3.jpg存放在仓库 public 目录 下可用于本地演示。轮播项的尺寸约定从源码看SwipeItem.vue 渲染的每个var-swipe-item会通过toSizeUnit(size)将容器宽度或高度取决于是否vertical设置到自身而 swipeItem.less 中flex-shrink: 0保证每个轮播项在轨道上不会被压缩。也就是说每个var-swipe-item恰好占满一屏轮播容器的尺寸这是整个滑动轨道尺寸计算的基础。禁止循环轮播默认情况下 Swipe 是循环轮播的loop默认为true。如果希望滑到末尾后停止可以设置:loopfalsetemplate var-swipe classswipe-example :loopfalse var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /style循环与非循环的边界处理在 Swipe.vue 中索引越界由clampIndex处理循环模式下索引-1会被折算为length - 1索引length会被折算为0非循环模式下则通过clamp将索引限制在[0, length - 1]区间内。测试用例 index.spec.js 中swipe loop用例验证了这一点当loop: false时连续向左拖动 4 次change事件最终停留在索引2不再前进。此外非循环模式下导航按钮也会联动禁用从 Swipe.vue 模板可见上一页按钮在!loop index 0时disabled下一页按钮在!loop index length - 1时disabled。开启自动播放通过autoplay属性设置自动播放间隔时间单位为毫秒轮播将每隔该时间自动切换到下一页template var-swipe classswipe-example :autoplay2000 var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /style自动播放的实现细节从 Swipe.vue 的startAutoplay源码可以看到三个关键行为至少两张才自动播放if (!autoplay || length.value 1) return单张轮播不会启动定时器递归 setTimeout每次调用next()完成切换后重新调用startAutoplay()布置下一次定时形成间隔播放链触摸即暂停handleTouchstart中会调用stopAutoplay()停止自动播放松手后在handleTouchend中重新startAutoplay()避免自动切换与用户手势冲突。autoplay的类型为string | number内部通过toNumber统一转换为毫秒数参与定时。测试用例swipe autoplayautoplay: 100验证了每隔约 100mschange事件依次触发索引1、2。垂直轮播添加vertical属性即可将轮播方向切换为垂直template var-swipe classswipe-example vertical var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /style垂直模式在源码中的体现垂直模式并不是简单的样式切换而是贯穿整个滑动链路轨道尺寸resize()中根据vertical决定读取offsetHeight还是offsetWidth轨道的width/height也随之切换位移方向handleTouchmove中轨道位移累加的是moveY而非moveXtransform使用translateY快速滑动方向判定handleTouchend中以deltaY 0手指向上滑作为下一页的判定指示器与导航布局垂直模式下指示器改为右侧竖向排列导航按钮改为上下居中布局见 swipe.less 中--indicators-vertical与--navigation-vertical-*相关样式。导航按钮通过navigation属性可开启左右导航箭头。当navigation为hover时导航按钮会在指针悬浮时显示适合桌面端场景template var-swipe classswipe-example navigation var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe var-swipe classswipe-example navigationhover var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; margin-top: 14px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /style导航按钮的实现与扩展从 Swipe.vue 模板可以看到导航按钮默认由var-button和var-icon组合渲染水平模式使用chevron-left/chevron-right图标垂直模式使用chevron-up/chevron-downnavigation hover时通过v-hover指令维护hovering状态只有navigation true || hovering才渲染按钮并套用进入/离开过渡动画动画类定义于 swipe.less更关键的是导航按钮区域prev/next插槽支持完全自定义可通过插槽传入的index、length、hovering、to、prev、next等插槽属性实现任意形态的翻页控件详见下文插槽章节。监听切换事件通过change事件可以监听当前轮播索引的变化事件参数为当前索引indexscript setup import { Snackbar } from varlet/ui /script template var-swipe classswipe-example change(index) Snackbar(String(index)) var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } /stylechange 事件的触发时机在 Swipe.vue 中onChange的回调统一通过call()触发触发点包括手势滑动松手后handleTouchend只有prevIndex ! index.value索引真正变化时才触发调用next()/prev()方法时默认触发除非传入{ event: false }显式禁止调用to(idx)跳转时内部通过逐页调用next/prev实现且只有到达目标页的那一次才允许触发change中间页传入event: false。类型定义见 props.ts 中的defineListenerProp(index: number) void()对应的SwipeToOptions.event语义为event值为false时阻止触发change事件。自定义指示器默认指示器是一组小圆点。通过indicator插槽可以完全接管指示器渲染。插槽会收到index当前索引、length总数和to跳转方法等属性template var-swipe classswipe-example var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat2.jpg /var-swipe-item var-swipe-item img classswipe-example-image srchttps://varletjs.org/cat3.jpg /var-swipe-item template #indicator{ index, length, to } div classswipe-example-indicators div classswipe-example-indicator v-for(l, idx) in length :keyl :class{swipe-example-active-indicator: idx index} clickto(idx) /div /div /template /var-swipe /template style .swipe-example { height: 160px; } .swipe-example-image { width: 100%; height: 100%; object-fit: cover; pointer-events: none; } .swipe-example-indicators { position: absolute; display: flex; bottom: 10px; left: 50%; transform: translateX(-50%); } .swipe-example-indicator { width: 8px; height: 8px; background: #fff; opacity: 0.3; margin: 0 4px; transition: opacity 0.3s; } .swipe-example-active-indicator { opacity: 1; } /style示例中自定义了一个方块指示器遍历length渲染指示点当前项idx index高亮点击任意指示点调用to(idx)跳转。仓库的完整示例可参考 example/index.vue。API 全览Props属性参数说明类型默认值loop是否开启循环轮播booleantrueautoplay自动播放间隔时间 (ms)string | number-duration切换过渡时间 (ms)string | number300initial-index初始化显示的索引string | number0indicator是否显示指示器booleantrueindicator-color指示器颜色string-vertical是否开启垂直轮播booleanfalsetouchable是否可以拖动booleantruenavigation是否显示导航箭头。设置为hover时指针悬浮会显示导航按钮boolean | stringfalse以上默认值与类型与 props.ts 中的定义一一对应。其中duration、autoplay、initialIndex均支持string | number内部通过toNumber与toSizeUnit处理见 elements.ts例如duration500与:duration500效果一致过渡时长最终反映在轨道的transition-duration样式上测试用例swipe duration断言了transition-duration: 500ms。方法方法名说明参数返回值resize产生位置大小变化时可以调用此方法进行重绘--prev上一页options?: SwipeToOptions-next下一页options?: SwipeToOptions-to跳转到指定下标index: number, options?: SwipeToOptions-方法通过组件setup的返回值暴露给模板与外部 ref 调用见 Swipe.vue 中// expose注释标记的resize、next、prev、to。其行为要点resize()会重新读取容器尺寸、重算trackSize与trackTranslate并广播给所有轮播项与注册的 resize 监听器组件在窗口 resize、onActivatedkeep-alive 激活以及轮播项数量变化时都会自动调用它next()/prev()在length 1时直接返回循环模式下越过边界时会借助fixPosition无缝回绕to(idx)内部把跳转拆解为逐页的next/prev调用且只有在最后一步才触发change事件event: false可全局禁止。SwipeToOptions参数说明类型默认值event值为false时阻止触发change事件boolean-该接口在 props.ts 中定义为{ event?: boolean }在 swipe.d.ts 中同步导出供 TS 用户直接引用。事件事件名说明参数change切换轮播时触发index: number轮播索引插槽Swipe Slots插槽名说明参数default轮播内容-prev上一页按钮index: number轮播索引length: number轮播总数hovering: boolean指针是否悬浮to、prev、next: 类型和同名方法一致next下一页按钮index: number轮播索引length: number轮播总数hovering: boolean指针是否悬浮to、prev、next: 类型和同名方法一致indicator指示器内容index: number轮播索引length: number轮播总数hovering: boolean指针是否悬浮to、prev、next: 类型和同名方法一致从 Swipe.vue 模板可见prev/next插槽默认渲染内置导航按钮而indicator插槽默认渲染内置指示圆点——三者的默认内容都可以被覆盖插槽属性的完整类型定义在 swipe.d.ts 的SwipeIndicatorData接口中。SwipeItem Slots插槽名说明参数default轮播项内容-样式变量以下为组件使用的 CSS 变量可以使用 StyleProvider 组件 进行样式定制。变量名默认值--swipe-indicator-color#fff--swipe-indicators-offset10px--swipe-indicator-offset4px--swipe-navigation-z-index9--swipe-navigation-button-width36px--swipe-navigation-button-height36px--swipe-navigation-button-border-radius50%--swipe-navigation-icon-size20px--swipe-navigation-prev-left8px--swipe-navigation-next-right8px--swipe-navigation-prev-top8px--swipe-navigation-next-bottom8px这些变量定义在 swipe.less 的:root中并分别作用于指示器颜色、圆点间距、距底位置与导航按钮z-index、尺寸、圆角、图标大小、四周偏移。例如想将指示圆点改为主题色只需覆盖--swipe-indicator-color。源码级原理滑动轨道是如何工作的理解 Swipe 的底层机制核心在于理解轨道 位移模型可从 Swipe.vue 的渲染与逻辑中还原1. 父子组件通过 provide/inject 协作。provide.ts 定义了SwipeProvider提供size、currentIndex、verticalswipe-item/provide.ts 通过useParent绑定父级并断言var-swipe-item必须处于var-swipe内部否则抛出SwipeItem, var-swipe-item/ must in var-swipe/提示。这样父组件就能统计length并调度每个子项。2. 尺寸与位移计算。resize()中size offsetWidth/offsetHeighttrackSize size * lengthtrackTranslate index * -size轨道通过translateX/translateY移动并用transition-duration控制过渡时长duration属性。3. 触摸滑动与方向判定。handleTouchmove中通过isExpectDirection判断手势方向是否与轮播方向一致水平轮播只响应横向手势不一致时直接返回避免与页面纵向滚动冲突滑动结束后handleTouchend综合位移距离与时间判定目标页快速滑动performance.now() - startTime 250且位移 20视为翻页否则根据位移过半情况取最近页。4. 循环回绕。循环模式下轨道越过首尾时dispatchSwipeItems会预先将首/尾子项克隆位移放置到轨道两端松手后fixPosition在关闭过渡动画lockDuration的状态下瞬间复位实现视觉上的无缝循环。5. 键盘可访问性。Swipe.vue 通过useEventListener监听window的keydown当某个var-swipe-item处于聚焦状态时ArrowLeft/ArrowRight分别触发prev()/next()对应测试用例swipe keyboard Arrow验证了方向键翻页行为。附测试与演示参考若想进一步验证文中所述行为可以关注单元测试 swipe/tests/index.spec.js覆盖了next/prev/to方法、键盘方向键、loop、autoplay、duration、initial-index、indicator与indicator-color、vertical、touchable、navigation含hover模式等全部核心能力移动端演示 example/index.vue提供了基本使用、禁止循环、自动播放、垂直轮播、导航、监听切换、自定义指示器七个完整的可运行示例类型声明 types/swipe.d.ts包含SwipeProps、SwipeToOptions、SwipeIndicatorData等接口方便 TS 项目接入。掌握 Swipe 的配置与原理后无论是移动端 Banner、图文轮播还是桌面端带悬浮导航的相册浏览都可以基于 Varlet 快速落地。赞分享UI组件前端【免费下载链接】varletA Vue3 component library based on Material Design 2 and 3, supporting mobile and desktop.项目地址https://gitcode.com/gh_mirrors/va/varlet点击查看免费下载相关推荐Varlet Swipe 轮播组件完整指南基础用法、API 参考与源码原理Varlet Swipe 轮播组件完整指南基础用法、API 参考与源码原理 轮播Swipe是移动端组件库中最常用的交互组件之一用于在一组内容之间进行横向UI组件前端rsuite Carousel 轮播组件完全指南从基础用法到源码级原理剖析rsuite Carousel 轮播组件完全指南从基础用法到源码级原理剖析 导读 Carousel 是 rsuite 中用于以轮播的方式显示一组元素的核心前端UI组件Varlet 组件库 Tooltip 提示组件完全指南从基础用法到源码级原理剖析Varlet 组件库 Tooltip 提示组件完全指南从基础用法到源码级原理剖析 导读 Tooltip提示是 Varlet 组件库中一个基于 PopperUI组件前端创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

读完文章,也想定制专属网站?

尧图设计师 24 小时内与您沟通定制方案

免费获取报价 →
↑