uni-app使用movable-area 实现数据的拖拽排序功能

文档地址

template部分
html 复制代码
<movable-area :style="getAreaStyle">
	<movable-view class="table-row" 
        v-for="v,i in move.list"
        :key="v.id"
        :y="v.y"
        @change="handle_moving"
		direction="vertical"
        @touchstart="handle_dragstart(i,v)" 
        @touchend="handle_dragend(i,v)"
		@longpress="handleLongpress(v)" 
        :disabled="move.disabled">
				<view class="table-cell">{{i+1}}</view>
				<view class="table-cell">选择物料</view>
	 </movable-view>
</movable-area>
css 复制代码
.table-cell,.table-row{
   height:50rpx;
}
.table-row{
  width:100%;
  display: flex;
}
.table-cell{
  width:200rpx;
}

注意使用movable-area时需要设置高度和宽度 否则默认10

js部分
javascript 复制代码
const move = reactive({
        list:[],
		disabled: true,
		activeIndex: -1,
		moveToIndex: -1,
		oldIndex: -1,
		tempDragInfo: {
			y: ''
		},
		cloneList: [],
		longpress: true,

	})

	// 获取位置
	const getPosition_y = (index) => {
		return index * 25
	}
	const getAreaStyle = computed(() => {
		return {
			width: '100%',
			height: move.list.length * 25 + 'px'
		}
	})

	// 初始化列表
	const initList = (list = []) => {
		const newList = JSON.parse(JSON.stringify(list));
		move.list = newList.map((item, index) => {
			return {
				...item,
				y: getPosition_y(index)
			}
		})
		move.cloneList = JSON.parse(JSON.stringify(move.list));
	}

	// 开始拖拽
	const handle_dragstart = (i,v) => {
		if(!v.id){
			return false;
		}
		move.activeIndex = i;
		move.oldIndex = i;
	}

	// 拖拽结束
	const handle_dragend = (i,v) => {
		if(!v.id){
			return false;
		}
		if (move.disabled) return;
		if (move.moveToIndex != -1 && move.activeIndex != -1 && move.activeIndex != move.moveToIndex) {
			move.cloneList.splice(move.moveToIndex, 0, ...move.cloneList.splice(move.activeIndex, 1));
		} else {
			move.list[move.activeIndex]['y'] = move.tempDragInfo.y;
		}
		initList(move.cloneList)
		move.activeIndex = -1;
		move.oldIndex = -1;
		move.moveToIndex = -1;
		move.disabled = true;
	}

	// 移动
	const handle_moving = (e) => {
		console.log({e})
		if (e.detail.source !== 'touch') return;
		let y = e.detail.y;
		move.tempDragInfo.y = y;
		const currentY = Math.floor((y + 12.5) / 25)
		move.moveToIndex = Math.min(currentY, move.list.length - 1);
		if (move.oldIndex != move.moveToIndex && move.oldIndex != -1 && move.moveToIndex != -1) {
			const newList = JSON.parse(JSON.stringify(move.cloneList));
			let splicItem = newList.splice(move.activeIndex, 1)[0]
			newList.splice(move.moveToIndex, 0, splicItem);
			move.list.forEach((item, index) => {
				if (index != move.activeIndex) {
					const itemIndex = newList.findIndex(val => val?.id === item?.id);
					item['y'] = getPosition_y(itemIndex);
				}
			});
			move.oldIndex = move.moveToIndex;
		}
	}


	const handleLongpress = (v) => {
		if(!v.id){
			return false
		}
		move.disabled = false;
	}
相关推荐
多客:duokelijie13 小时前
代练订单系统选型思路:跨品类游戏接入、订单分层管理、自动结算逻辑拆解!
数据库·mysql·微信小程序·前端框架·uni-app·php·持续部署
码间留白20 小时前
鸿蒙端对接 BLE 血压计:从一次握手到读数入库(二)设备篇
物联网·uni-app·鸿蒙·蓝牙ble·血压计
华玥作者2 天前
Vue 3 + TypeScript + uni-app 组件库推荐:hy-app(华玥组件库)
vue.js·typescript·uni-app
FinelyYang2 天前
uniapp使用kkfileview在线预览ppt,excel,word,pdf类型文件
pdf·uni-app·powerpoint
2501_916008892 天前
iPhone 设备信息查看,用 KeyMob 看型号、序列号、电池健康和 UDID
android·ios·小程序·https·uni-app·iphone·webview
ModyQyW3 天前
vite-plugin-uni-manifest 0.7:在 uni-app 读取之前生成
前端·uni-app
lyz2468593 天前
uniapp vue3 小程序开发注意事项
uni-app
雪芽蓝域zzs3 天前
WebStorm Uniapp Support + Uniapp Tool + Uniappx Language Service讲解
vue.js·uni-app·webstorm
普通人63 天前
Web端3D模型加载实战指南_Vue3_uni-app_HTML
前端·javascript·uni-app·html
PedroQue995 天前
0.8.2 新增 backFallback 配置,无 tabbar 页返回无忧
前端·uni-app