日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

H5多点触控原理以及对多点触控的追踪

發布時間:2023/12/16 编程问答 52 豆豆
生活随笔 收集整理的這篇文章主要介紹了 H5多点触控原理以及对多点触控的追踪 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

文章目錄

      • 接觸點類Touch
      • 觸摸事件
      • 接觸點的生命周期類
      • 多點觸控的追蹤器
      • 拋磚引玉

對于PC端,我們的點擊事件比較簡單,因為鼠標指針只有一個。

但是對于移動端來說,存在多個接觸點同時操作的情況,這種情況就是我們今天要研究的主題 – 多點觸控。

接觸點類Touch

移動端的任何觸摸都會觸發一個事件,該事件會攜帶一個touchList列表來表示:當前有哪些接觸點正在作用于我們的屏幕。

通俗點的解釋,接觸點可以理解為你的手指,touchList列表就代表了當前總共有幾個手指正在與屏幕接觸。

而touchList列表中的每一項都是Touch類的對象,它包含了我們手指與屏幕接觸的必要信息:接觸點的位置、壓力大小、接觸面積等等。

所以,在介紹之前,我們必須要先了解這個類。它代表的是屏幕上接觸的點。具體屬性值如下:

// Touch類 屬性說明// 接觸點的唯一標識,每個接觸點的id在接觸過程中都是唯一的,即每個手指都會分配一個id `identifier` // 接觸點的位置信息,這幾個屬性與pc端是一樣的 `clientX:0` `clientY:0` `pageX:0` `pageY:0` `screenX:0` `screenY:0`// 接觸點的壓力值大小 0.0-1.0之間 `force:0`// 這三個參數指示了包含接觸點的最小橢圓 `radiusX:0` //橢圓x軸長 `radiusY:0` //橢圓y軸長 `rotationAngle:0` // 橢圓旋轉角度// 接觸點接觸的HTML對象 `target:DocumentHTMLDom`

讀者朋友可以看出來,上面這個類,準確的定義了一個接觸點的各種屬性。那么,在哪才能得到這些接觸點的對象呢?

聰明如你,估計已經猜到了,那就是在觸摸事件中。

注意屬性中的identifier哦~非常重要!

觸摸事件

上面也提到了,Touch類只會存在于觸摸事件里。常用的觸摸事件有touchestart、touchmove、touchend、touchcacel。

