使用jQuery做一个制作滚轮跟随(Scroll Follow)动画
本文首先给大家介绍一个开源的小工具,方便而实用。最后给大家发一个自己写的代码,可定制性高。
目录
1、开源工具JQUERY SCROLL FOLLOW
开源工具下载地址如下:Open Source - Scroll Follow,这个工具非常简单,里面的介绍也基本能说明此工具的使用方法。
1.1、引用
此工具引用了jQuery (开发使用1.2.6)和jQuery UI Core (开发使用1.5.2)。如果使用擦除(一种动画方式)和Cookie(可以让浏览器记住之前的操作)还要引用jQuery Easing Plugin和jQuery Cookie Plugin。
最终自己做了这个动画很大一部分原因是这个工具引用东西太多,而且实现自己使用的功能又有点复杂。
1.2、使用
下面的一段代码实现一个div(id为example)随滚轮移动,有60px的偏移。然后有一个链接(id为exampleLink),单击可以实现动画的开始与停止(单击链接的文字会在Disable Follow和Enable Follow之间改变)。
1 2 3 4 5 6 7 8 9 10 11 |
<script type="text/javascript"> $( document ).ready( function () { $( '#example' ).scrollFollow( { speed: 1000, offset: 60, killSwitch: 'exampleLink', onText: 'Disable Follow', offText: 'Enable Follow' } ); } ); </script> |
示例页面:Scroll Follow示例。
1.3、参数
在前面的示例中已经使用了参数,共有如下几个参数:
speed
类型:int - 如果不指定则为500
动画两帧之间间隔,表示动画的速度,间隔越小速度越快。
easing
类型:string - 如果不指定则为'linear'
擦除动画的相关操作,默认为无。此功能需要使用jQuery Easing Plugin。
offset
类型:int - 默认为0
跟随对象的顶部偏移数
container
类型:string - 默认为其上一级对象(父对象)
包含对象的ID
killSwitch
类型:string - 默认为 'killSwitch'
打开关闭动画按钮的ID,此功能需要使用jQuery Cookie plugin。
onText
类型:string - 默认为 'Turn Slide Off'
当动画开启时killSwitch按键表现的文本。
offText
类型:string - 默认为 'Turn Slide On'
当动画停止时killSwitch按键表现的文本。
relativeTo
类型:string - 默认为 'top'
滚轮跟随动画可以相对于'top'(顶部)或'bottom'(底部)。
delay
类型:int - 默认为 0
动画开始前的延迟。
1.4、自己使用遇到的问题
1、jQuery的引用。自己使用的主题中也引用了jQuery,版本不一样,出现了冲突。自己做了很多工作解决了这个问题,解决方案如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
<!-- 引入1.6.4版的jq --> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.4/jquery.js"></script> <script> var jq164 = jQuery.noConflict(true); </script> <!-- 引入1.4.2版的jq --> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.js"></script> <script> var jq142 = jQuery.noConflict(true); </script> <script> (function($){ //此时的$是jQuery-1.6.4 $('#header'); })(jq164); </script> <script> (function($){ //此时的$是jQuery-1.4.2 $('#footer'); })(jq142); </script> |
2、动画停止问题。动画需要停止时,非常不方便。最终自己想了一个折衷的方法,做了几个不显示display:none的按钮,程序自动点击,并用一个变量记录动画的开始与停止。
3、动画过程中参数的更改问题。动画开始后如果再要对参数(比方说offset)进行改变,非常不便。自己现在还没有想到合适的方法。所以就开始自己写一个这个动画了,也非常简单。
2、自己开发的滚轮跟随动画
2.1、jQuery的动画函数
animate(params, [duration], [easing], [callback])
params 对象{},注意:所有指定的属性必须用骆驼形式,比如用marginLeft代替margin-left,如果使用的是“hide”、“show”或“toggle”这样的字符串值,则会为该属性调用默认的动画形式。
duration (可选)三种预定速度之一的字符串("slow", "normal", or "fast")或表示动画时长的毫秒数值(如:1000)。
easing (可选)String要使用的擦除效果的名称(需要插件支持).默认jQuery提供"linear" 和 "swing"。
callback (可选)Function在动画完成时执行的函数。
下面是一段示例代码:
1 2 3 4 5 6 7 8 |
$("#go").click(function () { $("#block").animate({ width: "90%", height: "100%", fontSize: "10em", borderWidth: 10 }, 1000); }); |
2.2、滚轮跟随动画的编写
先给出自己写的代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
<script type="text/javascript"> var box = $('#example2'); var parent = box.parent(); var maxScroll = parseInt(parent.top) + parseInt(parent.css("margin-top")) + parseInt(parent.outerHeight()) - parseInt(parent.css("border-bottom-width")) - parseInt(parent.css("padding-bottom")) - parseInt(parent.css("border-top-width")) - parseInt(parent.css("padding-top")) - parseInt(parent.css("margin-top")) - parseInt(box.outerHeight()) - parseInt(box.css("margin-bottom")) - parseInt(box.css("margin-top")); $(document).scroll( function () { var scrollTop = document.body.scrollTop; var topPs = scrollTop > maxScroll ? maxScroll : scrollTop; box.stop(); box.animate({ top: topPs }, 500); } ); </script> |
这就可以了吗?你错了,下面看看本博客用的动画代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 |
$(document).ready(function () { scroll(); }); function scroll() { var lastScroll = document.body.scrollTop; window.addEventListener("scroll", function () { var scrollTop = document.body.scrollTop; var mainHeight = document.getElementById("main").clientHeight; var sidebarHeight = document.getElementById("sidebar").clientHeight; var box; if (mainHeight < sidebarHeight) { box = $('#main'); } else { box = $('#sidebar'); } var pnt = box.parent(); box.stop(); if (lastScroll > scrollTop) { //表示向上滚动 if (scrollTop < box.position().top) { //只有当上部出现空白时才开始动画 //此变量表示当top=0时浮动的位置 var pntInnerH = parseInt(pnt.position().top) + parseInt(pnt.css("border-top-width")) + parseInt(pnt.css("padding-top")) + parseInt(pnt.css("margin-top")); var maxScroll = parseInt(pnt.innerHeight()) - parseInt(pnt.css("padding-bottom")) - parseInt(pnt.css("padding-top")) - parseInt(box.outerHeight()) - parseInt(box.css("margin-bottom")) - parseInt(box.css("margin-top")); var paddingPixal = 10; var topPz = scrollTop - pntInnerH > maxScroll ? maxScroll : scrollTop - pntInnerH + paddingPixal; topPz = topPz > paddingPixal ? topPz : 0; box.animate({ top: topPz }, 500); } } else if (lastScroll < scrollTop) { //向下滚动 var pageH = document.documentElement.clientHeight; var moveObjectBottomPs = parseInt(box.position().top) + parseInt(box.outerHeight()) + parseInt(box.css("margin-bottom")) + parseInt(box.css("margin-top")); if (scrollTop + pageH >= moveObjectBottomPs) { //只有在下部出现空白时才开始动画 var boxAllHeight = parseInt(box.outerHeight()) + parseInt(box.css("margin-bottom")) + parseInt(box.css("margin-top")); var pntInnerH = parseInt(pnt.position().top) + parseInt(pnt.css("border-top-width")) + parseInt(pnt.css("padding-top")) + parseInt(pnt.css("margin-top")); var maxScroll = parseInt(pnt.innerHeight()) - parseInt(pnt.css("padding-bottom")) - parseInt(pnt.css("padding-top")) - boxAllHeight; var offset = -Math.abs(boxAllHeight - pageH); var topPz; if ((scrollTop - pntInnerH < maxScroll) && (scrollTop - pntInnerH + offset < maxScroll)) topPz = scrollTop - pntInnerH + offset; else if ((scrollTop - pntInnerH < maxScroll) && (scrollTop - pntInnerH + offset > maxScroll)) topPz = scrollTop - pntInnerH; else if ((scrollTop - pntInnerH > maxScroll) && (scrollTop - pntInnerH + offset < maxScroll)) topPz = scrollTop - pntInnerH + offset; else topPz = maxScroll; //var topPz = scrollTop - pntInnerH > maxScroll ? maxScroll : scrollTop - pntInnerH + offset; topPz = topPz > 0 ? topPz : 0; box.animate({ top: topPz }, 500); } } lastScroll = scrollTop; }, false); } |
具体的细节我在这里就不多说了,有问题的话可以问我,也可以直接调试本页,看看具体是怎么运作的。
2.3、注意的问题
上面的parent就是要限制于某个对象中,上面就直接使用的是父对象,也可以自己选择其他的对象。
第4-15行代码,如果parent是固定不动的,也可以放到scroll事件外面,这样效率更高一些。如果parent位置也变动,主些代码一定要放入scroll事件中。
如果要使用类似于offset效果,就需要对topPs进行更改。
好了,就这样吧,如果有其他需要了解的可以给我留言。
原创文章,文章首发于:Riley Ge (@rileyge) — Steemit
原创文章,转载请注明: 转载自TsonTec:测量解决方案提供者
说点什么
您将是第一位评论人!