小程序里实现左滑动操作
1、wxml 文件
<view class="oper-list"> <view class="search-input"> <input placeholder="请输入账号" type="text" confirm-type="search" bindinput="saveKeyword" bindconfirm="queryAdminList" /> <text class="iconfont icon-chaxun1 icon-query"></text> </view> <view class="admin-add" bindtap="toAddAdmin"> <image src="../../../image/add-admin.png" /> </view> </view> <view wx:for="{{role_list}}" wx:for-item="role" wx:key="number" wx:if="{{role.number.length>0}}"> <view class="role-item-name"> {{role.name}} </view> <view wx:if="{{role.number==item.role}}" class="touch-item {{item.isTouchMove ? 'touch-move-active' : ''}}" data-index="{{item.id}}" wx:for="{{show_admin_list}}" wx:key="id"> <view class="content"> <view style="{{item.txtStyle}}" class='item' data-index='{{item.id}}' bindtouchstart="touchstart" bindtouchmove="touchmove" bindtouchend="touchE"> <view class="admin-info"> <view class="head-pic" bindtap="toAdminInfo" data-admin-no="{{item.clerk_no}}"> <image src="{{item.head_pic?item.head_pic:default_head_pic}}" /> </view> <view class="role-info" bindtap="toAdminInfo" data-admin-no="{{item.clerk_no}}"> <view class="admin-info-name"> {{item.clerk_name}} {{item.clerk_no}} </view> <view class="role-info-name"> {{item.role_name}} </view> </view> <view class="role-oper" wx:if="{{item.openid.length>0}}" bindtap="toAdminInfo" data-admin-no="{{item.clerk_no}}"> <view class="admin-phoneno"> {{item.phone_no}} </view> <view class="role-oper-btn"> 已绑定 </view> </view> <view class="role-oper" wx:else bindtap="bindAdmin" data-admin-no="{{item.clerk_no}}" data-admin-pwd="{{item.clerk_pwd}}"> <view class="share-pic"> <image src="../../../image/share.png"></image> <view class="share-txt"> 分享 </view> </view> </view> </view> </view> </view> <view class="del"> <view data-admin-no="{{item.clerk_no}}" data-openid="{{item.openid}}" data-id="{{item.id}}" catchtap="operAdmin" data-oper-type="unbind" data-index="{{item.id}}" class="untying">解绑</view> <view class='delete' data-admin-no="{{item.clerk_no}}" data-id="{{item.id}}" data-oper-type="delete" catchtap="operAdmin" data-index="{{item.id}}">删除</view> </view> </view> </view> <view class="admin-count"> {{show_admin_list.length}}个账号 </view>
2、wxss 文件
.touch-item {
display: flex;
justify-content: space-between;
width: 100%;
overflow: hidden;
background: rgba(255, 255, 255, 1);
opacity: 1;
}
.content {
width: 100%;
margin-right: 0;
-webkit-transition: all 0.4s;
transition: all 0.4s;
-webkit-transform: translateX(120px);
transform: translateX(120px);
margin-left: -120px;
}
.del {
width: 120px;
display: flex;
align-items: center;
justify-content: space-between;
color: #fff;
-webkit-transition: all 0.4s;
transition: all 0.4s;
font-size: 35rpx;
-webkit-transform: translateX(180px);
transform: translateX(180px);
}
.del .delete {
background: red;
display: flex;
align-items: center;
justify-content: center;
width: 50%;
height: 100%;
}
.del .untying {
background: orange;
display: flex;
align-items: center;
justify-content: center;
width: 50%;
height: 100%;
}
.touch-move-active .content, .touch-move-active .del {
-webkit-transform: translateX(0);
transform: translateX(0);
}
page {
background: #fff;
}
.oper-list {
width: 100%;
display: flex;
display: -webkit-flex;
margin-top: 10px;
margin-bottom: 10px;
/* position: fixed;
top: 10px;
left: 2%; */
}
.search-input {
width: 84%;
height: 40px;
line-height: 40px;
margin-left: 2%;
}
.search-input input {
height: 30px;
line-height: 30px;
padding: 5px;
border: 1rpx solid #eee;
vertical-align: middle;
border-radius: 30px;
background: #f5f5f5;
}
.admin-add {
height: 40px;
line-height: 40px;
text-align: center;
width: 14%;
}
.admin-add image {
width: 30px;
height: 30px;
padding: 5px;
}
.admin-list {
width: 100%;
margin-top: 10px;
}
.admin-info {
display: -webkit-flex;
height: 60px;
border-bottom: 1px solid #eee;
font-size: 14px;
}
/**
内容超出显示 ...
*/
.admin-info-name {
height: 25px;
line-height: 25px;
color: #7a7d88;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.role-info-name {
height: 25px;
line-height: 25px;
color: #7a7d88;
}
.admin-phoneno {
height: 25px;
line-height: 25px;
}
.role-oper-btn {
height: 25px;
line-height: 25px;
}
.head-pic {
width: 80px;
padding: 5px 0px 5px 10px;
}
.head-pic image {
width: 50px;
height: 50px;
border-radius: 10px;
}
.role-info {
flex: 1;
padding: 5px 0px;
}
.role-oper {
padding: 5px 10px 5px 0;
width: 30%;
text-align: right;
color: #7a7d88;
}
.share-pic {
height: 60px;
}
.share-pic image {
height: 20px;
width: 20px;
margin-right: 5px;
}
.share-txt {
height: 25px;
line-height: 25px;
}
.role-item-name {
background: #e4f2fb;
padding: 5px 10px;
color: #969ba6;
}
.admin-count {
background: #e4f2fb;
padding: 10px 0px;
color: #969ba6;
text-align: center;
}
.icon-query {
position: relative;
left: 90%;
bottom: 40px;
font-size: 26px;
color: #aaa;
}
3、js文件
const app = getApp(); const http = require('../../../utils/http.js'); const api = require('../../../config.js'); const utils = require('../../../utils/util.js'); Page({ /** * 页面的初始数据 */ data: { startX: 0, //开始坐标 startY: 0, page: 1, admin_list: [], show_admin_list: [], default_head_pic: '../../../image/default-head-pic.png', keyword: '', role_list: [], }, touchE: function(e) { // console.log(e); var that = this if (e.changedTouches.length == 1) { //手指移动结束后触摸点位置的X坐标 var endX = e.changedTouches[0].clientX; //触摸开始与结束,手指移动的距离 var disX = that.data.startX - endX; var delBtnWidth = that.data.delBtnWidth; //如果距离小于删除按钮的1/2,不显示删除按钮 var txtStyle = disX > delBtnWidth / 2 ? "left:-" + delBtnWidth + "rpx" : "left:0rpx"; //获取手指触摸的是哪一项 var index = e.currentTarget.dataset.index; var list = that.data.show_admin_list; list[index].txtStyle = txtStyle; //更新列表的状态 that.setData({ show_admin_list: list }); } }, //手指触摸动作开始 记录起点X坐标 touchstart: function(e) { //开始触摸时 重置所有删除 this.data.show_admin_list.forEach(function(v, i) { if (v.isTouchMove) //只操作为true的 v.isTouchMove = false; }) this.setData({ startX: e.changedTouches[0].clientX, startY: e.changedTouches[0].clientY, show_admin_list: this.data.show_admin_list }) }, //滑动事件处理 touchmove: function(e) { var that = this, index = e.currentTarget.dataset.index, //当前索引 startX = that.data.startX, //开始X坐标 startY = that.data.startY, //开始Y坐标 touchMoveX = e.changedTouches[0].clientX, //滑动变化坐标 touchMoveY = e.changedTouches[0].clientY, //滑动变化坐标 //获取滑动角度 angle = that.angle({ X: startX, Y: startY }, { X: touchMoveX, Y: touchMoveY }); that.data.show_admin_list.forEach(function(v, i) { v.isTouchMove = false //滑动超过30度角 return if (Math.abs(angle) > 30) return; if (i == index) { if (touchMoveX > startX) //右滑 v.isTouchMove = false else //左滑 v.isTouchMove = true } }) //更新数据 that.setData({ show_admin_list: that.data.show_admin_list }) }, /** * 计算滑动角度 * @param {Object} start 起点坐标 * @param {Object} end 终点坐标 */ angle: function(start, end) { var _X = end.X - start.X, _Y = end.Y - start.Y //返回角度 /Math.atan()返回数字的反正切值 return 360 * Math.atan(_Y / _X) / (2 * Math.PI); }, /** * 生命周期函数--监听页面加载 */ onLoad: function(options) { this.getRoleList(); }, /** * 获取角色列表 */ getRoleList: function() { let _this = this; let postData = { 'shopid': app.globalData.shopid, }; _this.setData({ role_list: [] }); wx.showLoading({ title: '角色列表获取中...', mask: true }) http.httpGet(api.GetRoleList, postData, (res) => { console.log(res); wx.hideLoading(); _this.getAdminList(); if (!res) { return; } if (res.success) { let _result = res.result; if (_result.success) { this.setData({ role_list: _result.data }); } else { utils.showToastMessage(_result); } } else { utils.showToastMessage(res); } }); }, toAddAdmin: function(e) { wx.redirectTo({ url: '../../../pages/Admin/AddAdmin/AddAdmin', }) }, saveKeyword: function(e) { this.setData({ keyword: e.detail.value }); }, bindAdmin: function(e) { console.log(e); wx.navigateTo({ url: '../../../pages/Admin/AdminQrcode/AdminQrcode?admin_no=' + e.currentTarget.dataset.adminNo + '&admin_pwd=' + e.currentTarget.dataset.adminPwd, }) }, queryAdminList: function() { var adminList = this.data.admin_list; let keyword = this.data.keyword.replace(/ /g, ''); if (keyword) { var showAdminList = []; for (let i = 0; i < adminList.length; i++) { if (adminList[i].clerk_no.indexOf(keyword) > -1 || adminList[i].clerk_name.indexOf(keyword) > -1) { showAdminList.push(adminList[i]); } } for (let i = 0; i < showAdminList.length; i++) { showAdminList[i].id = i; } this.setData({ show_admin_list: showAdminList }); } else { for (let i = 0; i < adminList.length; i++) { adminList[i].id = i; } this.setData({ show_admin_list: adminList }); } }, toAdminInfo: function(e) { console.log(e); wx.removeStorageSync('edit-admin-info'); let adminNo = e.currentTarget.dataset.adminNo; if (adminNo) { for (let i = 0; i < this.data.admin_list.length; i++) { if (this.data.admin_list[i].clerk_no == adminNo) { wx.setStorageSync('edit-admin-info', this.data.admin_list[i]) wx.navigateTo({ url: '../../../pages/Admin/AdminInfo/AdminInfo?admin_no=' + adminNo, }) } } } else { wx.showToast({ title: '账号编号为空', icon: 'none ' }) } }, getAdminList: function() { let _this = this; let postData = { 'openid': app.globalData.openid, 'shopid': app.globalData.shopid, }; wx.showLoading({ title: '账号获取中...', mask: true }) _this.setData({ admin_list: [], show_admin_list: [] }); http.httpPost(api.GetAdminList, postData, (res) => { console.log(res); wx.hideLoading(); if (!res) { return; } if (res.success) { let _result = res.result; if (_result.success) { let _branchList = []; _result.data.forEach(e => { if (!(e.openid && e.openid == app.globalData.openid)) { _branchList.push(e); } }); for (let i = 0; i < _branchList.length; i++) { _branchList[i].id = i; } _this.setData({ admin_list: _branchList, show_admin_list: _branchList }); } else { utils.showToastMessage(_result); } } else { utils.showToastMessage(res); } }); }, operAdmin: function(e) { let _this = this; console.log(e); let operType = e.currentTarget.dataset.operType; let adminNo = e.currentTarget.dataset.adminNo; let openid = e.currentTarget.dataset.openid; if (operType == "unbind" && !openid) { wx.showToast({ title: '该账号未绑定,操作无效', icon: 'none' }) return; } if (openid == app.globalData.openid) { wx.showToast({ title: '不能操作自己绑定的账号', icon: 'none' }) return; } wx.showModal({ title: '提示', content: '确定对该账户进行' + (operType == "delete" ? "删除" : "解绑") + "操作吗?", confirmText: (operType == "delete" ? "删除" : "解绑"), confirmColor: (operType == "delete" ? "red" : "orange"), success: res => { _this.toOperAdmin(operType, adminNo); } }) }, toOperAdmin: function(oper_type, admin_no) { let _this = this; let postData = { 'shopid': app.globalData.shopid, 'openid': app.globalData.openid, 'oper_type': oper_type, 'admin_no': admin_no }; _this.setData({ role_list: [] }); wx.showLoading({ title: oper_type == "delete" ? '删除中...' : '解绑中...', mask: true }) http.httpPost(api.OperAdmin, postData, (res) => { console.log(res); wx.hideLoading(); if (!res) { return; } if (res.success) { _this.onLoad(); let _result = res.result; if (_result.success) { wx.showToast({ title: oper_type == "delete" ? '删除成功' : '解绑成功', }) } else { utils.showToastMessage(_result); } } else { utils.showToastMessage(res); } }); }, /** * 生命周期函数--监听页面初次渲染完成 */ onReady: function() { }, /** * 生命周期函数--监听页面显示 */ onShow: function() { let editOper = wx.getStorageSync('edit-admin-info'); let editOper2 = wx.getStorageSync('edit-admin-info-2'); if (editOper || editOper2) { this.getAdminList(); wx.removeStorageSync('edit-admin-info'); wx.removeStorageSync('edit-admin-info-2') } }, /** * 生命周期函数--监听页面隐藏 */ onHide: function() { }, /** * 生命周期函数--监听页面卸载 */ onUnload: function() { }, /** * 页面相关事件处理函数--监听用户下拉动作 */ onPullDownRefresh: function() { }, /** * 页面上拉触底事件的处理函数 */ onReachBottom: function() { }, /** * 用户点击右上角分享 */ onShareAppMessage: function() { } })
4、效果图