一、觸屏事件
在移動端,瀏覽器具有良好的兼容性,所以原生 js 的書寫效果可以在移動端使用,我們知道移動端最大的特點就是 可以直接用手指觸發事件,因此就需要用到觸屏事件,
touch物件是一個觸摸點,這個觸摸點可以是一個手指,也可以是觸摸筆,觸屏事件可以回應用戶手指或者觸摸筆對螢屏或者觸控板的操作,
觸屏事件包括以下三種:
- touchstart:手指觸摸到DOM元素上時觸發
- touchmove:手指在DOM元素上滑動時觸發
- touchend:手指從DOM元素上離開時觸發
二、觸屏事件(touchEvent)物件
這是一類描述手指在觸摸平面(螢屏、觸摸板等)狀態變化的事件,這類事件用于描述一個或多個觸點,使得開發者更容易檢測觸點的移動、增加、減少等,
- touches:正在觸摸螢屏的所有手指的一個串列
- targetTouches:正在觸摸當前 DOM 元素手指的一個串列
- changedTouches:手指狀態發生了改變的的串列,從無到有,從有到無的變化
<body>
<div></div>
<script>
var div = document.querySelector('div');
div.addEventListener('touchstart', function(e) {
console.log('我被摸了');
// touches 正在觸摸螢屏的所有手指串列
console.log(e);
// targetTouches正在觸摸當前DOM元素的手指串列 最常用
// 如果監聽的是一個DOM元素 則他們兩個是一樣的
// changedTouches 手指狀態發生了改變的串列 從有到無 從無到有
console.log(e.targetTouches[0]);
// 上面得到的是當前正在觸摸元素的第一個手指資訊,包括觸摸點距離頁面的坐標、距離螢屏的坐標等
});
div.addEventListener('touchmove', function() {
console.log('手指在盒子上移動');
});
div.addEventListener('touchend', function(e) {
console.log(e);
// 當手指離開螢屏的時候,就沒有touches 和 targetTouches 但是會有 changedTouches
})
</script>
</body>


手指離開時觸發 touchend的事件

三、常見特效
以前做過開關燈的案例,如下:
<body>
<button id="btn">開關</button>
<script>
var btn = document.getElementById('btn');
var body = document.querySelector('body');
var flag = false;
btn.onclick = function() {
if (flag === false) {
body.style.backgroundColor = 'black';
flag = true;
} else {
body.style.backgroundColor = 'white';
flag = false;
}
}
</script>
</body>
當滑鼠點擊開關后,頁面背景顏色由白色變為黑色,或者由黑色變為白色,實作一種開關燈的效果,在這里需要用到一個變數 flag 來判斷當前元素是否有這個屬性或類,實作回圈點擊改變背景顏色的效果,顯然這樣做代碼比較多,移動端就使用了 classList 屬性,方便的實作屬性的添加( element.classList.add() )、移除( element.classList.remove() )、切換( element.classList.toggle() 如果有這個類就洗掉,如果沒有這個類就添加),
下面利用classList屬性實作開關燈和添加、移除某個類名:
<body>
<div class="one two"></div>
<button>開關燈</button>
<script>
// classList 回傳元素的類名
var div = document.querySelector('div');
var btn = document.querySelector('button');
console.log(div.classList[1]);
// 1.添加類名 實在后面追加類名,不會覆寫原來的類名 前面不需要加 .
div.classList.add('three');
// console.log(div.classList);
// 2.移除某個類名
// div.classList.remove('one');
// 3.切換類 如果有這個類就洗掉 沒有就添加
btn.addEventListener('click', function() {
document.body.classList.toggle('bg');
// .bg 這個類的樣式已經寫在<style></style>標簽內
});
</script>
</body>


