     # Time only advances
     if time > @time || time == 0
       @time = time
-      @fireCallbacks()
+      if @time >= @nextThreshold
+        @fireCallbacks()
+        @updateThreshold() # Descriptors change their registration time when isLoop = true
     else
       throw new Error "Time invalid."
     time

    @time = 0 # Initialize to 0 so any callers using getTime() can correctly
              # perform offset math.

  getTime: ->
    @time


    while descriptor = @dequeueNextDescriptor()
      descriptor.callback.apply(undefined)

  invalidateThreshold: ->
    @nextThreshold = 0

  updateThreshold: ->
    @nextThreshold = Number.POSITIVE_INFINITY
    for callback in @callbackDescriptors
      @nextThreshold = Math.min( @nextThreshold, callback.registrationTime + callback.interval )

  invalidateBeatLength: ->
    for descriptor in @callbackDescriptors
      if descriptor.interval.hasValueInBeats()
        descriptor.interval = descriptor.interval.beats()
    @invalidateThreshold()


# All timer DSL functions (every, until, after) are called with an instance of
