【问题标题】:Timer drags a bit when too much is happening当发生太多事情时,计时器会拖一点
【发布时间】:2021-02-21 20:48:25
【问题描述】:

我正在开发一个计时器,它需要进行一些计算并以一定的时间间隔运行一些功能。我试图保持尽可能大的间隔,但我需要它是一种细粒度的。

这里是周期性计时器,其中包含一些需要发生的事情。 如您所见,如果满足某些条件,每一秒(经过 % 1000 == 0 的毫秒数)它都会做一些事情。但我也需要每隔 10 毫秒检查一次。

这似乎有点过分了,在运行计时器 2 分钟后,它已经落后了 1 秒。我想我是以错误的方式接近这个。我可以/应该以某种方式将所有逻辑放在一个只运行异步的函数中,以便计时器可以继续运行。

如果计时器显示不时拖动几毫秒,如果它稍后赶上,这不是世界末日。但是现在整个计时器只是拖着。

_timer = Timer.periodic(Duration(milliseconds: 10), (timer) {
  passedMilliseconds = passedMilliseconds + 10;

  // METRONOME BEEP AND BLINK
  if (passedMilliseconds % currentTimerSettingsObject.milliSecondDivider == 0) {
    _playMetronomeBeep();
    _startMetronomeBlink();
  }

  // ONE SECOND
  if (passedMilliseconds % 1000 == 0) {
    secondsDuration--;

    // COUNTDOWN
    if (secondsDuration < currentTimerSettingsObject.countDown + 1) {
      _player.play('sounds/beep.mp3');
    }

    // SET COUNTDOWN START VALUES
    if (secondsDuration == currentTimerSettingsObject.countDown) {
      isCountdown = true;
    }
    notifyListeners();
  }

  // TIME IS UP
  if (secondsDuration < 0) {
    switchToNextTimer();
    notifyListeners();
  }
});

}

【问题讨论】:

标签: flutter dart asynchronous timer


【解决方案1】:

您不能依靠计时器来准确地按时传递事件。您需要使用更精确的方法,而不是简单地将计数器在每个刻度上增加 10。一个例子是在计时器之前启动Stopwatch,然后(知道您的滴答声只会以大约 10 毫秒的间隔)读取stopwatch.elapsedMilliseconds 并以此为基础做出决定。

你需要稍微改变你的逻辑。例如,您想知道何时通过 1 秒边界。以前,精确增量为 10,您知道最终会达到 1000 轮。现在,您可能会看到 995 后面跟着 1006,并且需要推断您已经越过了第二个边界来运行您的每秒逻辑。

【讨论】:

  • 谢谢你。它最终成为我的解决方案。我在 10 毫秒运行计时器的同时运行秒表。然后我从秒表到最后一个完整的 10 毫秒(即 37890 到 37899 变为 37890)的经过的毫秒数。每个周期周期我都会保存当前经过的最低毫秒数,并将其与前一个周期的形式进行比较。这样,我可以以 10 毫秒的粒度做任何我需要做的事情。我用秒做同样的事情,这也让我能够每整秒做一次事情。
猜你喜欢
  • 1970-01-01
  • 2018-11-13
  • 2013-04-22
  • 2018-07-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-10
相关资源
最近更新 更多