四、拖動元素
- 拖動原理:手指在螢屏上移動程序中,計算手指移動的距離,元素最終位置 = 元素的初始位置 + 手指移動的距離
- 這里需要用到 觸屏事件 touchstart、touchmove、touchend
拖動元素需要知道元素的坐標,因此要用到觸屏事件物件中的 targetTouches[0]中的pageX,pageY - 手指移動距離 = 手指現在的位置 - 手指之前的位置
- 拖動三部曲:
觸摸元素 touchstart: 獲取手指初始坐標,同時獲得盒子原來的位置
移動手指 touchmove: 計算手指移動的距離,并移動盒子
手指離開 touchend
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>移動端拖動元素</title>
<style>
div {
position: absolute;
top: 0;
left: 0;
width: 200px;
height: 200px;
background-color: pink;
}
</style>
</head>
<body>
<div></div>
// 手指移動會觸發滾動螢屏,所以要阻止默認滾動螢屏e.preventDefault()
<script>
var div = document.querySelector('div');
// 定義全域變數
var startX = 0; // 手指的初始坐標
var startY = 0;
var x = 0; // 盒子的初始坐標
var y = 0;
div.addEventListener('touchstart', function(e) {
// 獲取手指的初始坐標
startX = e.targetTouches[0].pageX;
startY = e.targetTouches[0].pageY;
// 獲取盒子的初始坐標
x = this.offsetLeft;
y = this.offsetTop;
});
div.addEventListener('touchmove', function(e) {
// 手指移動的距離 = 手指現在的位置 - 手指原來的位置
var moveX = e.targetTouches[0].pageX - startX;
var moveY = e.targetTouches[0].pageY - startY;
// 盒子移動的距離 = 盒子原來的位置 + 手指移動的距離
// 盒子加了定位 就通過修改 left 和 top 值進行移動
this.style.left = x + moveX + 'px';
this.style.top = y + moveY + 'px';
e.preventDefault();
});
</script>
</body>
</html>


五、點擊延時300ms問題解決方案
原因:移動端與WEB端不同,移動端瀏覽網站頁面時可能會比較小,看不清,這時用戶就會用手指放大頁面,瀏覽完成以后在螢屏被雙擊(double tap to zoom)就可以縮放頁面,因此在手指點擊螢屏一次時,內部程式會等待 300ms ,看是否在這段時間之內還有下一次點擊,這就導致了點擊一次會有延時效果,
解決方案
- 禁用縮放:瀏覽器禁用默認的雙擊行為就可以去掉延時,利用視口標簽設定禁止用戶縮放屬性
<meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=no, minimum-scale=1.0, maximum-scale=1.0" /> - 利用touch事件封裝(簡單理解即可)
原理:①當手指觸摸螢屏時,記錄當前時間
②當手指離開時,用離開時間 - 觸屏時間
③如果上面的計算結果小于150ms 并且沒有滑動螢屏則視為點擊事件
//封裝一個函式
function tap(obj, callback) {
var isMove = false;
var startTime = 0; // 記錄觸摸時的時間變數
obj.addEventListener('touchstart', function(e) {
startTime = Date.now(); //記錄觸摸時間
});
obj.addEventListener('touchmove', function(e) {
isMove = true;
// 看是否滑動 如果滑動就不是點擊事件
});
obj.addEventListener('touchend', function(e) {
// 沒有滑動 并且 時間差小于 150ms 則視為點擊事件
if(!isMove && (Date.now() - startTime) < 150){
callback && callback(); // 執行回呼函式
}
isMove = false; // 取反 重置
startTime = 0;
});
}
// 呼叫
tap(div, function() {
// 這里放執行代碼
});
- 使用 fastclick 插件解決(最常用)
在網上找到這個插件下載,然后在代碼中參考做適當修改即可,地址:https://github.com/ftlabs/fastclick
六、本地存盤
本地存盤的特性:
① 資料存盤在用戶瀏覽器中
② 設定讀取方便,甚至頁面重繪也不會丟失資料
③ 容量較大,window.sessionStorage 5M 左右
window.loginStorage 20M左右
window.sessionStorage
特性:
① 生命周期到關閉瀏覽器視窗為止
② 在同一個視窗或頁面下資料可以共享
③ 資料以鍵值對的形式存盤使用
存盤資料的方法:
sessionStorage.setItem(key, value)
獲取資料的方法:
sessionStorage.getItem(key)
洗掉資料的方法:
sessionStorage.removeItem(key)
清除所有資料的方法:
sessionStorage.clear()
window.loginStorage
特性:
① 生命周期永久生效,除非手動洗掉,否則關閉頁面也會存在
② 可以多個視窗或頁面共享,同一個瀏覽器也可以共享
③ 以鍵值對的形式存盤資料
存盤資料、獲取資料、洗掉資料的方法類似window.sessionStorage,這里不再贅述,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/273250.html
標籤:其他
上一篇:微信小程式商品詳情頁面開發案例(歡迎關注大白菜程式猿)
下一篇:個人簡歷
