首页 > 其他分享 >vue 移动端触屏事件

vue 移动端触屏事件

时间:2023-12-21 14:32:08浏览次数:28  
标签:vue false 端触 binding listener let && 移动 type

事件列表

  • v-tap: tap点击事件
  • v-swipe: swipe滑动事件
  • v-swipeleft: swipeleft左滑事件
  • v-swiperight: swiperight右滑事件
  • v-swipedown: swipedown下滑
  • v-swipeup: swipeup上滑
  • v-longtap: longtap长按

代码

/**
 * vue上点击事件处理类
 */
class VueTouch {
  /**
   * @param el
   * @param binding
   * @param type
   */
  constructor(el, binding, type) {
    let g = this;
    g.obj = el;
    g.binding = binding;
    g.touchType = type;
    g.firstTouchPosition = {x: 0, y: 0};
    g.firstTouchTime = 0;
    g.callBack = typeof(binding.value) === "object" ? binding.value.fn : binding.value;
    g.moved = false;
    g.leaved = false;
    g.longTouched = false;
    // 事件监听回调集合
    let _listener = Object.create(null);
    // 事件方法
    let _listen = (type) => {
      return function (e) {
        let {stop, prevent, self, once} = g.binding.modifiers;
        // 配置判断
        if (stop) e.stopPropagation();
        if (prevent) e.preventDefault();
        if (once) g.obj.removeEventListener("touch" + type, _listener[type]);
        if (self && e.target !== e.currentTarget) return;
        g[type](e);
      }
    };
    _listener.start = _listen('start');
    _listener.end = _listen('end');
    _listener.move = _listen('move');
    this.obj.addEventListener("touchstart", _listener.start, false);
    this.obj.addEventListener("touchend", _listener.end, false);
    this.obj.addEventListener("touchmove", _listener.move, false);
  }
  start(e) {
    let g = this;
    // 初始化点击状态
    g.moved = false;
    g.leaved = false;
    g.longTouched = false;
    g.firstTouchPosition = g.getMultiCenter(e.changedTouches);
    g.firstTouchTime = e.timeStamp;
    g.time = setTimeout(function () {
      if (!g.leaved && !g.moved) {
        g.touchType === "longtap" && g.callBack(e, g.binding.value);
        g.longTouched = true;
      }
    }.bind(g), 1000);
  }
  end(e) {
    let g = this;
    let {x, y} = g.getMultiCenter(e.changedTouches);
    let _disX = x - g.firstTouchPosition.x;
    let _disY = y - g.firstTouchPosition.y;
    let _dis = Math.sqrt(_disX * _disX + _disY * _disY);
    let _timeDis = e.timeStamp - g.firstTouchTime;
    clearTimeout(g.time);
    let _angle = this.getAngle(_disX, _disY);
    if (_dis > 18 && _timeDis < 300) {
      g.touchType === "swipe" && g.callBack(e, g.binding.value);
      if (_angle >= 60 && _angle <= 120)
        g.touchType === "swipedown" && g.callBack(e, g.binding.value);
      if (_angle <= -60 && _angle >= -120)
        g.touchType === "swipeup" && g.callBack(e, g.binding.value);
      if (_angle <= 20 && _angle >= -20)
        g.touchType === "swipeleft" && g.callBack(e, g.binding.value);
      if ((_angle <= -160 && _angle >-180) || (_angle >= 160 && _angle <= 180))
        g.touchType === "swiperight" && g.callBack(e, g.binding.value);
    } else {
      if (!g.longTouched && !g.moved) {
        g.touchType === "tap" && g.callBack(e, g.binding.value);
        g.leaved = true;
      }
    }
  }
  move() {
    this.moved = true;
  }
  /**
   * 获取点击集合的中心坐标
   * @param touches touch对象集合
   * @return {{x: number, y: number}}
   */
  getMultiCenter(touches) {
    let g = this, x = 0, y = 0;
    const _length = touches.length;
    for (let i = 0; i < _length; i++) {
      x += touches[i].pageX;
      y += touches[i].pageY;
    }
    return {
      x: Math.round(x / _length),
      y: Math.round(y / _length)
    };
  };
  getAngle(disX, disY) {
    let g = this;
    if (typeof disX !== 'number' || typeof disY !== 'number')
      return 45;
    return Math.atan2(disY, disX) * 180 / Math.PI;
  }
}
Vue.directive("tap", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "tap");
  }
});
Vue.directive("swipe", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "swipe");
  }
});
Vue.directive("swipeleft", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "swipeleft");
  }
});
Vue.directive("swiperight", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "swiperight");
  }
});
Vue.directive("swipedown", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "swipedown");
  }
});
Vue.directive("swipeup", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "swipeup");
  }
});
Vue.directive("longtap", {
  bind: function (el, binding) {
    new VueTouch(el, binding, "longtap");
  }
});

 


