mirror of
https://github.com/CorentinTh/it-tools.git
synced 2025-04-20 14:56:17 -04:00
refactor(chronometer): improved chronometer precision
This commit is contained in:
parent
fda0b0ca25
commit
e48d60b1ed
3 changed files with 37 additions and 17 deletions
|
@ -1,12 +1,13 @@
|
||||||
import { describe, expect, it } from 'vitest';
|
import { describe, expect, it } from 'vitest';
|
||||||
import { formatChronometerTime } from './chronometer.service';
|
import { formatMs } from './chronometer.service';
|
||||||
|
|
||||||
describe('chronometer', () => {
|
describe('chronometer', () => {
|
||||||
describe('formatChronometerTime', () => {
|
describe('formatChronometerTime', () => {
|
||||||
it('format the elapsed time', () => {
|
it('format the elapsed time', () => {
|
||||||
expect(formatChronometerTime({ elapsed: 123456 })).toEqual('02:03.456');
|
expect(formatMs(0)).toEqual('00:00.000');
|
||||||
expect(formatChronometerTime({ elapsed: 123456, msPerUnit: 100 })).toEqual('03:25:45.600');
|
expect(formatMs(1)).toEqual('00:00.001');
|
||||||
expect(formatChronometerTime({ elapsed: 12345600 })).toEqual('03:25:45.600');
|
expect(formatMs(123456)).toEqual('02:03.456');
|
||||||
|
expect(formatMs(12345600)).toEqual('03:25:45.600');
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,10 +1,8 @@
|
||||||
export function formatChronometerTime({ elapsed, msPerUnit = 1 }: { elapsed: number; msPerUnit?: number }) {
|
export function formatMs(msTotal: number) {
|
||||||
const elapsedMs = elapsed * msPerUnit;
|
const ms = msTotal % 1000;
|
||||||
|
const secs = ((msTotal - ms) / 1000) % 60;
|
||||||
const ms = elapsedMs % 1000;
|
const mins = (((msTotal - ms) / 1000 - secs) / 60) % 60;
|
||||||
const secs = ((elapsedMs - ms) / 1000) % 60;
|
const hrs = (((msTotal - ms) / 1000 - secs) / 60 - mins) / 60;
|
||||||
const mins = (((elapsedMs - ms) / 1000 - secs) / 60) % 60;
|
|
||||||
const hrs = (((elapsedMs - ms) / 1000 - secs) / 60 - mins) / 60;
|
|
||||||
const hrsString = hrs > 0 ? `${hrs.toString().padStart(2, '0')}:` : '';
|
const hrsString = hrs > 0 ? `${hrs.toString().padStart(2, '0')}:` : '';
|
||||||
|
|
||||||
return `${hrsString}${mins.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}.${ms
|
return `${hrsString}${mins.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}.${ms
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
<template>
|
<template>
|
||||||
<div>
|
<div>
|
||||||
<n-card>
|
<n-card>
|
||||||
<div class="duration">{{ formatChronometerTime({ elapsed: counter, msPerUnit }) }}</div>
|
<div class="duration">{{ formatMs(counter) }}</div>
|
||||||
</n-card>
|
</n-card>
|
||||||
<br />
|
<br />
|
||||||
<n-space justify="center">
|
<n-space justify="center">
|
||||||
<n-button v-if="!isActive" secondary type="primary" @click="resume">Start</n-button>
|
<n-button v-if="!isRunning" secondary type="primary" @click="resume">Start</n-button>
|
||||||
<n-button v-else secondary type="warning" @click="pause">Stop</n-button>
|
<n-button v-else secondary type="warning" @click="pause">Stop</n-button>
|
||||||
|
|
||||||
<n-button secondary @click="counter = 0">Reset</n-button>
|
<n-button secondary @click="counter = 0">Reset</n-button>
|
||||||
|
@ -14,12 +14,33 @@
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { useInterval } from '@vueuse/core';
|
import { useRafFn } from '@vueuse/core';
|
||||||
import { formatChronometerTime } from './chronometer.service';
|
import { ref } from 'vue';
|
||||||
|
import { formatMs } from './chronometer.service';
|
||||||
|
|
||||||
const msPerUnit = 10;
|
const isRunning = ref(false);
|
||||||
|
const counter = ref(0);
|
||||||
|
|
||||||
const { counter, pause, resume, isActive } = useInterval(msPerUnit, { controls: true, immediate: false });
|
let previousRafDate = Date.now();
|
||||||
|
const { pause: pauseRaf, resume: resumeRaf } = useRafFn(
|
||||||
|
() => {
|
||||||
|
const deltaMs = Date.now() - previousRafDate;
|
||||||
|
previousRafDate = Date.now();
|
||||||
|
counter.value += deltaMs;
|
||||||
|
},
|
||||||
|
{ immediate: false },
|
||||||
|
);
|
||||||
|
|
||||||
|
function resume() {
|
||||||
|
previousRafDate = Date.now();
|
||||||
|
resumeRaf();
|
||||||
|
isRunning.value = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
function pause() {
|
||||||
|
pauseRaf();
|
||||||
|
isRunning.value = false;
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style lang="less" scoped>
|
<style lang="less" scoped>
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue