移动web Javascript框架
之前做为联想打印机官网做移动端的页面,由于之前没多少经验,好不容易搞定了,一直没整理,比较杂乱,抽空整理了下。准备弄成一份框架,以后有新东西可以在这个基础上添加。
模拟日常智能机的app交互。
尚未完善,持续更新。
html部分:
<!doctype html> <html> <head> <script type="text/javascript" src="js/scroll.js"></script> <link href="css/common.css" rel="stylesheet"/> <meta charset="utf-8"/> <meta name="viewport" content="width=device-width; minimum-scale=1.0; maximum-scale=1" /> <title>手机demo</title> </head> <body> <div class="wrap" id="wrap"> <div class="wrap_pos" id="wrap_pos" style="top:0px;left:0px;"> <div class="page"> <div class="pageInner" style="background: #ccc;top:0px;left:0px;"> <p>容一内容一内容一</p> <p> 容一内容一内容一</p> <p> 内内容一内容一内容一</p> <p> 内容一内容一内容一内容一</p> <p> 内容一内容一容一内容一内容一</p> <p> 内容一内容一一内容一内容一</p> <p>容一内容一内容一</p> <p> 容一内容一内容一</p> <p> 内内容一内容一内容一</p> <p> 内容一内容一内容一内容一</p> <p> 内容一内容一容一内容一内容一</p> <p> 内容一内容一一内容一内容一</p> </div> </div> <div class="page"> <div class="pageInner" style="background: #ddd;top:0px;left:0px;"> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> <p>内容二</p> </div> </div> <div class="page"> <div class="pageInner" style="background: #eee;top:0px;left:0px;"> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> <p>内容三</p> </div> </div> <div class="page"> <div class="pageInner" style="background: #888;top:0px;left:0px;"> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> <p>内容四</p> </div> </div> </div> </div> <script> //获取窗口高宽 function getW(){ var client_h,client_w,scrollTop; client_h = document.documentElement.clientHeight || document.body.clientHeight; client_w = document.documentElement.clientWidth || document.body.clientWidth; scrollTop = document.documentElement.scrollTop || document.body.scrollTop; scrollHeight = document.documentElement.scrollHeight || document.body.scrollHeight; return o = {w:client_w,h:client_h,s:scrollTop,s_h:scrollHeight}; }; //init (function(){ var win = getW(); dh.$M(dh.$("wrap"),{w:win.w,h:win.h}); var pageList = dh.$$$("page"); for(var i = 0,l=pageList.length;i<l;i++){ dh.$M(pageList[i],{w:win.w,h:win.h}); }; var scollobj = new Scroll({ele:"wrap_pos",item:"page",w:win.w}); })(); </script> </body> </html>
/** * Created by JetBrains WebStorm. * User: Jin.dh * Date: 12-5-24 * Time: 下午12:05 * To change this template use File | Settings | File Templates. */ //工具 var dh = { extend:function(obj1,obj2){ for (var i in obj2) { obj1[i] = obj2[i]; }; return obj1; }, getMS:function() { var z = new Date(); return (z.getMinutes() * 60 + z.getSeconds()) * 1000 + z.getMilliseconds() }, myAddListener:function(ele, type, fn) { if (isIphone || isIpad || isAndroid) { var mapping = { mousedown: 'touchstart', mouseup: 'touchend', mousemove: 'touchmove' }; type = mapping[type] || type; } if (ele.addEventListener) { ele.addEventListener(type, fn, false); } else { ele.attachEvent('on' + type, fn); } }, getW:function() { var client_h, client_w, scrollTop; client_h = document.documentElement.clientHeight || document.body.clientHeight; client_w = document.documentElement.clientWidth || document.body.clientWidth; scrollTop = document.documentElement.scrollTop || document.body.scrollTop; return o = { w: client_w, h: client_h, s: scrollTop }; }, getEvent:function(e, def) { e = e || window.event; if (!def) { //缺省执行 if (!e.stopPropagation) { //IE e.cancelBubble = true } else { e.stopPropagation() } if (!e.preventDefault) { //IE e.returnValue = false } else { e.preventDefault() } } e = e.touches ? e.touches[0] : e; return e; }, $: function (id) { return typeof id === "object" ? id : document.getElementById(id) }, $$: function (tagName, oParent) { return (oParent || document).getElementsByTagName(tagName) }, $$$: function (className, tagName, elem) { var i = 0, aClass = [], reClass = new RegExp("(^|\\s)" + className + "(\\s|$)"), aElement = dh.$$(tagName || "*", elem || document); for (i = 0; i < aElement.length; i++) reClass.test(aElement[i].className) && aClass.push(aElement[i]); return aClass }, addClass: function (elem, value) { !elem.className ? elem.className = value : elem.className += " " + value }, removeClass: function (elem, className) { var reg = new RegExp('(\\s|^)' + className + '(\\s|$)'); var ematch = elem.className.match(reg); if (ematch) elem.className = elem.className.replace(reg, ' ') }, getStyle:function(ele){ var style; if (document.defaultView && document.defaultView.getComputedStyle){ style = document.defaultView.getComputedStyle(ele, null); }else { style = ele.currentStyle; }; return style; }, $M:function(ele, css) { if (!ele || !css) {return; } var z, y = ele.style, x; for (var i in css) { z = css[i]; x = z + 'px'; switch (i) { case 'l': y.left = x; break; case 't': y.top = x; break; case 'w': y.width = x; break; case 'h': y.height = x; break; case 'o': y.overflow = z; break; case 'bd': y.border = z; break; case 'bg': y.backgroundColor = z; break; case 'i': ele.innerHTML = z; break; default: y[i] = z; break; } } }, find:function(a, b) { return a.indexOf(b) + 1; }, setMove:function(obj,event){ //拖拽必备条件(清除焦点,设置鼠标范围,obj为拖动对象,event为事件对象)。 //清除选择 window.getSelection ? window.getSelection().removeAllRanges() : document.selection.empty(); if(document.all){ //is IE //焦点丢失 obj.onlosecapture = function(){obj.stop();} //设置鼠标捕获 obj.setCapture(); }else{ //焦点丢失 window.onblur =function(){obj.stop();} //阻止默认动作 event.preventDefault(); }; obj.stop = function(){ if(obj.releaseCapture){ obj.releaseCapture(); }; document.onmousemove = null; document.onmouseup = null; window.onblur = null; } } }; (function () { //brwoser browser = navigator.userAgent.toLowerCase(); isAndroid = dh.find(browser, "android"); isIphone = dh.find(browser, "iphone"); isIpad = dh.find(browser, "ipad"); isTouch = isIphone || isIpad; })(); // function link() { links = document.getElementsByClassName('link'); // alert(links.length); var link; for (var i = 0, len = links.length; i < len; i++) { ele = links[i]; dh.myAddListener(ele, 'mousedown', function () { this.down = 1; this.click = 1; this.start = dh.getMS(); }); dh.myAddListener(ele, 'mousemove', function () { if (this.down) { this.click = 0; } }) dh.myAddListener(ele, 'mouseup', function (e) { if (this.down) { if (this.click && dh.getMS() - this.start < 200) { alert("this Link"); } } this.down = 0; this.click = 0; }); } }; //滚动类 function Scroll(o){ var that = this; var win = dh.getW(); that.o = {directionX:true,directionY:true,ele:null,item:"page",w:640,wrap:null,h:null}; dh.extend(this.o,o); if(!document.getElementById(this.o["ele"]) && typeof this.o["ele"]!="object")return false; that.ele = dh.$(that.o["ele"]); that.wrap = that.o["wrap"]?dh.$(that.o["wrap"]):that.ele.parentNode; that.h = that.o["h"]?that.o["h"]:that.wrap.offsetHeight; that.item = dh.$$$(that.o["item"],"div",that.ele); that.w = that.o["w"]; if(that.o["directionX"]){ that.l = that.item.length; that.c = 0; dh.$M(that.ele,{w:that.w*that.l,position:"absolute",l:that.w*that.c,t:0}); }; that.isMove = false;//用来判断是否在运动,防止用户在运动中触发事件 that.page_old = null;//记录上一个运动page; that.direction_old = null;//记录之前运动方向 for(var i = 0,l=that.l;i<l;i++){ var p = that.item[i]; p.content = dh.$$("div",p)[0]; p.maxT = that.h-p.content.offsetHeight; bindScroll(p); }; function bindScroll(page){ dh.myAddListener(page,"mousedown",function(event){ that.direction = null; if(that.timer){clearTimeout(that.timer);} if(that.isMove&&that.direction_old=="y"){ //如果Y轴运动尚未停止,并且超出范围,直接跳至范围内 var pos = parseInt(dh.getStyle(that.page_old.content)["top"]); if(pos<that.page_old.maxT){ dh.$M(that.page_old.content,{t:that.page_old.maxT}); }; if(pos>0){ dh.$M(that.page_old.content,{t:0}); }; }; var e = dh.getEvent(event); this.down = 1; that.startX = parseInt(dh.getStyle(that.ele)["left"]); that.startY = parseInt(dh.getStyle(this.content)["top"]); that.lastX = e.clientX; that.lastY = e.clientY; that.startTime = dh.getMS(); }); dh.myAddListener(page,"mousemove",function(event){ var e = dh.getEvent(event); if(this.down){ that.mousemoveFn(e,this); that.isMove = true; }; }); dh.myAddListener(page,"mouseup",function(){ this.down = 0; that.timeline = dh.getMS()-that.startTime; that.mouseupFn(this); }); }; }; Scroll.prototype={ mousemoveFn:function(e,page){ var that = this; if(!that.direction){ var moveX =e.clientX - that.lastX; var moveY = e.clientY - that.lastY; if(Math.abs(moveX)>Math.abs(moveY)||!that.o["directionY"]||(that.isMove&&that.direction_old=="x")){ that.direction = "x"; }else{ that.direction = "y"; }; }; if(that.direction=='x'){ dh.$M(that.ele,{l:that.startX+(e.clientX-that.lastX)}); that.direction_old = "x"; }; if(that.direction=='y'){ dh.$M(page.content,{t:that.startY+(e.clientY-that.lastY)}); that.direction_old = "y"; }; }, mouseupFn:function(page){ var that = this; if(that.direction=="x"){ var nowX = parseInt(dh.getStyle(that.ele)["left"]); if(Math.abs(Math.abs(that.startX)- Math.abs(nowX))>that.w/2||that.timeline<150){//如果大于屏幕一半 if(that.startX>nowX){ that.c < that.l-1 ? that.c++:that.c = that.l-1; }else{ that.c > 0 ? that.c--:that.c = 0; }; } that.move(that.ele,"left",-that.c*that.w); }else if(that.direction=='y'){ that.page_old = page; var distance_y = (parseInt(dh.getStyle(page.content)["top"])-that.startY)/that.timeline*10,pos; clearTimeout(that.timer); that.timer = setInterval(function(){ distance_y*=0.95; if(Math.abs(distance_y)<2){ distance_y = 0; clearInterval(that.timer); }; pos = parseInt(dh.getStyle(page.content)["top"])+distance_y; if(pos<page.maxT){ clearInterval(that.timer); that.move(page.content,"top",page.maxT); }; if(pos>0){ clearInterval(that.timer); that.move(page.content,"top",0); }; dh.$M(page.content,{t:pos}); },30); }else if(that.isMove&&that.direction_old=="x"){ that.move(that.ele,"left",-that.c*that.w); }; }, move:function(ele,fx,pos){ var that = this; var b=parseInt(dh.getStyle(ele)[fx]),c=pos-b,d=50,t=0; function Run(){ ele.style[fx] = Math.ceil(Tween.Quad.easeOut(t,b,c,d))+"px"; if(parseInt(dh.getStyle(ele)[fx])==pos){ that.isMove = false; // 如果到达目的地,状态停止 }; if(t<d){ t+=5; that.timer = setTimeout(Run, 30); }; } Run(); } }; //tween var Tween = { Quad: { easeOut: function(t,b,c,d){ return -c *(t/=d)*(t-2) + b; } } }; function showMsg(o){ document.title = o; }
css部分:
@charset "utf-8"; /* CSS Document */ li,ul,body{margin:0px;padding:0;} a img{border:none;display:block;} .wrap{width:500px;height:480px;overflow: hidden;background: #000;position: relative;margin:0 auto;} .wrap_pos {width:10000px;} .wrap_pos .page{float:left;width:500px;line-height: 100px; position:relative;height:480px;overflow:hidden;} .wrap_pos .pageInner{position:absolute;left:0px;top:0px;z-index:3;width:100%;}