前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >微信小程序单指拖拽和双指缩放旋转

微信小程序单指拖拽和双指缩放旋转

作者头像
超级小可爱
发布2023-03-07 20:23:12
2.4K3
发布2023-03-07 20:23:12
举报
文章被收录于专栏:小孟开发笔记

小程序单指拖拽和双指操作是一个比较常用的功能,效果如下图

在这里插入图片描述
在这里插入图片描述
  • 实现这三个功能,主要用三个触摸事件touchstarttouchmovetouchend
代码语言:javascript
复制
<view style="height: 100vh; width: 100vw">
  <image
    src="..."
    style="transform: translate({{translateX}}px, {{translateY}}px) scale({{scale}}) rotate({{rotate}}deg);"
    catch:touchstart="touchStart"
    catch:touchmove="touchMove"
    catch:touchend="touchEnd"
  />
</view>
  • 用了以下变量
代码语言:javascript
复制
Page({
  data: {
    translateX: 0, // 位移x坐标 单位px
    translateY: 0, // 位移y坐标 单位px
    distance: 0, // 双指接触点距离
    scale: 1, // 缩放倍数
    rotate: 0, // 旋转角度
    oldRotate: 0, // 上一次旋转停止后的角度
    startMove: { // 起始位移距离
      x: 0,
      y: 0,
    },
    startTouches: [] // 起始点touch数组
  },
})

单指拖拽

  • 单指拖拽比较简单,只需要记录移动的点坐标,然后减去起始点坐标,就可以求出针对页面的移动距离
  • touchstart
代码语言:javascript
复制
touchStart(e) {
  const touches = e.touches
  const { translateX, translateY } = this.data
  const { pageX, pageY } = touches[0]
  this.data.startMove = {
    x: pageX - translateX,
    y: pageY - translateY
  }
  this.data.startTouches = touches
},
  • touchmove
代码语言:javascript
复制
touchMove(e) {
  const touches = e.touches
  const { pageX: onePageX, pageY: onePageY } = touches[0]
  const { startMove } = this.data
  this.setData({
    translateX: onePageX - startMove.x,
    translateY: onePageY - startMove.y
  })
}

双指缩放

  • 双指缩放的原理是根据两点坐标求出距离(勾股定理),然后在用移动坐标的距离比就可以求出缩放倍数
  • touchmove
代码语言:javascript
复制
touchMove(e) {
  const touches = e.touches
  const { pageX: onePageX, pageY: onePageY } = touches[0]
  const { startMove, scale, distance: oldDistance, startTouches } = this.data
  if (touches.length === 2 && startTouches.length === 2) {
      // 双指缩放
    const { pageX: twoPageX, pageY: twoPageY } = touches[1]
    // 求出当前双指距离
    const distance = Math.sqrt((twoPageX - onePageX) ** 2 + (twoPageY - onePageY) ** 2)
    this.data.distance = distance
    this.setData({
      scale: scale * (distance / (oldDistance || distance))
    })
  } else if (startTouches.length !== 2) {
      // 单指拖拽
    this.setData({
      translateX: onePageX - startMove.x,
      translateY: onePageY - startMove.y
    })
  }
}

startTouches.length !== 2这个判断的原因是防止图片跳动,因为如果你两个手指触摸,然后离开一个手指,我是禁止拖拽的,只有双指都离开后再次触摸才能单指拖拽

双指旋转

双指旋转的原理是根据三角函数求出起始点的角度,然后再求出移动坐标的角度,相减然后加上上一次旋转的角度就等于你当前所需的选择角度

touchmove

代码语言:javascript
复制
touchMove(e) {
  const touches = e.touches
  const { pageX: onePageX, pageY: onePageY } = touches[0]
  const { startMove, scale, distance: oldDistance, startTouches, oldRotate } = this.data
  if (touches.length === 2 && startTouches.length === 2) {
    const { pageX: twoPageX, pageY: twoPageY } = touches[1]
    const distance = Math.sqrt((twoPageX - onePageX) ** 2 + (twoPageY - onePageY) ** 2)
+   let rotate = this.getAngle(touches[0], touches[1]) - this.getAngle(startTouches[0], startTouches[1]) + oldRotate
    // 如果大于360度,就减去360
+   rotate = rotate > 360 ? rotate - 360 : rotate
    this.data.distance = distance
    this.setData({
      scale: scale * (distance / (oldDistance || distance)),
+     rotate
    })
  } else if (startTouches.length !== 2) {
    this.setData({
      translateX: onePageX - startMove.x,
      translateY: onePageY - startMove.y
    })
  }
},
  • getAngle
代码语言:javascript
复制
//getAngle
getAngle(p1, p2) {
  const x = p1.pageX - p2.pageX
  const y = p1.pageY- p2.pageY
  return Math.atan2(y, x) * 180 / Math.PI
}
  • touchend
代码语言:javascript
复制
touchEnd() {
  // 保存当前旋转角度
  this.data.oldRotate = this.data.rotate
},

总结

  • 代码片段https://developers.weixin.qq.com/s/0nS1tImU7Rs5
  • H5原理一致,只需改一下语法即可
  • 我这个只是基础版本,如果需要一些边界控制和还一些需求的限制,计算据边框距离即可,也可以用小程序的boundingClientRectAPI
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 单指拖拽
  • 双指缩放
  • 总结
相关产品与服务
云开发 CloudBase
云开发(Tencent CloudBase,TCB)是腾讯云提供的云原生一体化开发环境和工具平台,为200万+企业和开发者提供高可用、自动弹性扩缩的后端云服务,可用于云端一体化开发多种端应用(小程序、公众号、Web 应用等),避免了应用开发过程中繁琐的服务器搭建及运维,开发者可以专注于业务逻辑的实现,开发门槛更低,效率更高。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档