       # Skip some frame updates unless we're playing and not at end (or we haven't drawn much yet)
       frameAdvanced = (@playing and @currentFrame < lastFrame) or @totalFramesDrawn < 2
       if frameAdvanced and @playing
-        @currentFrame += @world.frameRate / @options.frameRate
+        advanceBy = @world.frameRate / @options.frameRate
+        if @fastForwardingToFrame and @currentFrame < @fastForwardingToFrame - advanceBy
+          advanceBy = Math.min(@currentFrame + advanceBy * @fastForwardingSpeed, @fastForwardingToFrame) - @currentFrame
+        else if @fastForwardingToFrame
+          @fastForwardingToFrame = @fastForwardingSpeed = null
+        @currentFrame += advanceBy
         @currentFrame = Math.min @currentFrame, lastFrame
       newWorldFrame = Math.floor @currentFrame
       worldFrameAdvanced = newWorldFrame isnt oldWorldFrame

    @setPlayingCalled = true
    if @playing and @currentFrame >= (@world.totalFrames - 5)
      @currentFrame = 0
    if @fastForwarding and not @playing
      @setProgress @currentFrame / @world.frames.length

  onSetTime: (e) ->
    toFrame = @currentFrame


    @setWorld event.world
    @onFrameChanged(true)
    if @playing and (ffToFrame = Math.min(event.firstChangedFrame, @frameBeforeCast, event.world.frames.length)) and ffToFrame > @currentFrame
      @fastForwardingToFrame = ffToFrame
      @fastForwardingSpeed = Math.max 4, 4 * 90 / (@world.maxTotalFrames * @world.dt)

  # initialization

