2014-05-15 62 views
2

你好,我正在努力實現這個效果http://mario.ign.com/modern-era/super-mario-3D-world沒有鼠標移動我想用某種緩解效果來做到這一點,使其光滑,但實際上不知道如何實現de desaceleration效果,到目前爲止我所做的這是http://jsfiddle.net/xtatanx/8RB24/1/Mousemove動畫

var $container = $('#container'); 
var contWidth = $container.width(); 
var $point = $('.point'); 
var delay = 100; 

$container.mousemove(function(e){ 
    clearTimeout(timer); 

    var timer = setTimeout(function(){ 
     console.log(e.offsetX); 
     $point.each(function(){ 
      if(e.offsetX > (contWidth - $point.width())){ 
       return; 
      } 
      var xp = $(this).position().left; 
      xp += parseFloat((e.offsetX - xp)/ 20); 
      $(this).css({ 
       left: xp 
      }); 
     }); 
    }, delay); 

}); 

但我認爲,動畫犯規覺得馬里奧現場我將不勝感激,如果你們能幫助我ginding資源或指導我實現這個效果流暢。非常感謝你。

+0

你可以使用TweenLite或TweenJS等補間庫,使其變得非常容易。 – BadFeelingAboutThis

+0

是的,但是是爲了學習的目的,我想以某種方式來使用任何庫之前我自己的存檔。就像我覺得加載一個完整的庫,只是爲了這個效果不好 –

+1

幾乎每個人都使用Robert Penner的算法:http://www.robertpenner.com/easing/ – BadFeelingAboutThis

回答

2

你的簡陋是因爲它只在mousemove事件上運行。如果你把它分解成一個區間(比如每秒30幀),它會更平滑。這種方式即使在鼠標停止後也會繼續緩解。

var $container = $('#container'); 
var contWidth = $container.width(); 
var $point = $('.point'); 
var delay = 100; 
var decay = .1; 

var intervalId; 
var mouseX, mouseY; 

//this function is called 30 times per second. 
function ticker(){ 
    $point.each(function(){ 
     if(mouseX > (contWidth - $point.width())){ 
      mouseX = (contWidth - $point.width()); //instead of returning, just set the value to the max 
     } 
     var xp = $(this).position().left; 
     xp += parseFloat((mouseX - xp) * decay); //using a decay variable for easier tweaking 
     $(this).css({ 
      left: xp 
     }); 
    }); 
} 

//this interval calls the ticker function every 33 milliseconds 
intervalId = setInterval(ticker, 33); //33 millisecond is about 30 fps (16 would be roughly 60fps) 

$container.mousemove(function(e){ 
    mouseX = e.offsetX; //store the current mouse position so we can reference it during the interval 
    mouseY = e.offsetY; 
}); 
+0

這是工作得很好,感覺順利,所有,但不明白什麼是我使用的setTiemout和你的setInterval之間的區別,幾乎是代碼的這個portions。 (if(!intervalId)){intervalId = setInterval(function(){... },33); // 30 fps' –

+1

設置間隔一遍又一遍地運行,setTimeout只運行一次。所以在你的setTimeout函數被調用一次之前(每次鼠標移動)。使用setInterval它獨立於鼠標移動事件,每運行33毫秒。 – BadFeelingAboutThis

+0

很酷這對我很好。最後一個問題。如果我希望藍點與鼠標方向相反,我會怎麼做呢?我做了'$(this).css({left:xp * -1});'但它的表現真的很奇怪 –

1

看看這個。不知道這是你想要的,但它確實是「一個」的伎倆。

$container.mousemove(function(e){ 

    var xp = e.clientX-offset; 
    blue.css({ 
     left: xp+'px' 
    }); 

}); 

http://jsfiddle.net/d65yan/8RB24/2/

看的.blue {} CSS 一些vendro前綴需要,如果你想支持舊版本MOZ和鍍鉻的,忘掉即達9版雖然

+0

這是一個很好的我認爲,只是在短暫的鼠標移動感覺像跳躍,但可能是一個很好的解決方案 –

+0

這是因爲啓動延遲和轉換函數,延遲越小,它會響應小變化越好,但那麼你將失去延遲..也如果你改變線性它的功能會更好地響應。現在我正在使用easy,但你可以設置其他人甚至定製的,檢查出css轉換更多細節 –

+0

如果瀏覽器兼容性不是'一個問題(並且你不需要任何額外的邏輯如何移動),這是一個更有效和優雅的做法,而不是間隔 – BadFeelingAboutThis