利用translate封装移动端滑屏效果(缓冲动画/滚动条)

责编:menVScode 2018-04-12 0:05 阅读(578)

具体滑屏布局,css样式可以查看此篇文章:http://menvscode.com/detail/5ace2f814f66b879b92af410

js代码

function mScroll(init){
	if(!init.el){
		return false;
	}
	var wrap = document.querySelector(init.el);
	var inner = wrap.children[0];
	var scrollBar = document.createElement("div");
	var startPoint = 0; // 初始化手指按下的坐标 pageY
	var startEl = 0; // 初始化滑动元素的坐标 pageY
	var lastY = 0; // 初始化上次按下的坐标
	var lastTime = 0; // 初始化上次按下的坐标 的时间
	var lastDis = 0; // 手指移动最后抬起的pageY - 上次按下的坐标pageY = 最后一次移动的距离
	var lastTimeDis = 0; // 两者距离的时间差
	var maxTranslate = wrap.clientHeight-inner.offsetHeight;

	if(init.scrollBar){ // 判断是否需要滚动条
		var scale = wrap.clientHeight/inner.offsetHeight;
		inner.style.minHeight = '100%';
		scrollBar.style.cssText = "width:6px;height:50px;background:rgba(0,0,0,.5);position:absolute;right:0;top:0;border-radius:3px;opacity:0;transition:.3s opacity;";
		wrap.appendChild(scrollBar);
	}

	css(inner,"translateZ",0.01);
	inner.addEventListener('touchstart', function(e) {
		maxTranslate = wrap.clientHeight-inner.offsetHeight;

		if(init.scrollBar){ 
			if(maxTranslate>=0){
				scrollBar.style.display = 'none'; 
			}else{
				scrollBar.style.display = 'block'; 
			}
			scale = wrap.clientHeight/inner.offsetHeight;
			scrollBar.style.height = scale*wrap.clientHeight+'px';

			scrollBar.style.opacity = 1;
		}

		clearInterval(inner.timer); //按下禁止滚动
		startPoint = e.changedTouches[0].pageY;
		startEl = css(inner,"translateY");
		lastY = startEl;
		lastTime = new Date().getTime();
		lastDis = lastTimeDis = 0;
	});
	inner.addEventListener('touchmove', function(e) {
		var nowTime = new Date().getTime();
		var nowPoint = e.changedTouches[0].pageY;
		var dis = nowPoint - startPoint;
		var translateY = startEl + dis;
		css(inner,"translateY",translateY);

		if(init.scrollBar){
			css(scrollBar,"translateY",-translateY*scale);
		}

		lastDis = translateY - lastY;
		//console.log(translateY+'-'+lastY)
		lastY = translateY;
		lastTimeDis = nowTime - lastTime;
		lastTime = nowTime;
	});
	inner.addEventListener('touchend',function(e){
		//console.log(lastDis,lastTimeDis)
		var type = "easeOutStrong";
		var speed = Math.round(lastDis / lastTimeDis * 10);
		speed = lastTimeDis <=0 ? 0 : speed;
		var target = Math.round(speed*20+css(inner,"translateY"));
		//console.log(speed)
		//console.log(target)
		if(target > 0){
			target = 0
			type = "backOut";
		}else if(target<maxTranslate){
			target = maxTranslate
			type = "backOut";
		}

		MTween({
			el:inner,
			target:{translateY:target},
			time:500,
			// time: Math.round(Math.abs(target - css(inner,"translateY"))*2),
			type:type,
			callBack:function(){
				if(init.scrollBar){ scrollBar.style.opacity = 0; }
			},
			callIn:function(){
				if(init.scrollBar){ 
					var translateY = css(inner,"translateY");
					css(scrollBar,"translateY",-translateY*scale);
				}
			}
		})
	});
}

调用效果方法

mScroll({
    el:"#wrap",
    scrollBar:true
})

滑屏效果

GIF

前端交流群: MVC前端网(menvscode.com)-qq交流群:551903636

邮箱快速注册

忘记密码