Kotlin の ViewModel で実装する 30 秒タイマー ~途中停止にも対応~

2025/02/10に公開

この記事では、Kotlin の ViewModel 内で 30 秒間のカウントダウンタイマーを実装する方法について解説します。コルーチンを利用した非同期処理や、タイマーの途中停止に対応する実装例を紹介します。

実装のポイント

  • LiveData による状態管理
    タイマーの残り時間を MutableLiveData 経由で管理し、UI に通知します。

  • コルーチンによる非同期処理
    viewModelScope.launch を使用して、ViewModel のライフサイクルに合わせた非同期処理を実行します。

  • タイマーの途中停止
    実行中のタイマー処理を Job として保持し、必要に応じてキャンセルすることができます。

コード例

以下のコードは、上記のポイントを踏まえた 30 秒タイマーの実装例です。

import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.ViewModel
import androidx.lifecycle.viewModelScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch

class TimerViewModel : ViewModel() {

    // タイマーの残り時間(ミリ秒)を監視する LiveData
    private val _remainingTime = MutableLiveData<Long>()
    val remainingTime: LiveData<Long> get() = _remainingTime

    // タイマー用の Job
    private var timerJob: Job? = null

    /**
     * タイマーを開始します。
     * 30秒(30,000ミリ秒)からカウントダウンを開始し、
     * 定期的に _remainingTime に残り時間を通知します。
     */
    fun startTimer() {
        // 既にタイマーが動いていればキャンセル
        timerJob?.cancel()

        timerJob = viewModelScope.launch {
            val totalTime = 30_000L // 30秒
            var elapsedTime = 0L

            // 100ミリ秒ごとに更新
            while (elapsedTime < totalTime) {
                // タイマーの残り時間を更新(ミリ秒単位)
                _remainingTime.postValue(totalTime - elapsedTime)
                delay(100L)
                elapsedTime += 100L
            }
            // カウントダウン終了時は 0 をセット
            _remainingTime.postValue(0L)
        }
    }

    /**
     * タイマーを途中で停止します。
     */
    fun stopTimer() {
        timerJob?.cancel()
        timerJob = null
    }
}

コード解説

  1. LiveData の活用
    MutableLiveData を用いてタイマーの残り時間を管理しています。
    UI 側ではこの値の変化を監視することで、カウントダウンの進行状況に合わせた表示更新が可能です。

  2. viewModelScope とコルーチン
    viewModelScope.launch により、ViewModel のライフサイクルに連動した非同期処理が行えます。
    delay(100L) を用いて 100 ミリ秒ごとにタイマーの状態を更新しています。

  3. キャンセル機能
    stopTimer() メソッドで実行中のタイマー処理(Job)をキャンセルすることにより、ユーザー操作に応じたタイマー制御が可能となります。

まとめ

Kotlin の ViewModel とコルーチンを組み合わせることで、シンプルかつ柔軟なタイマー機能が実装できます。
この記事で紹介した 30 秒タイマーの実装例を参考に、実際のプロジェクトでの活用を検討してみてください。

この記事に関するご意見やご質問は、コメント欄でお知らせいただけると幸いです。
お読みいただきありがとうございました。

Discussion