【问题标题】:Move object from one point to another based on duration根据持续时间将对象从一个点移动到另一个点
【发布时间】:2011-06-21 19:16:45
【问题描述】:

一段时间以来一直在思考这个问题,并在网上寻找解决方案,但没有效果。

基本上,如果我有一个精灵,例如位于 (10,10),我想将它移动到 (50,100),整个过程需要 2 秒或我指定的任何持续时间。这背后的确切数学是什么?我使用基于距离的解决方案来确定速度,但只是使用随机修改器来控制过程。我需要更精确的东西才能在设定的持续时间内准确执行。

对于这个问题的任何帮助将不胜感激!

【问题讨论】:

    标签: c# javascript actionscript-3


    【解决方案1】:

    假设线性插值(即以恒定速率从起始位置直线移动到结束位置):

    从起点到终点的向量是终点 - 起点,即对于您的示例 (40,90)。

    如果您希望这种情况在两秒内发生,则需要将其除以二以获得每秒行进的距离,例如 (20,45) 每秒。

    要获取任何给定时间的位置,首先记录开始时间并计算当前时间减去开始时间(以秒为单位)。因此,如果动画从 12:01:30.000 开始,现在是 12:01:31.500,那么距离动画开始已经过去了 1.5 秒。

    要获取当前位置,您需要将开始位置添加到每秒移动量 * 经过的时间,因此在我的示例中:

    (10,10) + (20,45) * 1.5 = (10,10) + (30, 67.5) = (40, 77.5)

    【讨论】:

      【解决方案2】:

      这只是插值和时间的问题。 有线性的、正弦的、二次的、...

      下面是 actionscript 中的更多信息和示例:link

      【讨论】:

        【解决方案3】:

        仔细看看 jQuery 的动画算法...也许你可以使用一些代码。

        http://code.jquery.com/jquery-1.6.1.js(搜索“custom:”作为起点)。

        【讨论】:

          【解决方案4】:

          您需要一些信息来执行此操作,即开始位置、结束位置、持续时间和经过的时间。

          以下是 actionscript 中的示例:

          package {
              import flash.utils.getTimer;
              import flash.events.Event;
              import flash.display.Shape;
              import flash.geom.Point;
              import flash.display.Sprite;
          
              public class Mover extends Sprite {
          
                  private var circle      :Shape;
                  private var start       :Point;
                  private var end         :Point;
                  private var duration    :int;
          
                  public function Mover() {
          
                      // first we create something to move, like, a circle
                      circle = new Shape();
                      circle.graphics.beginFill(0xff00ff);
                      circle.graphics.drawCircle(0, 0, 20);
                      addChild(circle);
          
                      // start and end positions
                      start = new Point(0, 0);
                      end = new Point(100, 100);
          
                      // and finally, the duration, i'm using milliseconds
                      duration = 2000;
          
                      // this event handler will run each frame
                      addEventListener(Event.ENTER_FRAME, handleEnterFrame);
                  }
          
                  private function handleEnterFrame(event:Event):void {
                      // we figure out how much of the animation has elapsed by using getTimer
                      // should you want to use a start time, add it here 
                      var progress:Number = getTimer() / duration;
          
                      // we need to clamp our progress so we don't under- or overshoot the target
                      if(progress < 0) progress = 0;
                      if(progress > 1) progress = 1;
          
          
                      // then it's a matter of setting the position
                      // we use the start position as a base and then gradually add in 
                      // the difference between the start and the end
                      circle.x = start.x + (end.x - start.x) * progress;
                      circle.y = start.y + (end.y - start.y) * progress;  
                  }
              }
          }
          

          如果您对 如何 不是很感兴趣并且只想要结果,我全心全意地推荐一个补间引擎,如 TweenLite 或其他无数引擎。千万别用flash自带的,有点垃圾。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2017-11-25
            • 1970-01-01
            • 2011-06-03
            • 2019-12-03
            • 2012-06-30
            相关资源
            最近更新 更多