JOURNAL

スマホブラウザの『バックグラウンドタブ』はどれくらい制限されるのか

「バックグラウンドのタブって、JSの処理どこまで制限されるんだろう」というのは、SPLIT TIMER作ってるとき避けて通れなかったテーマです。これまでの記事でも何度か触れてる話ですが、今回は実際に調べた内容をもう少しちゃんとまとめておきます。

setIntervalは裏切る

多くのブラウザは、非表示タブのsetIntervalsetTimeoutの実行間隔を、バッテリーのために意図的に間引きます。1秒ごとに設定してるつもりでも、裏に回すと数秒〜下手すれば数十秒に1回しか動かないことがある。

これを知らずに素朴な実装をすると、「なんで裏に回すとズレるの」で数時間潰すことになります。

自分がまさにそれでした。

対処は「差分から逆算」

対処法としては、「一定間隔で数える」んじゃなくて「開始時刻を記録しておいて、都度、今の時刻との差分から残り時間を計算し直す」方式にするのが定石です。これなら間引きが起きても、タブが表に戻った瞬間に正しい値へちゃんと復帰します。

あとはdocument.visibilityStateでタブが表示中か非表示かを判定できるので、非表示になったタイミングを検知して、戻ったときに再計算する、みたいな合わせ技も使えます。

document.addEventListener('visibilitychange', () => {
  if (document.visibilityState === 'visible') {
    recalcRemainingTime(); // 表に戻った瞬間に再計算
  }
});

ブラウザの省電力機能と真正面から戦っても勝ち目はありません。

「そういうものだ」と割り切って、その前提で設計を組み立てるのが結局一番早い、というのがこのテーマを何度も扱ってきた自分の結論です。