React timer hookでタイマーやストップウォッチを実装してみた

2021.07.19

こんにちは、CX事業本部 IoT事業部の若槻です。

時間経過により画面遷移をするReactアプリの実装を検討していたところ、React timer hookというパッケージを見つけました。

React timer hookは、Reactのカスタムフックで、時間のロジックや状態の処理、タイマーやストップウォッチの機能をReactコンポーネントに簡単に実装することができます。

今回は、React(TypeScript)でreact-timer-hookを利用してタイマーやストップウォッチを実装してみました。

インストール

% npm i react-timer-hook

実装

基本的にreadmeに記載のデモ用スクリプトを使用していますが、TypeScriptで動かせるように(一部強引に)型付けを行っています。

タイマー

useTimerを使用すると画面上でタイマー機能を実装できます。

useTimer.ts

import React from "react";
import { useTimer } from "react-timer-hook";

function MyTimer({ expiryTimestamp }: { expiryTimestamp: number }) {
  const {
    seconds,
    minutes,
    hours,
    days,
    isRunning,
    start,
    pause,
    resume,
    restart,
  } = useTimer({
    expiryTimestamp,
    onExpire: () => console.warn("onExpire called"),
  });

  return (
    <div style={{ textAlign: "center" }}>
      <h1>react-timer-hook </h1>
      <p>Timer Demo</p>
      <div style={{ fontSize: "100px" }}>
        <span>{days}</span>:<span>{hours}</span>:<span>{minutes}</span>:
        <span>{seconds}</span>
      </div>
      <p>{isRunning ? "Running" : "Not running"}</p>
      <button onClick={start}>Start</button>
      <button onClick={pause}>Pause</button>
      <button onClick={resume}>Resume</button>
      <button
        onClick={() => {
          // Restarts to 5 minutes timer
          const time = new Date();
          time.setSeconds(time.getSeconds() + 300);
          restart(time as unknown as number);
        }}
      >
        Restart
      </button>
    </div>
  );
}

export default function App() {
  const time = new Date();
  time.setSeconds(time.getSeconds() + 600); // 10 minutes timer
  return (
    <div>
      <MyTimer expiryTimestamp={time as unknown as number} />
    </div>
  );
}

指定時間からタイマーのカウントダウンが開始し、停止(pause)、レジューム(resume)、指定時間からの再スタート(restart)のアクションがボタンクリックにより可能です。

ストップウォッチ

useStopwatchを使用すると画面上でストップウォッチ機能を実装できます。

useStopwatch.ts

import React from "react";
import { useStopwatch } from "react-timer-hook";

function MyStopwatch() {
  const { seconds, minutes, hours, days, isRunning, start, pause, reset } =
    useStopwatch({ autoStart: true });

  return (
    <div style={{ textAlign: "center" }}>
      <h1>react-timer-hook</h1>
      <p>Stopwatch Demo</p>
      <div style={{ fontSize: "100px" }}>
        <span>{days}</span>:<span>{hours}</span>:<span>{minutes}</span>:
        <span>{seconds}</span>
      </div>
      <p>{isRunning ? "Running" : "Not running"}</p>
      <button onClick={start}>Start</button>
      <button onClick={pause}>Pause</button>
      <button
        onClick={reset as unknown as React.MouseEventHandler<HTMLButtonElement>}
      >
        Reset
      </button>
    </div>
  );
}

export default function App() {
  return (
    <div>
      <MyStopwatch />
    </div>
  );
}

ストップウォッチのカウントアップが開始し、停止(pause)、指定時間へのリセット(reset)のアクションがボタンクリックにより可能です。

現在時刻の表示

useTimeを使用すると画面上で現在時刻の表示を実装できます。

useTime.ts

import React from "react";
import { useTime } from "react-timer-hook";

function MyTime() {
  const { seconds, minutes, hours, ampm } = useTime({ format: "12-hour" });

  return (
    <div style={{ textAlign: "center" }}>
      <h1>react-timer-hook </h1>
      <p>Current Time Demo</p>
      <div style={{ fontSize: "100px" }}>
        <span>{hours}</span>:<span>{minutes}</span>:<span>{seconds}</span>
        <span>{ampm}</span>
      </div>
    </div>
  );
}

export default function App() {
  return (
    <div>
      <MyTime />
    </div>
  );
}

デジタル時計のように現在時刻を1秒ごとに刻一刻と表示できています。

おわりに

React(TypeScript)でreact-timer-hookを利用してタイマーやストップウォッチを実装してみました。

基本的なできることは確認できたので、次はReact timer hookを使って時間経過による画面遷移を実装できるのか(または使わなくてもできるのか)確認していきたいと思います。

参考

以上