ワダチを作る #18:iPad のホーム画面のアプリだけで、ロック中の一時停止のあと音が鳴らない。実機の記録を頼りに、4 回で直した

前回(#17)は、習慣の編集の画面と記録の画面の直しでした。今回は、ずっと残っていた、坐禅のタイマーの不具合の話です。

  • iPad のホーム画面のアプリだけで、ロック画面の一時停止のあと、音が鳴らない
  • 最初の直し方は、実機で効かなかった
  • 実機の記録で原因を確かめて、4 回目で直った
  • コードの読みやすさの見直しと、本番リリース

どんな不具合か

ワダチの坐禅のタイマーは、開始の鐘・環境音(雨・波)・終わりの鐘を 1 本の音声にして、<audio> で流しています。残り時間も、音声の再生位置で決めています(#4)。

自分は、iPad mini をホーム画面のアプリ(PWA)にして、画面をロックしたまま瞑想します。そこで、次のことが起きていました。

  • ロック画面で一時停止して、再生すると、環境音が鳴らない
  • 一時停止 → 再生 → 一時停止すると、経過時間が戻る

端末ごとに試すと、起きるのは iPad のホーム画面のアプリだけでした。

端末 Safari ホーム画面のアプリ
iPhone 問題なし 問題なし
iPad 問題なし 不具合

コードは、どの端末も同じです。iPad のホーム画面のアプリにだけある癖、ということになります。

推測は、外れていた

最初の見立ては、「一時停止のあいだに、iPad がページを止めて、読み直している」でした。読み直されれば、状態が初めに戻る(時間が戻る)し、音声も読み込み直されない(音が鳴らない)からです。

確かめるため、前に、タイマーの画面に診断の記録を付けてありました。音声のすべての合図(再生・一時停止・位置の移動など)と再生位置を、時刻つきで端末に残し、あとで写せるものです。

iPad で試して、記録を貼ってもらうと、見立ては外れでした。

  • ページは、読み直されていなかった(記録は、開始から止めるまで、ひと続き)
  • ロック中に、一時停止のあとで再生すると、<audio> は「再生中」と言うのに、再生位置が進まない(音が出ていない)

「本当に止めた音声を、ロック中にもう一度鳴らせない」という、iPad のホーム画面のアプリの癖でした。こちらからは、直しようがありません。

直し方:止めずに、止めたふりをする

それなら、一時停止のときに、音声を本当には止めなければよいと考えました。

  • 一時停止のとき、止めた位置を覚えておき、音声は流し続ける
  • 残り時間・座った時間は、覚えた位置で止める
  • 再開のとき、覚えた位置に戻す

「やわらかい一時停止」と呼んでいます。iPad のホーム画面のアプリのときだけ、この形にします(ほかの端末は、今までどおり本当に止める)。

1 回目と 2 回目:まだ鳴らない

1 回目は、一時停止のあいだ、音を消して(ミュートして)流し続ける形にしました。手元の自動テストは通りました。ところが、iPad で試すと、ロック画面の再生を押しても、戻りませんでした。

2 回目は、ロック画面のボタンの受け方を直しました。やわらかい一時停止のあいだ、音声は流れ続けているので、iPad のロック画面は、ボタンを「一時停止」の形のまま出します。そこで、届いた操作の名前(再生か一時停止か)ではなく、今の状態で切り替えるようにしました。これでも、直りませんでした。

3 回目:診断の記録を、アプリで見られるようにした

ここで、もう一度、実機の記録を見ることにしました。ところが、診断の記録は、URL に ?debug を付けたときだけ出す作りです(ふだん使う人に、開発者向けの文を見せないため)。ホーム画面のアプリには、URL を打つ欄がありません。

3 回目は、そのための直しです。タイマーの画面の見出しを、3 秒以内に 5 回続けて押すと、診断の記録が出るようにしました。

4 回目:音を消すと、ロック画面の操作が届かない

記録で分かったのは、音を消すと、iOS が、ロック画面のボタンの操作を、アプリに届けなくなることでした。音が出ていない音声は、iOS にとって「再生中のもの」ではないようです。

そこで、音を消すのをやめました。

  • 音声の最後に、60 秒の無音を足しておく
  • 一時停止のときは、その無音の部分に飛び、音を消さずに流す(聞こえるのは無音)
  • 無音の終わりが近づいたら、無音の始めに戻す(一時停止が長くても、音声が終わらない)

これで、iPad mini のホーム画面のアプリで、ロック画面の一時停止 → 再生 → 一時停止 → 再生が、どれもアプリに届き、続きから環境音が鳴り、時間も戻らなくなりました。iPhone と iPad の Safari も、前と変わらないことを確かめています。

推測で直さず、記録を持ち帰る

振り返ると、1 回目・2 回目は、どちらも推測で直していました。手元の自動テストは通りますが、実機の癖は、手元では起こせません。

直ったのは、実機の記録を持ち帰れる仕組みがあったからです。診断の記録は、公開の前に消す予定で、Issue も作ってありました。今回のことで、今の形(?debug、または見出しを 5 回)で残すことにしました。

コードの読みやすさの見直し

ほかに、公開の前にもらったレビュー(#14)の、保守についての指摘 6 件も片付けました。どれも、動きは変えない直しです。

  • 習慣の編集の、保存の処理が長い → 内容の欄を読む部分を分けた(約 100 行 → 約 60 行)
  • 記録を読む処理が 4 つある → 1 つにしか使っていなかったものを外した
  • エラーのページに、色の値を直書きしている → 直書きは避けられない(アプリの CSS を読み込めないページ)ので、値を 1 か所にまとめ、デザインの値とずれたらテストが落ちるようにした
  • 期間の判定の式が、2 か所にある → 1 か所にまとめた
  • 日本の時刻(+9 時間)の計算が、4 か所にある → 1 か所にまとめた
  • 習慣の並び順を、1 から振り直したほうがよい → やめた。朝と夜の習慣が同じ列を使うので、片方を振り直すと、もう片方の値と重なる

6 件のうち、何を直して、何を直さなかったかは、理由も含めて Issue に残しました。70 代の自分が読んで、「なぜこうなっているのか」が分かるように、です。

CI が、15 分で打ち切られた

今日は、PR の CI(GitHub Actions)が 2 回、15 分の上限で打ち切られました。テストが遅いのではなく、テスト用のブラウザを毎回ダウンロードする時間が、10〜14 分かかった回があったためです。やり直すと、通りました。

Actions の無料の枠(月 2,000 分。ハコヅミと共有)は、今月はぎりぎりです。ブラウザを毎回ダウンロードしない方法と合わせて、来月に直します。

本番に出した

ここまでの直しを、本番に出しました。

  • iPad のホーム画面のアプリのタイマー(今回)
  • やらない曜日の記録・外すときの確認・始めた日の直し・登録の画面で内容を足す(#17)
  • コードの読みやすさの見直し

これで、ステップ2 から持ち越していた残件(やらない曜日の記録と、iPad のタイマー)が、どちらも片付きました。

おわりに

  • 実機でしか起きない不具合は、推測で直さず、実機の記録を持ち帰る仕組みを先に作る
  • 音を消した音声は、iOS には「再生中」ではない。止めたふりは、無音を流して作る
  • レビューの指摘は、直さないものにも、理由を書いて残す

次は、環境音を本物の素材にする話と、CI のブラウザのダウンロードの直しを進めます。

← トップページに戻る