简体   繁体   English

如何控制动画速度(requestAnimationFrame)?

[英]How to control animation speed (requestAnimationFrame)?

I change the text color with requestAnimationFrame(animate);我使用requestAnimationFrame(animate);更改文本颜色requestAnimationFrame(animate); function:功能:

requestAnimationFrame(animate);

function animate(time){
  ... // change text color here
  if (offset_s < offset_e) {requestAnimationFrame(animate);}
}

offset_s and offset_s indicates start and end positions of the text for color change. offset_soffset_s表示颜色变化的文本的开始和结束位置。 In some cases the animation should last for 2 seconds, but in order cases - for 5 seconds, but offset_e - offset_s could be the same in these two cases.在某些情况下,动画应该持续 2 秒,但在顺序情况下 - 5 秒,但offset_e - offset_s在这两种情况下可能相同。 What can I do to control the speed of animation based on given time in seconds/milliseconds?我该怎么做才能根据给定的时间(以秒/毫秒为单位)控制动画的速度?

From the tags of the question i can only see that you animate something drawn on canvas and thats why u cannot use css-animation or jquery-animation.从问题的标签中,我只能看到您在画布上绘制了一些动画,这就是为什么您不能使用 css-animation 或 jquery-animation。

You have to control the length of the animation by calculating the time difference.您必须通过计算时间差来控制动画的长度。

u can do it similar to this example你可以像这个例子那样做

function start_animate(duration) {
  var requestID;
  var startTime =null; 
  var time ;   

  var animate = function(time) {


   time = new Date().getTime(); //millisecond-timstamp

   if (startTime === null) {
        startTime = time;
   }
   var progress = time - startTime;

   if (progress < duration ) {

       if(offset_s < offset_e){
         // change text color here

       }
       requestID= requestAnimationFrame(animate);
   } 
   else{
      cancelAnimationFrame(requestID);
   }
   requestID=requestAnimationFrame(animate);
  }
  animate();
}

trigger your animation and call start_animate(2000) //duration in millisecond 1000=1 sec触发动画并调用 start_animate(2000) //duration in 毫秒 1000=1 sec

You should separate concerns clearly.你应该清楚地分开关注点。
Have a single requestAnimationFrame running, which computes the current animation time and calls every update and draw related functions.运行单个 requestAnimationFrame,它计算当前动画时间并调用每次更新和绘制相关函数。
Then your animations would be handled by a function (or class instance if you go OOP) that deals with the current animation time.然后你的动画将由处理当前动画时间的函数(或类实例,如果你去 OOP)处理。

Just some direction for the code :只是代码的一些方向:

var animationTime = -1;
var _lastAnimationTime = -1;

function launchAnimation() {
    requestAnimationFrame(_launchAnimation);
}    

function _launchAnimation(time) {
    animationTime = 0;
    _lastAnimationTime = time;
    requestAnimationFrame(animate);
}

function animate(time){
  requestAnimationFrame(animate);
  var dt = time - _lastAnimationTime ;
  _lastAnimationTime = time;
  animationTime += dt;

  // here call every draw / update functions
  //  ...
  animationHandler.update(animationTime);
  animationHandler.draw(context);
}

To start your 'engine', just call launchAnimation then you'll have a valid animationTime and dt to deal with.要启动您的“引擎”,只需调用launchAnimation您就会有一个有效的animationTimedt来处理。

I'd make animationHandler an instance of an AnimationHandler class, that allows to add/remove/update/draw animations.我会让animationHandler一个AnimationHandler类的实例,它允许添加/删除/更新/绘制动画。

I suggest to use setInterval function in JavaScript.我建议在 JavaScript 中使用 setInterval 函数。

requestAnimationFrame really needs some 'ugly' calculations. requestAnimationFrame确实需要一些“丑陋”的计算。 Don't believe me?不相信我? Scroll up, you will see...向上滚动,你会看到...

So, to make setInterval function as handy as rAF(requestAnimationFrame) store the function inside of variable.因此,要使setInterval函数像 rAF(requestAnimationFrame) 一样方便,请将函数存储在变量中。 Here is an example:下面是一个例子:

var gameLoop = setInterval(function() {
  update();
  draw();
  if (gameOver)
    clearInterval(gameLoop);
}, 1000/FPS);

given way, you can control your FPS and pick correct velocity for your objects.给定方式,您可以控制您的 FPS 并为您的对象选择正确的速度。

I typically do something like我通常会做类似的事情

es6 es6

constructor() {
    this.draw();
}

draw() {
    const fps30 = 1000 / 30;
    const fps60 = 1000 / 60;
    window.requestAnimationFrame(() => {
        setTimeout(this.draw.bind(this), fps30);
    });
}

es5 es5

function DrawingProgram() {
    this.draw();
}

DrawingProgram.prototype.draw = function() {
    var fps30 = 1000/30;
    var fps60 = 1000/60;
    var self = this;
    window.requestAnimationFrame(function() {
        window.setTimeout(function() {
            self.draw(); // you could also use apply/call here if you want
        }, fps30)
    });
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM