onVideoProgress_() {
    if (!this.video_) {
      return;
    }

    const isQuartile = (quartilePercent, currentPercent) => {
      const NumberUtils = shaka.util.NumberUtils;

      if ((NumberUtils.isFloatEqual(quartilePercent, currentPercent) ||
          currentPercent > quartilePercent) &&
          this.completionPercent_ < quartilePercent) {
        this.completionPercent_ = quartilePercent;
        return true;
      }
      return false;
    };

    const checkEnded = () => {
      if (this.config_ && this.config_.playRangeEnd != Infinity) {
        // Make sure the video stops when we reach the end.
        // This is required when there is a custom playRangeEnd specified.
        if (this.isEnded()) {
          this.video_.pause();
        }
      }
    };

    const seekRange = this.seekRange();
    const duration = seekRange.end - seekRange.start;
    const completionRatio =
        duration > 0 ? this.video_.currentTime / duration : 0;

    if (isNaN(completionRatio)) {
      return;
    }

    const percent = completionRatio * 100;

    let event;
    if (isQuartile(0, percent)) {
      event = shaka.Player.makeEvent_(shaka.util.FakeEvent.EventName.Started);
    } else if (isQuartile(25, percent)) {
      event = shaka.Player.makeEvent_(
          shaka.util.FakeEvent.EventName.FirstQuartile);
    } else if (isQuartile(50, percent)) {
      event = shaka.Player.makeEvent_(
          shaka.util.FakeEvent.EventName.Midpoint);
    } else if (isQuartile(75, percent)) {
      event = shaka.Player.makeEvent_(
          shaka.util.FakeEvent.EventName.ThirdQuartile);
    } else if (isQuartile(100, percent) || percent > 100) {
      event = shaka.Player.makeEvent_(
          shaka.util.FakeEvent.EventName.Complete);
      checkEnded();
    } else {
      checkEnded();
    }

    if (event) {
      this.dispatchEvent(event);
    }
  }
Callback for video progress events

@private