晨彦电脑科技 Belong to oneself's sky
RSS
Aug 11

实现页面不同位置间平滑滚动的两种解决方案 不指定

雪糕先生 2009/08/11 不指定 14:36
在网页设计中,当页面较长或是想实现一个导航效果时,我们经常会用锚点来实现同一页面间不同位置的跳转。但是这样做也许会造成用户的一种困惑——当用锚点跳转时,页面内容瞬间发生了改变,用户也许就会想:我还在原来的那个页面上吗?如果我们能把这种情况做成平滑滚动的效果(而非瞬间跳转到页面的另一个位置),就可以获得一个好的用户体验。

对于这种情况的解决方案可能已经有不少,这里我找到两个感觉比较好的与大家分享:

解决方案一:

这个方法使用起来非常简单(当然功能单一,也没有乱七八糟的参数可配置):将smoothscroll.js文件在head标签中引用,页面中所有锚点跳转的效果都变成了平滑滚动。

smoothscroll.js 文件内容如下

引用
/* Smooth scrolling
   Changes links that link to other parts of this page to scroll
   smoothly to those links rather than jump to them directly, which
   can be a little disorienting.
  
   sil, http://www.btoss.com/
  
   v1.0 2003-11-11
   v1.1 2005-06-16 wrap it up in an object
*/

var ss = {
  fixAllLinks: function() {
    // Get a list of all links in the page
    var allLinks = document.getElementsByTagName('a');
    // Walk through the list
    for (var i=0;i<allLinks.length;i++) {
      var lnk = allLinks[i];
      if ((lnk.href && lnk.href.indexOf('#') != -1) &&
          ( (lnk.pathname == location.pathname) &#124;&#124;
      ('/'+lnk.pathname == location.pathname) ) &&
          (lnk.search == location.search)) {
        // If the link is internal to the page (begins in #)
        // then attach the smoothScroll function as an onclick
        // event handler
        ss.addEvent(lnk,'click',ss.smoothScroll);
      }
    }
  },

  smoothScroll: function(e) {
    // This is an event handler; get the clicked on element,
    // in a cross-browser fashion
    if (window.event) {
      target = window.event.srcElement;
    } else if (e) {
      target = e.target;
    } else return;

    // Make sure that the target is an element, not a text node
    // within an element
    if (target.nodeName.toLowerCase() != 'a') {
      target = target.parentNode;
    }
  
    // Paranoia; check this is an A tag
    if (target.nodeName.toLowerCase() != 'a') return;
  
    // Find the <a name> tag corresponding to this href
    // First strip off the hash (first character)
    anchor = target.hash.substr(1);
    // Now loop all A tags until we find one with that name
    var allLinks = document.getElementsByTagName('a');
    var destinationLink = null;
    for (var i=0;i<allLinks.length;i++) {
      var lnk = allLinks[i];
      if (lnk.name && (lnk.name == anchor)) {
        destinationLink = lnk;
        break;
      }
    }
    if (!destinationLink) destinationLink = document.getElementById(anchor);

    // If we didn't find a destination, give up and let the browser do
    // its thing
    if (!destinationLink) return true;
  
    // Find the destination's position
    var destx = destinationLink.offsetLeft;
    var desty = destinationLink.offsetTop;
    var thisNode = destinationLink;
    while (thisNode.offsetParent &&
          (thisNode.offsetParent != document.body)) {
      thisNode = thisNode.offsetParent;
      destx += thisNode.offsetLeft;
      desty += thisNode.offsetTop;
    }
  
    // Stop any current scrolling
    clearInterval(ss.INTERVAL);
  
    cypos = ss.getCurrentYPos();
  
    ss_stepsize = parseInt((desty-cypos)/ss.STEPS);
    ss.INTERVAL =
setInterval('ss.scrollWindow('+ss_stepsize+','+desty+',"'+anchor+'")',10);
  
    // And stop the actual click happening
    if (window.event) {
      window.event.cancelBubble = true;
      window.event.returnValue = false;
    }
    if (e && e.preventDefault && e.stopPropagation) {
      e.preventDefault();
      e.stopPropagation();
    }
  },

  scrollWindow: function(scramount,dest,anchor) {
    wascypos = ss.getCurrentYPos();
    isAbove = (wascypos < dest);
    window.scrollTo(0,wascypos + scramount);
    iscypos = ss.getCurrentYPos();
    isAboveNow = (iscypos < dest);
    if ((isAbove != isAboveNow) &#124;&#124; (wascypos == iscypos)) {
      // if we've just scrolled past the destination, or
      // we haven't moved from the last scroll (i.e., we're at the
      // bottom of the page) then scroll exactly to the link
      window.scrollTo(0,dest);
      // cancel the repeating timer
      clearInterval(ss.INTERVAL);
      // and jump to the link directly so the URL's right
      location.hash = anchor;
    }
  },

  getCurrentYPos: function() {
    if (document.body && document.body.scrollTop)
      return document.body.scrollTop;
    if (document.documentElement && document.documentElement.scrollTop)
      return document.documentElement.scrollTop;
    if (window.pageYOffset)
      return window.pageYOffset;
    return 0;
  },

  addEvent: function(elm, evType, fn, useCapture) {
    // addEvent and removeEvent
    // cross-browser event handling for IE5+,  NS6 and Mozilla
    // By Scott Andrew
    if (elm.addEventListener){
      elm.addEventListener(evType, fn, useCapture);
      return true;
    } else if (elm.attachEvent){
      var r = elm.attachEvent("on"+evType, fn);
      return r;
    } else {
      alert("Handler could not be removed");
    }
  }
}

ss.STEPS = 25;

ss.addEvent(window,"load",ss.fixAllLinks);


HTML

引用
<script type="text/javascript" src="http://btoss.com/smoothscroll.js"></script>
解决方案二:

ScrollTo是一款用来实现页面间不同位置平滑滚动的jquery插件。相比解决方案一,它的功能就强大多了,有不少参数可以配置,跳转的位置也不仅限于锚点(可以是DOM对象,绝对坐标位置、相对位置等等),而且跳转的范围不仅可以设置为整个屏幕,而且可以指定为某个节点内。 例如(以下例子均假设跳转链接id=’link’):

滚动至屏幕的最顶端(重置屏幕位置)

$('#top').click(function(){
/*第一个参数0表示滑动至屏幕原点,第二个参数表示滑动速度*/
           $.scrollTo(0 , 800 );  
  });
滚动至页面某一坐标(绝对位置)

$('#link').click(function(){
/*第一个参数表示滑动至屏幕距上110px、距左290px处,第二个参数表示滑动速度*/
           $.scrollTo(0{top:'110px',left:'290px'}, 800 );  
  });
滚动至页面某一坐标(相对位置)

$('#link').click(function(){
/*第一个参数表示相对当前上移110px、右移290px,第二个参数表示滑动速度*/
           $.scrollTo(0{top:'-=110px',left:'+=290px'}, 800 );  
  });
Actions
Tags:
 
网页特效 , 评论(0) , 引用(0) , 阅读(2929) , Via 本站原创
发表评论

昵称

网址

电邮

打开HTML 打开UBB 打开表情 隐藏 记住我 [登入] [注册]

 
赞助商链接
热门Tags
统计