執行個體講解Javascript緩動效果

來源:互聯網
上載者:User

我們這裡將討論的是Javascript緩動效果的實現,這個看似沒有實際作用的功能,其實實現更多花樣繁多Javascript緩動效果的基石。

緩動,學名為Tween,緩衝移動的簡稱。要想頁面內容切換起來舒服,就使用淡入淡出特效,要想讓頁面元素動起來自然,就要使用Javascript緩動效果。這兩個混合起來,可以衍生多種特效的。感謝Flash開發人員為我們做了那麼多先行研究,我們直接把它們拆出來裝在各種菜單與相簿中。我們先從最簡單的東西做起,加速與減速。

既然是緩動,它就一定涉及以下概念:距離,時間與速度。我們可以想象存在一條直線L,點A與點B就是L的起點與終點,有一個點C在直線L上移動,從點A到點B。所需的時間通常都是未知,但速度我們一定要制定。看下面的圖,我們想讓綠色的方塊在淡緊色的滑動帶上移動。滑動帶左上方就相當於點A,右上方就相當於B點,方塊的左上方就相當於點C,移動距離為兩者的寬度之差。由於我們移動的物體是存在寬度,也就是說點C永遠不可能與點B重合。但一個準確的目的地為了方便,我們把它稱之為點D)是必須的,我們一定要計算它出來。因為在加速運動中,點C隨時可能超過點D,當點超過它時,我們就要終止此移動,並把點C拉回到點D上。

加速

點擊可移動綠色方塊

為了擷取它們在頁面上的座標與尺寸,getCoords()與getStyle()又到出場時間了。對不起,我實在沒有意思來炫耀我的函數。更何況getStyle()被砍去了不少東西,威力沒有以前那麼強大。

01. //輔助函數1 02. var getCoords = function (el){ 03.    var box = el.getBoundingClientRect(), 04.    doc = el.ownerDocument, 05.    body = doc.body, 06.    html = doc.documentElement, 07.    clientTop = html.clientTop || body.clientTop || 0, 08.    clientLeft = html.clientLeft || body.clientLeft || 0, 09.    top  = box.top  + (self.pageYOffset || html.scrollTop  ||  body.scrollTop ) - clientTop, 10.    left = box.left + (self.pageXOffset || html.scrollLeft ||  body.scrollLeft) - clientLeft 11.    return { 'top' : top, 'left' : left }; 12. }; 13. //輔助函數2 14. var getStyle = function (el, style){ 15.    if (!+ "\v1" ){ 16.      style = style.replace(/\-(\w)/g, function (all, letter){ 17.        return letter.toUpperCase(); 18.      }); 19.      var value = el.currentStyle[style]; 20.      (value == "auto" )&&(value = "0px" ); 21.      return value; 22.    } else { 23.      return document.defaultView.getComputedStyle(el, null ).getPropertyValue(style) 24.    } 25. }

那麼我們怎麼移動呢?在Javascript只有讓它變為絕對位置對象,給它的top與left賦值。它就會立即移動到相應的座標上。由於Javascript處理位置變化太有效率,根本不可能讓你有“移動”的感覺,感覺是直接從點C直接跳到點D。我們必須讓物體每移動一點點,就停一下,讓眼睛有個殘影。根據人眼睛的視覺停留效應,若前一幅畫像留在大腦中的印象還沒消失,後一幅畫像就接踵而至,而且兩副畫面間的差別很小,就會有“動”的感覺。那麼停留多麼毫秒最合適呢?我們不但要照顧人的眼睛,還要顧及一下顯示器的顯示速度與瀏覽器的渲染速度。根據外國的統計,25毫秒為最佳數值。其實,這個數值我們應該當作常識來記住。聯想一下,日本動畫好像有個規定是1秒30張畫,中國的,比較垃圾,是1秒24張。用1秒去除以張數,就得到每張停留的時間。日本的那個27.77毫秒已經很接近我們的25毫秒了,因為瀏覽器的渲染速度明顯不如電視機的渲染速度,尤其是IE6這個拉後腿的。要實現加速度,就是讓它每次移動快一點點,讓上一次移動的距離乘以一個大於1的數便可。

01. //輔助函數3,相當於$(),不用$符號命名是因為部落格園在用JQuery,會引起命名衝突 02. //我新一代查代元素的方法,擁有緩衝能力 03. var cache = [] 04. var _ = function (id){ 05.    return cache[id] || (cache[id] = document.getElementById(id)); 06. } 07. //主函數:加速移動 08. var accelerate= function (el){ 09.    el.style.position = "absolute" ; 10.    var begin =  getCoords(el).left, 11.    distance = parseFloat(getStyle(_( "taxiway" ), "width" )) - parseFloat(getStyle(el, "width" )), 12.    end = begin + distance, 13.    speed = 10; //第一次移動的速度,單位px/ms,隱式地乘以1ms 14.    ( function (){ 15.      setTimeout( function (){ 16.        el.style.left = getCoords(el).left + speed + "px" ; //移動 17.        speed *= 1.5; //下一次移動的距離 18.        if (getCoords(el).left >= end){ 19.          el.style.left = end + "px" ; 20.        } else {        21.          setTimeout(arguments.callee,25); //每移動一次停留25毫秒 22.        } 23.      },25) 24.    })() 25. }

明白了加速,減速就好辦了。我們給第一次移動的距離一個很大的數,往後每次減少一點點,換言之乘以一個小於1的數。但這裡有個注意點,如果有一次,它移動的距離少於1px怎麼辦?!它再往後也是少於1px。瀏覽器就會忽略這個值,當作0來處理。這樣一來,它就會停在中途不動了。為了防止這樣可怕的事發生,我們利用Math.ceil來確保其最小移動距離為1px,哪怕最後的勻速移動也要抵達終點。

01. //主函數:減速移動 02.   var decelerate = function (el){ 03.     el.style.position = "absolute" ; 04.     var begin =  getCoords(el).left, 05.     distance = parseFloat(getStyle(_( "taxiway" ), "width" )) - parseFloat(getStyle(el, "width" )), 06.     end = begin + distance, 07.     speed = 100; //第一次移動的速度,單位px/ms,隱式地乘以1ms 08.     ( function (){ 09.       setTimeout( function (){ 10.         el.style.left = getCoords(el).left + speed + "px" ; //移動 11.         speed = Math.ceil(speed * 0.9); //下一次移動的距離 12.         if (getCoords(el).left <= end){ 13.           el.style.left = end + "px" ; 14.         } else {        15.           setTimeout(arguments.callee,25); 16.         } 17.       },25) 18.     })() 19.   }

現在函數的功能還很弱,主要是由於在抽象與制定上有所欠缺,如果克服這些缺點並配合Robert Penner大神的緩動公式,我們就可以搞出花樣繁多的緩動效果來。

原文標題:由淺入深javascript的緩動效果

連結:http://www.cnblogs.com/rubylouvre/archive/2009/09/16/1566699.html

  1. JSON是什嗎?為JavaScript準備的資料格式
  2. 十個最常用的JavaScript自訂函數
  3. 有關JavaScript事件載入的一些延伸思考
  4. JavaScript使用心得匯總:從BOM和DOM談起
  5. ExtJS在Android模擬器上的運行效果

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.