zoukankan      html  css  js  c++  java
  • 微信小程序实现手指缩放移动图片

    微信小程序实现手指缩放移动图片

    实现方式一:view子元素缩放、移动

    通过监听父view的touch事件,单指touch move用于移动,双指touch move则用于缩放,通过transform:translate进行移动、transform:scale进行缩放。

    • wxml:
    <!--scale.wxml-->
    <view class="container">
      <view class="tip">
        <text>view子元素缩放、移动 </text>
        <text>说明:双指缩放开发工具上并不支持,需要在真机上进行。 </text>
      </view>
      <view class="img" catchtouchstart="touchstartCallback"  catchtouchmove="touchmoveCallback" catchtouchend="touchendCallback"  >
        <image style="transform:translate({{stv.offsetX}}px, {{stv.offsetY}}px) scale({{stv.scale}});" src="../../images/timg.jpeg"></image>
      </view>
    
      <view>
        <text>x: {{stv.offsetX}}</text>, 
        <text>y: {{stv.offsetY}}</text>, 
        <text>d: {{stv.distance}}</text>, 
        <text>s: {{stv.scale}}</text>, 
      </view>
    </view>
    
    • wxss:
    /**scale.wxss**/
    .img {
       100%;
      height: 500rpx;
      overflow: hidden;
      background: #AAA;
    }
    .img image {
      height:400px;
    }
    
    • js:
    //scale.js
    //获取应用实例
    var app = getApp()
    Page({
      data: {
        stv: {
          offsetX: 0,
          offsetY: 0,
          zoom: false, //是否缩放状态
          distance: 0,  //两指距离
          scale: 1,  //缩放倍数
        }
      },
      //事件处理函数
      touchstartCallback: function(e) {
        //触摸开始
        console.log('touchstartCallback');
        console.log(e);
    
        if (e.touches.length === 1) {
          let {clientX, clientY} = e.touches[0];
          this.startX = clientX;
          this.startY = clientY;
          this.touchStartEvent = e.touches;
        } else {
          let xMove = e.touches[1].clientX - e.touches[0].clientX;
          let yMove = e.touches[1].clientY - e.touches[0].clientY;
          let distance = Math.sqrt(xMove * xMove + yMove * yMove);
          this.setData({
            'stv.distance': distance,
            'stv.zoom': true, //缩放状态
          })
        }
    
      },
      touchmoveCallback: function(e) {
        //触摸移动中
        //console.log('touchmoveCallback');
        //console.log(e);
    
        if (e.touches.length === 1) {
          //单指移动
          if (this.data.stv.zoom) {
            //缩放状态,不处理单指
            return ;
          }
          let {clientX, clientY} = e.touches[0];
          let offsetX = clientX - this.startX;
          let offsetY = clientY- this.startY;
          this.startX = clientX;
          this.startY = clientY;
          let {stv} = this.data;
          stv.offsetX += offsetX;
          stv.offsetY += offsetY;
          stv.offsetLeftX = -stv.offsetX;
          stv.offsetLeftY = -stv.offsetLeftY;
          this.setData({
            stv: stv
          });
    
        } else {
          //双指缩放
          let xMove = e.touches[1].clientX - e.touches[0].clientX;
          let yMove = e.touches[1].clientY - e.touches[0].clientY;
          let distance = Math.sqrt(xMove * xMove + yMove * yMove);
    
          let distanceDiff = distance - this.data.stv.distance;
          let newScale = this.data.stv.scale + 0.005 * distanceDiff;
    
          this.setData({
            'stv.distance': distance,
            'stv.scale': newScale,
          })
        }
    
      },
      touchendCallback: function(e) {
        //触摸结束
        console.log('touchendCallback');
        console.log(e);
    
        if (e.touches.length === 0) {
          this.setData({
            'stv.zoom': false, //重置缩放状态
          })
        }
      },
      onLoad: function () {
        console.log('onLoad');
      }
    })
    

    实现方式二:scroll-view子元素缩放

    通过监听父scroll-view的touch事件,计算出两指的距离,缩放用的是css zoom来进行的,因为transform:scale的缩放不能改变box的大小,对于scroll-view来说就会产生问题。但是用zoom有一个问题就是缩放基点是按左上角进行的, 体验不是很好。

    • wxml:
    <!--scale.wxml-->
    <view class="container">
      <view class="tip">
        <text>scroll-view子元素缩放</text>
        <text>说明:双指缩放开发工具上并不支持,需要在真机上进行。 </text>
      </view>
    
      <scroll-view class="img" bindtouchstart="touchstartCallback"  bindtouchmove="touchmoveCallback" bindtouchend="touchendCallback" scroll-x="true"  scroll-y="true" >
          <image style="zoom:{{stv.scale}};" src="../../images/timg.jpeg"></image>
      </scroll-view>
    
      <view>
        <text>x: {{stv.offsetX}}</text>, 
        <text>y: {{stv.offsetY}}</text>, 
        <text>d: {{stv.distance}}</text>, 
        <text>s: {{stv.scale}}</text>, 
      </view>
    </view>
    
    • wxss:
    /**scale.wxss**/
    .img {
       100%;
      height: 500rpx;
      background: #AAA;
      text-align: center;
    }
    .img image {
      height: 800rpx;
       600rpx;
    }
    
    • js:
    //scale.js
    //获取应用实例
    var app = getApp()
    Page({
      data: {
        stv: {
          offsetX: 0,
          offsetY: 0,
          zoom: false, //是否缩放状态
          distance: 0,  //两指距离
          scale: 1,  //缩放倍数
        }
      },
      //事件处理函数
      touchstartCallback: function(e) {
        //触摸开始
        console.log('touchstartCallback');
        console.log(e);
    
        if (e.touches.length === 1) {
          let {clientX, clientY} = e.touches[0];
          this.startX = clientX;
          this.startY = clientY;
          this.touchStartEvent = e.touches;
        } else {
          let xMove = e.touches[1].clientX - e.touches[0].clientX;
          let yMove = e.touches[1].clientY - e.touches[0].clientY;
          let distance = Math.sqrt(xMove * xMove + yMove * yMove);
          this.setData({
            'stv.distance': distance,
            'stv.zoom': true, //缩放状态
          })
        }
    
      },
      touchmoveCallback: function(e) {
        //触摸移动中
        console.log('touchmoveCallback');
        console.log(e);
    
        if (e.touches.length === 1) {
          //单指移动
          if (this.data.stv.zoom) {
            //缩放状态,不处理单指
            return ;
          }
          let {clientX, clientY} = e.touches[0];
          let offsetX = clientX - this.startX;
          let offsetY = clientY- this.startY;
          this.startX = clientX;
          this.startY = clientY;
          let {stv} = this.data;
          stv.offsetX += offsetX;
          stv.offsetY += offsetY;
          stv.offsetLeftX = -stv.offsetX;
          stv.offsetLeftY = -stv.offsetLeftY;
          this.setData({
            stv: stv
          });
    
        } else {
          //双指缩放
          let xMove = e.touches[1].clientX - e.touches[0].clientX;
          let yMove = e.touches[1].clientY - e.touches[0].clientY;
          let distance = Math.sqrt(xMove * xMove + yMove * yMove);
    
          let distanceDiff = distance - this.data.stv.distance;
          let newScale = this.data.stv.scale + 0.005 * distanceDiff;
    
          this.setData({
            'stv.distance': distance,
            'stv.scale': newScale,
          })
        }
    
      },
      touchendCallback: function(e) {
        //触摸结束
        console.log('touchendCallback');
        console.log(e);
    
        if (e.touches.length === 0) {
          this.setData({
            'stv.zoom': false, //重置缩放状态
          })
        }
      },
      onLoad: function () {
        console.log('onLoad');
      }
    })
    
  • 相关阅读:
    Linux下rabitMq的部署(源码安装)
    yum安装时出现:Cannot retrieve metalink for repository: epel. Please verify its path and try again
    性能实战分析-问题分析(三)
    当前服务器的并发连接数查看
    性能实战分析-问题分析(二)
    数据库中文乱码及分析
    HDU 4857 逃生 (优先队列+反向拓扑)
    HNU 12826 Balloons Colors
    HNU 12827 NASSA’s Robot
    HNU 12812 Broken Audio Signal
  • 原文地址:https://www.cnblogs.com/cnsyear/p/12732106.html
Copyright © 2011-2022 走看看