移动web知识

时间:2023-03-09 16:09:27
移动web知识

1、像素知识

  px: css pixels,逻辑像素,浏览器使用的抽象单位

  dp,pt:device independent pixels ,设备无关像素

  dpr:devicePixelRatio 设备像素缩放比

  

  计算公司:1px=(dpr)*dpr*dp

2、Viewport

  手机浏览器默认为我们做了两件事。

    一:页面渲染在一个980px(iso)的Viewport。

    二:缩放

  是有 visual Viewport 与 layout viewport.

  最佳meta设置如下:

  <meta name="viewport" content="width=device-width,initial-scale=1,user-scalable=no">

  window.innerWidth/document.body.clientWidth=缩放比

  【布局Viewport】=【设备宽度】=【度量Viewport】

3、Tap基础事件

  自定义Tap事件原理:

  在touchstart、touchend时记录时间、手指位置,在touchend时进行比较,如果手指位置为同一位置(或允许移动一个非常小的位移值),

  且事件间隔较短(一般认为是200ms),且过程中未触发过touchmove,即可认为触发了手持设备的"click",一般称为"tap"。

  Tap透传Bug

  解决方案:

  1、使用缓动动画,过渡300ms延迟。

  2、中间层dom元素的加入,让中间层接受这个“穿透”事件,稍后隐藏。

  3、上下都使用"tap"事件。

四、Touch 基础事件

  touchstart、touchmove、touchend、touchcancel(系统取消touch时触发)。

  Bug:

    Android只会触发一次touchstart,一次touchmove,touchend不触发。

  在 touchmove中加入:event.preventDefault(),但会导致默认行为不发生,比如scroll。

  触摸板上下左右滑动事例:

<style>
.touchpad{
width: %;
height: 200px;
font-size: 40px;
text-align: center;
line-height: 200px;
background: rgba(,,,0.5);
position: relative;
color: #ddd;
} .ball{
display: none;
position: absolute;
width: 25px;
height: 25px;
border-radius: 15px;
background-color: #7AE6FF;
top: ;
left: ;
}
p{
height: 30px;
} </style>
</head>
<body> <p id="desc"></p>
<div id="touchPad" class="touchpad">触摸板</div>
<div id="ball" class="ball"></div> <script src="../js/zepto.js"></script>
<script type="text/javascript">
var touchpad = document.querySelector('#touchPad'),
ball = document.querySelector('#ball'),
desc = document.querySelector('#desc'); //获取touch的点(兼容mouse事件)
var getTouchPos = function(e){
var touches = e.touches;
if(touches && touches[]) {
return { x : touches[].clientX ,
y : touches[].clientY };
}
return { x : e.clientX , y: e.clientY };
} //计算两点之间距离
var getDist = function(p1 , p2){
if(!p1 || !p2) return ;
return Math.sqrt((p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y));
}
//计算两点之间所成角度
var getAngle = function(p1 , p2){
var r = Math.atan2(p2.y - p1.y, p2.x - p1.x);
var a = r * / Math.PI;
return a;
};
//获取swipe的方向
var getSwipeDirection = function(p2,p1){
var dx = p2.x - p1.x;
var dy = -p2.y + p1.y;
var angle = Math.atan2(dy , dx) * / Math.PI; if(angle < && angle > -) return "right";
if(angle >= && angle < ) return "top";
if(angle >= || angle < -) return "left";
if(angle >= - && angle <= -) return "bottom"; } var startEvtHandler = function(e){
var pos = getTouchPos(e);
ball.style.left = pos.x + 'px';
ball.style.top = pos.y + 'px';
ball.style.display = 'block'; var touches = e.touches;
if( !touches || touches.length == ){ //touches为空,代表鼠标点击
point_start = getTouchPos(e);
time_start = Date.now();
}
} var moveEvtHandler = function(e){
var pos = getTouchPos(e);
ball.style.left = pos.x + 'px';
ball.style.top = pos.y + 'px'; point_end = getTouchPos(e);
e.preventDefault();
} //touchend的touches和targetTouches没有对象,只有changeTouches才有
var endEvtHandler = function(e){
ball.style.display = 'none'; var time_end = Date.now(); //距离和时间都符合
if(getDist(point_start,point_end) > SWIPE_DISTANCE && time_start- time_end < SWIPE_TIME){ var dir = getSwipeDirection(point_end,point_start);
touchPad.innerHTML = 'swipe'+dir;
}
} var SWIPE_DISTANCE = ; //移动30px之后才认为swipe事件
var SWIPE_TIME = ; //swipe最大经历时间
var point_start,
point_end,
time_start,
time_end; //判断是PC或者移动设备
var startEvt, moveEvt, endEvt;
if("ontouchstart" in window){
startEvt="touchstart";
moveEvt="touchmove";
endEvt="touchend";
}else{
startEvt="mousedown";
moveEvt="mousemove";
endEvt="mouseup";
} touchpad.addEventListener(startEvt, startEvtHandler);
touchpad.addEventListener(moveEvt, moveEvtHandler);
touchpad.addEventListener(endEvt, endEvtHandler); </script> </body>