2021-05-05 23:40:07
uni-app滑动删除可通过手势识别与布局偏移实现,核心是监听滑动事件、动态调整布局,并通过细节优化提升交互体验,也可借助组件库快速开发。
一、基础实现方式布局设计
列表项采用flex布局,左侧为主内容区域,右侧为隐藏的操作按钮(如“删除”)。
默认状态下操作按钮通过transform: translateX(100%)或绝对定位隐藏在右侧。
示例代码结构:<view @touchstart="handleTouchStart" @touchend="handleTouchEnd"> <view class="content">主内容</view> <view class="actions">删除</view></view>
手势监听与动态偏移
监听touchstart和touchend事件,记录起始位置(startX)和结束位置(endX)。
根据滑动距离(endX - startX)动态调整内容区域的transform: translateX()值,实现滑动效果。
示例逻辑:handleTouchStart(e) { this.startX = e.touches[0].pageX;},handleTouchEnd(e) { const endX = e.changedTouches[0].pageX; const slideDistance = this.startX - endX; if (slideDistance > 30) { // 滑动阈值 this.isOpen = true; // 展开操作按钮 } else { this.isOpen = false; // 收回 }}
阈值控制
设置滑动阈值(如30px),避免轻微滑动误触发操作按钮展开。
滑动距离超过阈值时,自动展开按钮;未超过则恢复原状。
动画优化
为transform属性添加transition效果,使滑动过程更平滑。
示例CSS:.content { transition: transform 0.3s ease-in-out;}
单列表项展开控制
通过变量(如currentOpenIndex)记录当前展开的列表项索引,滑动新项时自动关闭已展开项。
示例逻辑:handleTouchEnd(e, index) { if (this.currentOpenIndex !== null && this.currentOpenIndex !== index) { this.closeAll(); // 关闭其他已展开项 } // 更新当前展开状态 this.currentOpenIndex = slideDistance > 30 ? index : null;}
点击外部关闭展开项
监听页面点击事件,若点击区域非列表项或操作按钮,则关闭所有展开项。
示例逻辑:onPageClick() { this.closeAll();}
防止滑动与滚动冲突
在touchmove事件中判断滑动方向,垂直滑动时阻止默认行为以避免影响列表滚动。
示例逻辑:handleTouchMove(e) { const moveY = e.touches[0].pageY - this.startY; if (Math.abs(moveY) > 5) { // 垂直滑动阈值 e.preventDefault(); // 阻止默认滚动 }}
uni-ui的uni-swipe-action组件
直接调用封装好的组件,无需手动处理手势和动画。
示例代码:<uni-swipe-action> <uni-swipe-action-item :options="[{text: '删除', style: {backgroundColor: '#dd524d'}}]" @click="onDelete(index)" > <view class="item-content">列表项内容</view> </uni-swipe-action-item></uni-swipe-action>
其他UI库(如uView、ThorUI)
类似uni-swipe-action,提供配置化滑动删除功能,支持自定义按钮样式和事件。
平台差异处理
H5端需注意touch事件的兼容性,部分浏览器可能需要添加-webkit-overflow-scrolling: touch优化滚动。
小程序端需测试手势灵敏度,避免因平台差异导致滑动卡顿。
性能优化
避免在滑动过程中频繁操作DOM或执行复杂计算(如v-for中直接修改数据)。
使用requestAnimationFrame优化动画性能,减少重绘和回流。
测试场景覆盖
测试多列表项同时滑动、快速滑动、边界滑动等场景,确保功能稳定。
检查滑动后列表滚动是否流畅,避免因事件拦截导致卡顿。