它們都是TouchEvent類的實例,TouchEvent類的屬性包含了前面介紹的接觸點Touch實例列表。我們主要關注它的三個屬性即可,如下:

  • TouchEvent.changedTouches
    這是一個只讀屬性,是一個TouchList對象,它包含了代表所有從上一次觸摸事件到此次事件過程中,狀態發生了改變的觸點的 Touch 對象。

  • TouchEvent.touches
    這是一個只讀屬性,是一個TouchList對象,它包含了所有當前正在接觸的接觸點Touch對象,無論它們的起始于哪個element上,也無論它們狀態是否發生了變化。

  • TouchEvent.targetTouches
    這是一個只讀屬性,是一個TouchList對象,它包含了如下觸點的 Touch 對象:觸摸起始于當前事件的目標 element 上,并且仍然沒有離開觸摸平面的觸點。

  • 完整的屬性列表,可以參考MDN文檔,https://developer.mozilla.org/zh-CN/docs/Web/API/TouchEvent。

    對于手勢庫來說,這幾個TouchList屬性已經夠用了。

    接觸點的生命周期類

    想一想我們一個手指在屏幕上滑動的過程:開始接觸 -> 接觸時的移動 -> 接觸結束。

    這實際上就是一個接觸點的生命周期,我們來為這一過程定義一個數據結構吧。

    /*** touch事件的生命周期類* @constructor* */ var TouchLife = (function () {var id = 0;return function () {/*** 生命周期的id* @type {number}* */this.id=id++;/*** 開始的touch事件* @type {Touch}* */this.startTouchEvent = null;/*** 結束的touch事件* @type {Touch}* */this.endTouchEvent = null;/*** 移動的touch事件* @type {Touch[]}* */this.moveTouchEventList = [];}; })();

    生命周期的開始和結束都只需要一個Touch對象,而移動可以多次移動,需要一個TouchList來保存。

    另外附加了一個生命周期的ID,用來唯一標識一次生命周期。

    多點觸控的追蹤器

    有了接觸點的生命周期,我們還需要一個追蹤器,用來追蹤多個接觸點的生命周期。

    試想一下,對于PC,只有一個鼠標指針,我們能很好的記錄它的運行軌跡。

    但是對于移動端,當存在多個接觸點同時作用于屏幕時,怎么來記錄他們的運行軌跡呢?

    這就是追蹤器的主要功能:記錄接觸點的運行軌跡

    除此之外,在某個生命周期狀態變化的時候,追蹤器應該能通知應用程序做處理。

    這里直接給出它的實現:

    /*** touch事件追蹤器* @param opt* @param opt.target 被追蹤的dom對象* @constructor*/ function TouchLifeTracer(opt) {/*** 追蹤的對象* */this.target = opt.target;/*** 作用于target的所有生命周期,包含存活和死亡的周期* */this._lifeList = [];/*** 當前存活的生命周期,正在與target接觸的觸摸點生命周期* */this.currentLifeList = [];/*** 某個生命周期開始* @type {function}* @param callback(life)* */this.onlifestart = null;/*** 某個生命周期狀態變更* @type {function}* @param callback(life)* */this.onlifechange = null;/*** 某個生命周期開始* @type {function}* @param callback(life)* */this.onlifeend = null;/*** 添加生命周期* @param life {TouchLife} 生命周期* @return {*}*/this.addLife = function (life) {this._lifeList.push(life);};/*** 根據identifier查找生命周期,此方法只能在生命周期內使用* @param identifier* @return {*}*/this.findCurrentLifeByTouchID = function (identifier) {for(var i=0;i<this.currentLifeList.length;i++){var life = this.currentLifeList[i];if(life.startTouchEvent.identifier===identifier)return life;}};/*** 根據touchID刪除當前觸摸的生命周期* @param identifier* @return {boolean}*/this.deleteCurrentLifeByTouchID = function (identifier) {for(var i=0;i<this.currentLifeList.length;i++){var life = this.currentLifeList[i];if(life.startTouchEvent.identifier===identifier){this.currentLifeList.splice(i,1);return true;}}return false;};/*** 初始化*/this.init = function () {var self = this;this.target.addEventListener("touchstart",function (e) {e.preventDefault();var touchLife = new TouchLife();touchLife.startTouchEvent = e.changedTouches[0];self.addLife(touchLife);self.currentLifeList.push(touchLife);self.onlifestart && self.onlifestart(life);});this.target.addEventListener('touchmove',function (e) {e.preventDefault();var touches = e.changedTouches;for(var i=0;i<touches.length;i++){var touch = touches[i];var life = self.findCurrentLifeByTouchID(touch.identifier);life.moveTouchEventList.push(touch);self.onlifechange && self.onlifechange(life);}});this.target.addEventListener('touchend',function (e) {e.preventDefault();var touch = e.changedTouches[0];var life = self.findCurrentLifeByTouchID(touch.identifier);life.endTouchEvent = touch;self.deleteCurrentLifeByTouchID(touch.identifier);self.onlifeend && self.onlifeend(life);});};this.init(); }

    上面這個算是最簡單的追蹤器了,它僅僅包含了最基本的屬性和方法。包括:

    • 幾個必要的屬性:追蹤器作用的對象、存活的生命周期、全部生命周期。
    • 幾個必要的方法:新增生命周期、刪除生命周期、查找生命周期、追蹤器的初始化。
    • 幾個必要的事件:生命周期的開始、生命周期的變化、生命周期的結束。

    存活的生命周期,對應于我們正在接觸屏幕的手指。

    而全部生命周期,對應于我們所有接觸屏幕的歷史記錄。

    有了這個追蹤器,我們在監控多點觸控的時候,就相當的方便了。比如:

    // 獲取元素 var a1 = document.getElementById('canvasID');// 初始化 var tracer = new TouchLifeTracer({target:a1}); tracer.onlifestart = function (life) {//todo with life startconsole.log('檢測到一個新的接觸點觸摸元素'); }; tracer.onlifeend = function (life) {//todo with life endconsole.log('檢測到一個接觸點離開元素'); };

    拋磚引玉

    有了這個追蹤器,是不是就可以自己擼一個手勢庫出來了呢?答案是肯定的。

    手勢庫的原理,也就是多點觸控+手勢的判斷條件,僅此而已!

    百度搜手勢庫比較靠前的,比如Hammer.js,比如AlloyFinger,這些庫都是基于這兩點基礎知識來對手勢進行模擬的。

    始終相信,別人能做到的,我們也能做到!

    那么,下篇文章我們就來真正的實現一個手勢庫,敬請期待!

    覺得有用,還請點贊收藏!
    勵志前端,CSDN唯一賬號!關注我,帶你了解更多前端知識!

    總結

    以上是生活随笔為你收集整理的H5多点触控原理以及对多点触控的追踪的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。