Timer.js 2.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. class Timer {
  2. constructor() {
  3. this._previousTime = 0;
  4. this._currentTime = 0;
  5. this._startTime = now();
  6. this._delta = 0;
  7. this._elapsed = 0;
  8. this._timescale = 1;
  9. this._useFixedDelta = false;
  10. this._fixedDelta = 16.67; // ms, corresponds to approx. 60 FPS
  11. // use Page Visibility API to avoid large time delta values
  12. this._usePageVisibilityAPI = ( typeof document !== 'undefined' && document.hidden !== undefined );
  13. if ( this._usePageVisibilityAPI === true ) {
  14. this._pageVisibilityHandler = handleVisibilityChange.bind( this );
  15. document.addEventListener( 'visibilitychange', this._pageVisibilityHandler, false );
  16. }
  17. }
  18. disableFixedDelta() {
  19. this._useFixedDelta = false;
  20. return this;
  21. }
  22. dispose() {
  23. if ( this._usePageVisibilityAPI === true ) {
  24. document.removeEventListener( 'visibilitychange', this._pageVisibilityHandler );
  25. }
  26. return this;
  27. }
  28. enableFixedDelta() {
  29. this._useFixedDelta = true;
  30. return this;
  31. }
  32. getDelta() {
  33. return this._delta / 1000;
  34. }
  35. getElapsed() {
  36. return this._elapsed / 1000;
  37. }
  38. getFixedDelta() {
  39. return this._fixedDelta / 1000;
  40. }
  41. getTimescale() {
  42. return this._timescale;
  43. }
  44. reset() {
  45. this._currentTime = now() - this._startTime;
  46. return this;
  47. }
  48. setFixedDelta( fixedDelta ) {
  49. this._fixedDelta = fixedDelta * 1000;
  50. return this;
  51. }
  52. setTimescale( timescale ) {
  53. this._timescale = timescale;
  54. return this;
  55. }
  56. update() {
  57. if ( this._useFixedDelta === true ) {
  58. this._delta = this._fixedDelta;
  59. } else {
  60. this._previousTime = this._currentTime;
  61. this._currentTime = now() - this._startTime;
  62. this._delta = this._currentTime - this._previousTime;
  63. }
  64. this._delta *= this._timescale;
  65. this._elapsed += this._delta; // _elapsed is the accumulation of all previous deltas
  66. return this;
  67. }
  68. }
  69. function now() {
  70. return ( typeof performance === 'undefined' ? Date : performance ).now();
  71. }
  72. function handleVisibilityChange() {
  73. if ( document.hidden === false ) this.reset();
  74. }
  75. export { Timer };