标签:vue,false,端触,binding,listener,let,&&,移动,type
From: https://blog.51cto.com/u_9911196/8923878

相关文章

  • vue上传图片到指定文件夹
    vue代码<template><divclass="app-container"> <divclass="wenben"><el-upload:disabled="dis==0?true:false"class="upload-demo":action="uploadUrl":on-......
  • vue3+vite动态引入图片(import.meta.glob)
    Vite官方提供的 import.meta.glob API。这个方法一般用于批量引入js或者ts文件,但实际上这个方法就是很多import语句的集合而已,import是可以引入图片的,所以import.meta.glob也同样可以引入图片资源,只不过需要加入配置项as:'url'就可以了。 通常来说,我们可以用ES提供的......
  • vue中下载--后端返回的文档流
     实现后端返回的文档流,点击下载<divclass="prom-add"@click="downLoad"><iclass="el-icon-download"></i>下载</div>importrequestfrom'@/router/axios'//下载asyncdownLoad(){letparams={......
  • Vue中动态(import 、require)显示img图片
    vue中,经常会遇到显示图片的问题,如果是一个普通组件的话,那么这样就可以了<imgsrc="../assets/images/avtor.jpg"width="100%">上文的弊端有两个:首先,是采用绝对路径引入。如果以后图片移动了位置,需要修改代码。其次,如果说图片是一个logo图片,同一页面内有多处用到。就需要引用......
  • Vue项目引入图片的两种场景和三种方式
    场景一:public目录下的图片public目录public目录下的图片引入方式:Bash<!--'/images/'+图片名称,这种属于绝对路径,/指向public目录--><imgsrc="/images/image.png"> 场景二:在src目录下的图片src目录 通过import引入图片Bash//第一步:import引入importerrG......
  • Vue基础
    1vue是什么 2谁开发的 3Vue的特点  ......
  • 边做笔试边查缺补漏——算法、js基础、vue3官方文档、八股文
    边投简历边完善自己的知识库。最近这些天一直在面试和笔试+投简历中,每次面试或笔试完后其实最重要的不是结果,而是做题的过程或者说对话的过程。因为只有这些才让我知道自己哪里还有不足,比如一碰到算法题就歇菜、vue3和vue2混用、js基础知识不牢固等等。那我痛定思痛,有缺点咱就认......
  • vue vue3 jsx tsx
    0.安装插件(@vitejs/plugin-vue-jsx)vite官方提供了官方的插件来支持在vue3中使用jsx/tsx,直接安装就行。yarn add @vitejs/plugin-vue-jsx -D安装完之后在vite.config.ts中插入一下代码import vueJsx from "@vitejs/plugin-vue-jsx";export default defineConfig({......
  • Vue3
    1、ref和reactive原来reactive是一个对象类型,使用reactive重新赋值一个对象不起作用<scriptlang="ts"setup>import{reactive}from"vue";letuser=reactive({name:'小明',age:10});constdj=()=>{user={name:'大白',age:1......
  • vue3 静态配置文件
    前言有时候我们负责做的只是一个大平台系统下的某个子系统,有时候我们需要调用这个大平台系统下别的子系统的接口。如果直接把别的接口地址,直接写在代码里,那么如果别的子系统的接口调整了,会影响到我们的系统,我们还要重新打包,部署,会很繁琐。解决思路我们的想法是这样:敲代码的......