jQuery插件开发之windowScroll
2015-07-13 20:12
891 查看
回首望,曾经洋洋得意的代码现在不忍直视。曾经看起来碉堡的效果现在也能稍微弄点出来。社会在往前发展,人也得向前迈进。
参考于搜狗浏览器4.2版本首页的上下滚动效果。主要实现整个窗口的上下和左右滚动逻辑,还有很多可以拓展的空间。希望大家能多提意见与建议。
欢迎fork项目:https://github.com/codetker/myWindowScroll, 实现的效果见http://www.梦萦无双.xyz/myWindowScroll/demo/Default.html, 应用见http://wechat.wutnews.net/Web/PhotoWall/(尚在改善中)。
插件效果:
实现window的上下滚动,默认绑定键盘上下按钮和鼠标滑轮
实现window的左右滚动,默认绑定键盘左右按钮
可附加ul li协助控制滚动
可修改后附加缓动函数,实现多种效果,详情见缓动函数表 http://easings.net/zh-cn#easeInOutQuad
html 结构(ZenCoding形式)
其中div.toLeftOrTop,div.toRightOrBottom,ul.controlUl可选
调用方法(详情见demo)(按需设置参数)
A.vertical
B.horizontal
运行demo
最简单的方法为改Default.html中jquery对应script元素的src为本地的jquery(离线)或CDN中的jquery(在线),然后双击Default.html即可
或者配置myBoxScroll.jquery.json or package.json
PS:代码之间耦合过强,可重复利用的很多,准备参考学长的建议按模块写个人函数库,通过模块加载注入需要使用的工具函数
Demo代码如下:
HTML
View Code JS
参考于搜狗浏览器4.2版本首页的上下滚动效果。主要实现整个窗口的上下和左右滚动逻辑,还有很多可以拓展的空间。希望大家能多提意见与建议。
欢迎fork项目:https://github.com/codetker/myWindowScroll, 实现的效果见http://www.梦萦无双.xyz/myWindowScroll/demo/Default.html, 应用见http://wechat.wutnews.net/Web/PhotoWall/(尚在改善中)。
插件效果:
实现window的上下滚动,默认绑定键盘上下按钮和鼠标滑轮
实现window的左右滚动,默认绑定键盘左右按钮
可附加ul li协助控制滚动
可修改后附加缓动函数,实现多种效果,详情见缓动函数表 http://easings.net/zh-cn#easeInOutQuad
html 结构(ZenCoding形式)
-div.divClass -div.toLeftOrTop -div.toRightOrBottom -div.stageClass*n -ul.controlUl -li.liClass*n
其中div.toLeftOrTop,div.toRightOrBottom,ul.controlUl可选
调用方法(详情见demo)(按需设置参数)
A.vertical
$(".divClass").windowScroll({ 'choose': 0, //垂直滚动,默认 'verticalSpeed': 1, //控制垂直滚动速度 'objControlUl': 'ul.controlUl', //控制垂直滚动按钮,默认为null 'list': '.stageClass', //垂直滚动的对象 'crash': true, //撞击底部特效 'toTop': '.toLeftOrTop', //向上按钮,默认为null 'toBottom': 'toRightOrBottom', //向下按钮,默认为null 'liHover': 'stageSelect' //设置当前stage的类名 });
B.horizontal
$(".divClass").windowScroll({ 'choose': 1, //水平滚动 'horizontalSpeed': 1, //控制水平滚动速度 'objControlUl': 'ul.controlUl', //控制水平滚动按钮,默认为null 'list': '.stageClass', //水平滚动的对象 'crash': true, //撞击左右特效 'toTop': '.toLeftOrTop', //向左按钮,默认为null 'toBottom': 'toRightOrBottom', //向右按钮,默认为null 'liHover': 'stageSelect' //设置当前page的类名 });
运行demo
最简单的方法为改Default.html中jquery对应script元素的src为本地的jquery(离线)或CDN中的jquery(在线),然后双击Default.html即可
或者配置myBoxScroll.jquery.json or package.json
PS:代码之间耦合过强,可重复利用的很多,准备参考学长的建议按模块写个人函数库,通过模块加载注入需要使用的工具函数
Demo代码如下:
HTML
/* * windowScroll 0.1 * window滚动插件,上下左右,可选择是否回弹。参考搜狗欢迎页面 * 兼容等常见浏览器 * 借鉴搜狗4.2版http://ie.sogou.com/features4.2.html */ ;(function($, window, document, undefined) { //定义构造函数 var WindowObj = function(ele, opt) { this.$element = ele; this.defaults = { 'choose': 0, 'list': null, 'verticalSpeed': 1, 'horizontalSpeed': 1, 'objControlUl': null, 'toLeft': null, 'toRight': null, 'toTop': null, 'toBottom': null, 'crash': true, 'liHover': null }; this.options = $.extend({}, this.defaults, opt); }; //给构造函数添加方法 WindowObj.prototype = { //上下滚动的方法 verticalMove: function() { var obj = this.$element, speed = this.options.verticalSpeed, objControl = this.options.objControlUl, controlList = $(objControl).find('li'), windowHeight = $(window).height(), list = this.options.list, listMax = $(list).length, toTop = this.options.toTop, toBottom = this.options.toBottom, crashButton = this.options.crash, liHover = this.options.liHover, stop = 0, stageIndex, windowobject = is_chrome(); function setCss() { $(obj).css({ 'width': $(window).width() + 'px', 'height': $(window).height() * listMax + 'px' }); $(list).css({ 'min-width': $(window).width() + 'px', 'height': $(window).height() + 'px' }); } setCss(); function markStage() { getIndex(); $(controlList).removeClass(liHover); $(controlList).eq(stageIndex).addClass(liHover); } function is_chrome() { var is_ch = navigator.userAgent.toLowerCase().indexOf('chrome') > -1; if (is_ch) { //判断webkit内核,供scrollTop兼容性使用 return 'body'; } else { //支持IE和FF return 'html'; } } //阻止默认行为和冒泡 function stopDefaultAndBubble(e) { e = e || window.event; if (e.preventDefault) { e.preventDefault(); } e.returnValue = false; if (e.stopPropagation) { e.stopPropagation(); } e.cancelBubble = true; } //得到当前的垂直位置 function getIndex() { stageIndex = Math.round($(window).scrollTop() / windowHeight); } function goTop() { getIndex(); scrollStage(windowobject, stageIndex, 1); } function goBottom() { getIndex(); scrollStage(windowobject, stageIndex, -1); } //绑定键盘上下按键事件 $(document).keydown(function(event) { /* 绑定keycode38,即向上按钮 */ if (event.keyCode == 38) { goTop(); } else if (event.keyCode == 40) { //绑定40,即向下按钮 goBottom(); } }); //绑定滑轮功能的函数 function handle(delta) { getIndex(); if (delta < 0) { scrollStage(windowobject, stageIndex, -1); //stageIndex为当前页码 } else { scrollStage(windowobject, stageIndex, 1); //stageIndex为当前页码 } } //判断滑轮,解决兼容性 function wheel(event) { var delta = 0; if (!event) event = window.event; if (event.wheelDelta) { delta = event.wheelDelta; if (window.opera) delta = -delta; } else if (event.detail) { delta = -event.detail; } if (delta) handle(delta); //调用执行函数 } //注册事件 if (window.addEventListener) { window.addEventListener('DOMMouseScroll', wheel, false); } window.onmousewheel = document.onmousewheel = wheel; //绑定鼠标滚轮事件 $(document).bind('mousedown', function(e) { if (e.which == 2) { //which=2代表鼠标滚轮,即为中键 stopDefaultAndBubble(e); //bugfix 搜狗浏览器的ie内核只有在定时器触发这个函数才生效 setTimeout(function() { stopDefaultAndBubble(e); }, 10); } }); //如果有ul li控制按钮 if (objControl !== null) { $(objControl).delegate('li', 'click', function() { stageIndex = $(this).index(); scrollStage(windowobject, stageIndex, 0); }); } //如果有上下控制 $(toTop).click(function() { goTop(); }); $(toBottom).click(function() { goBottom(); }); function scrollStage(obj, stIndex, dir) { var sIndex = stIndex, windowobject = obj, direction = 0 || dir, target = windowHeight * sIndex; function move() { $(windowobject).animate({ 'scrollTop': target + 'px' }, 1000 * speed, function() { crash(1, target, 20, 150, -1); markStage(); }); } function after_crash(distant, time, termin) { if (distant <= 15 || time > 150) { stop = 1; //停止碰撞 $(windowobject).animate({ 'scrollTop': termin + 'px' }, time, function() { stop = 0; }); } } //撞击函数 function crash(direction, termin, distant, time, aspect) { if (crashButton) { if (!stop) { if (direction === 1) { direction = 0; if (aspect === 1) { $(windowobject).animate({ 'scrollTop': '-=' + distant + 'px' }, time, function() { crash(direction, termin, distant * 0.6, time, 1); after_crash(distant, time, termin); }); } else { $(windowobject).animate({ 'scrollTop': '+=' + distant + 'px' }, time, function() { crash(direction, termin, distant * 0.6, time, -1); after_crash(distant, time, termin); }); } } else if (direction === 0) { direction = 1; if (aspect === 1) { $(windowobject).animate({ 'scrollTop': termin + 'px' }, time, function() { crash(direction, termin, distant * 0.6, time, 1); after_crash(distant, time, termin); }); } else { $(windowobject).animate({ 'scrollTop': termin + 'px' }, time, function() { crash(direction, termin, distant * 0.6, time, -1); after_crash(distant, time, termin); }); } } } } } if (!$(windowobject).is(':animated')) { switch (direction) { case 0: if ($(window).scrollTop() > target) { direction = -1; move(); } else if ($(window).scrollTop() == windowHeight * sIndex) { direction = 0; crash(1, target, 20, 150, -1); } else { direction = 1; move(); } break; case 1: if (sIndex === 0) { crash(1, target, 20, 150, 1); } else { sIndex -= 1; target = windowHeight * sIndex; move(); } break; case -1: if (sIndex === listMax - 1) { crash(1, target, 20, 150, -1); } else { sIndex += 1; target = windowHeight * sIndex; move(); } break; default: } } } }, //左右滚动 horizontalMove: function() { var obj = this.$element, speed = this.options.horizontalSpeed, objControl = this.options.objControlUl, controlList = $(objControl).find('li'), windowWidth = $(window).width(), list = this.options.list, listMax = $(list).length, liHover = this.options.liHover, toLeft = this.options.toLeft, toRight = this.options.toRight, crashButton = this.options.crash, pageIndex; function setCss() { $(obj).css({ 'width': windowWidth * listMax + 'px', 'height': $(window).height() + 'px' }); $(list).css({ 'width': windowWidth + 'px', 'min-height': $(window).height() + 'px' }); } setCss(); function markPage() { getPageIndex(); $(controlList).removeClass(liHover); $(controlList).eq(pageIndex).addClass(liHover); } function getPageIndex() { pageIndex = (-1) * Math.round(parseInt($(obj).css('margin-left')) / windowWidth); } function goLeft() { getPageIndex(); scrollPage(obj, pageIndex, 1); } function goRight() { getPageIndex(); scrollPage(obj, pageIndex, -1); } //绑定键盘左右按键事件 $(document).keydown(function(event) { //判断event.keyCode为39(即向右按钮) if (event.keyCode === 39) { goRight(); } //判断event.keyCode为37(即向左按钮 else if (event.keyCode === 37) { goLeft(); } }); //如果有ul li控制按钮 if (objControl !== null) { $(objControl).delegate('li', 'click', function() { pageIndex = $(this).index(); scrollPage(obj, pageIndex, 0); }); } //如有有左右控制按钮 $(toLeft).click(function() { goLeft(); }); $(toRight).click(function() { goRight(); }); function scrollPage(obj, pageIndex, dir) { var windowobject = obj, direction = 0 || dir, dist = Math.round(parseInt($(obj).css('margin-left'))), aim; function getAim() { aim = pageIndex * windowWidth * (-1); } function crash(type) { if (crashButton) { if (type === 'left') { $(windowobject).animate({ 'margin-left': '+=' + '50px' }, 500).animate({ 'margin-left': '-=' + '100px' }, 500).animate({ 'margin-left': '+=' + '50px' }, 500); } else { $(windowobject).animate({ 'margin-left': '-=' + '50px' }, 500).animate({ 'margin-left': '+=' + '100px' }, 500).animate({ 'margin-left': '-=' + '50px' }, 500); } } } function move() { $(windowobject).animate({ 'margin-left': aim + 'px' }, 1000 * speed, function() { markPage(); }); } if (!$(windowobject).is(':animated')) { switch (direction) { case 0: getAim(); if (dist !== aim) { move(); } else { direction = 0; crash('left'); } break; case 1: if (pageIndex === 0) { crash('left'); } else { pageIndex -= 1; getAim(); move(); } break; case -1: if (pageIndex === (listMax - 1)) { crash('right'); } else { pageIndex += 1; getAim(); move(); } break; default: break; } } } } }; //绑定方法到jquery对象原型上 $.fn.windowScroll = function(options) { var windowObj = new WindowObj(this, options); if (windowObj.options.choose === 0) { return windowObj.verticalMove(); } else if (windowObj.options.choose === 1) { return windowObj.horizontalMove(); } else { //add some functions } }; })(jQuery, window, document);
View Code JS
相关文章推荐
- jquery get ajax 重复提交的奇怪问题
- jQuery插件开发之datalist
- jQuery获取input值、select值、select文本
- Jquery插件开发
- 不错的jquery插件
- Use jQuery to hide a DIV when the user clicks outside of it
- jQuery Ajax 实例 全解析
- jQuery自动添加表单项的方法
- jQuery 动态绑定的点击事件
- jQuery DOM节点操作
- jquery easyui dialog
- JS,Jquery获取各种屏幕的宽度和高度
- Jquery Easyui datagrid如何在动态获取当前选中行的值
- jquery easyui datagrid 设置设置在选中
- jQuery插件第五十六:十七种翻页插件
- jQuery中DOM和CSS操作
- jquery提升性能最佳实践小结
- jquery.autocomplete.js 使用备忘
- jQuery 让DIV显示后延时几秒后消失
- 根据不同浏览器选择jquery版本