- touch事件与点击穿透问题
https://segmentfault.com/a/1190000003848737
解决- 遮挡:
由于 click 事件的滞后性,在这段时间内原来点击的元素消失了,于是便“穿透”了。因此我们顺着这个思路就想到,可以给元素的消失做一个fade效果,类似jQuery里的
fadeOut
,并设置动画duration大于300ms,这样当延迟的 click 触发时,就不会“穿透”到下方的元素了。同样的道理,不用延时动画,我们还可以动态地在触摸位置生成一个透明的元素,这样当上层元素消失而延迟的click来到时,它点击到的是那个透明的元素,也不会“穿透”到底下。在一定的timeout后再将生成的透明元素移除
-
pointer-events
pointer-events
是CSS3中的属性,它有很多取值,有用的主要是auto
和none
,其他属性值为SVG服务。取值 含义 auto 效果和没有定义 pointer-events 属性相同,鼠标不会穿透当前层。 none 元素不再是鼠标事件的目标,鼠标不再监听当前层而去监听下面的层中的元素。但是如果它的子元素设置了pointer-events为其它值,比如auto,鼠标还是会监听这个子元素的。 关于使用 pointer-events 后的事件冒泡,有人做了个实验,见代码
因此解决“穿透”的办法就很简单,demo如下
$('#closePopup').on('tap', function(e){ $('#popupLayer').hide(); $('#bgMask').hide(); $('#underLayer').css('pointer-events', 'none'); setTimeout(function(){ $('#underLayer').css('pointer-events', 'auto'); }, 400); });
-
fastclick
使用fastclick库,其实现思路是,取消 click 事件(参看源码 164-173 行),用 touchend 模拟快速点击行为(参看源码 521-610 行)。
FastClick.attach(document.body);
从此所有点击事件都使用
click
,不会出现“穿透”的问题,并且没有300ms的延迟。解决穿透的demo有人(叶小钗)对事件机制做了详细的剖析,循循善诱,并剖析了fastclick的源码以自己模拟事件的创建。请看这篇文章,看完后一定会对移动端的事件有更深的了解
- 遮挡:
- 页面后台执行时,动画累积 计时器累积 停滞 叠加:
百度说PC没问题,但见过PC页也有这种情况的。解决: 页面不可见时清除动画,页面可见时重新启动动画。-
// 页面的 visibility 属性可能返回三种状态
-
// prerender,visible 和 hidden
-
let pageVisibility = document.visibilityState;
-
-
// 监听 visibility change 事件
-
document.addEventListener('visibilitychange', function() {
// 页面变为不可见时触发
if (document.visibilityState == 'hidden') { ... }
-
-
// 页面变为可见时触发
-
if (document.visibilityState == 'visible') { ... }
-
})
VisibilityChange 事件 : 页面的可见状态发生变化时,会触发
VisibilityChange
事件。-
document.addEventListener('visibilitychange', function () {
-
console.log(document.visibilityState);
-
});
-
3. 跨域请求不会自动带cookie,需要在设置ajax时加上以下参数:
xhrFields: {
withCredentials: true
},
crossDomain: true,
4. 简单请求/非简单请求:简单请求就是使用设定的请求方式请求数据 而非简单请求则是在使用设定的请求方式请求数据之前,先发送一个OPTIONS请求,看服务端是否允许客户端发送非简单请求. 只有"预检"通过后才会再发送一次请求用于数据传输
简单请求:同时满足一下两个条件:
- 方法为: HEAD、GET、POST
- 无自定义头且Content-Type:是以下三值: application/x-www-form-urlencoded 、 multipart/form-data、text/plain
非简单请求:
- put/delete的ajax请求
- 发送json格式的请求
- 带自定义头的ajax请求
5.CORS: 后端设置
res.header("Access-Control-Allow-Origin","*");
res.header("Access-Control-Allow-Methods","PUT,POST,GET,DELETE,OPTIONS");
6. new Date时 如果参数是 yyyy-mm-dd的格式,那么会被当成UTC时区,也就是+8h, 每次new出来都是八点。
可以使用yyyy/mm/dd格式
7.数组的reduce:
方法接收一个函数作为累加器(accumulator),数组中的每个值(从左到右)开始缩减,最终为一个值。
arr.reduce(callback,[initialValue])
-
callback (执行数组中每个值的函数,包含四个参数)
- previousValue (上一次调用回调返回的值,或者是提供的初始值(initialValue))
- currentValue (数组中当前被处理的元素)
- index (当前元素在数组中的索引)
- array (调用 reduce 的数组)
- initialValue (作为第一次调用 callback 的第一个参数,即第一个参数的初始值)
- 进阶应用: 目标对象多个属性的同时叠加(减等等)和目标对象属性的多种处理。
-
let reducers = { totalPrice: function(count, item) { return count.totalPrice += item.pice; }, averPrice: function(count, item, index) { return count.averPrice = count.totalPrice / (index + 1); }, quantity: function(count, item) { return count.quantity += item.quantity; } }; let bindReducers = function(reducers) { return function(count, item, index) { return Object.keys(reducers).reduce(function(pre, key){ //这里的reduce是for循环的作用,计算count的每个属性, 循环结束后返回这次item计算出的count //因为没有用到上一个的返回值,所以1可以随便传 reducers[key](count, item, index); return count; },1); } }; let countReducers = bindReducers(reducers); let initCount = {totalPrice: 0, averPrice: 0, quantity: 0}; let items = [{pice: 10, quantity: 20},{pice: 20, quantity: 30},{pice: 30, quantity: 40}]; let result = items.reduce(countReducers, initCount); console.log(result, initCount); //因为是对initCount直接进行了更改所以没必要另取返回值
8. 判断文字是否超出:
scrollHeight: 是实际高度
clientHeight:是展示的高度
如果不一样,说明有部分被隐藏掉了
9.hybrid ios禁止橡皮筋效果
document.body.addEventListener('touchmove', function (e) {
e.preventDefault(); //阻止默认的处理方式(阻止下拉滑动的效果)
}, {passive: false});
10./\.jsx?$/ 能匹配js和jsx两种后缀