タイムシフトをサポートする

ユーザーがサービス チャンネルのライブ番組を一時停止、巻き戻し、早送りできるようにするには、テレビ入力サービスでタイムシフトの API を使用します。アプリがタイムシフトをサポートしていれば、ユーザーはコンテンツをよりいっそう柔軟な形で視聴できます。たとえば次のようなことができます。

  • 短期間の中断をするときに番組を一時停止し、重要な瞬間を見逃さないようにする
  • すでに見たコンテンツや興味のないコンテンツを早送りする
  • 番組コンテンツを好きなタイミングまで巻き戻して再視聴する

図 1. タイムシフトに使用される Android TV の再生コントロール

タイムシフトでは、番組データの短い一時的な録画セグメントを使用して、ライブ番組を再生する機能を実装します。タイムシフト録画は現在の再生セッション以外では再生できないため、タイムシフトを使用して番組を一時停止して翌日視聴したり、別のチャンネルに切り替えるときに番組を一時停止して後で視聴したりすることはできません。ユーザーが番組コンテンツを録画して現在の再生セッション以外で視聴できるようにする場合は、テレビ録画の API を使用します。

タイムシフトのサポートを追加する

テレビ入力サービスにタイムシフトのサポートを追加するには、TvInputService.Session クラスでタイムシフトの API を実装し、アプリ内でタイムシフト録画の録画と再生を処理して、入力サービスがタイムシフトをサポートしていることをシステムに通知する必要があります。

実装する必要のある TvInputService.Session メソッドは次のとおりです。

入力サービスがタイムシフトをサポートしていることをシステムに通知する方法について詳しくは、タイムシフトのステータスをシステムに通知するをご覧ください。

TIF Companion Library を使用して TvInputService.Session クラスを実装する場合は、ExoPlayer を使用するタイムシフトの実装が自動的に取得されます。この実装を使用するか、BaseTvInputService.Session のタイムシフト API メソッドをオーバーライドして独自の実装を用意します。TIF Companion Library の使用について詳しくは、TIF Companion Library を使用してテレビ入力サービスを作成するをご覧ください。

セッション開始時にコンテンツを録画する

ユーザーは、チャンネルの再生コントロールにアクセスして(コンテンツの視聴中に [選択] を押して再生コントロールに移動する)、または利用可能な場合はデバイスのリモコンの専用再生コントロールを利用して、番組コンテンツを一時停止、巻き戻し、早送りすることができます。ユーザーは番組コンテンツの視聴中にいつでもタイムシフトを利用できるため、テレビ入力サービスは、ユーザーが onTune() の実装のチャンネルにチューニングしたらすぐにタイムシフト コンテンツの録画を開始する必要があります。この時点で、タイムシフトのステータスをシステムに通知するにある説明のとおり、notifyTimeShiftStatusChanged(int) を呼び出して、録画ができる状態であることをシステムに通知する必要があります。

録画コンテンツ ストレージを管理する

テレビ入力サービスは、タイムシフト録画をアプリの専用ストレージに保存し、システムによって onTimeShiftResume() などのタイムシフト メソッドが呼び出されたときにコンテンツを再生します。 コンテンツがすでにクラウドに保存されており、アプリがクラウド内でタイムシフト録画を管理できる場合、アプリ ストレージの代わりにクラウド ストレージを使用することができます。

コンテンツ内で保護されたコンテンツが使用されている場合、テレビ入力サービスは録画されたコンテンツの適切な暗号化と再生時のコンテンツの復号を行います。

録画された動画コンテンツには大量のストレージが必要になることがあるため、セッションの再生時には録画コンテンツを慎重に管理する必要があります。再生セッション時間がタイムシフト用の録画と保存が可能な時間を上回る場合は、タイムシフト録画を調整して現在のバッファが維持されるようにしながら現在の時間が録画されるようにする必要があります。たとえば、ユーザーがこれまでに 31 分間コンテンツを再生しており、最大タイムシフト録画時間が 30 分間である場合、1 分目から 31 分目までのコンテンツを含むように録画と開始時刻を調整する方法が考えられます。

テレビ入力サービスがストレージ不足のためタイムシフトをサポートできない場合は、システムに通知する必要があります。タイムシフト サポートの制約をシステムに通知する方法について詳しくは、タイムシフトのステータスをシステムに通知するをご覧ください。

ユーザーが別のチャンネルに切り替えたときや再生セッションを終了したときは、録画されたタイムシフト データを削除します。

タイムシフトのステータスをシステムに通知する

テレビ入力サービスがタイムシフトをサポートしている場合、ユーザーがチャンネルにチューニングしたときに notifyTimeShiftStatusChanged(TvInputManager.TIME_SHIFT_STATUS_AVAILABLE)onTune() の実装内で呼び出します。

入力サービスのタイムシフト機能に変更があった場合にシステムに通知するには、notifyTimeShiftStatusChanged(int) を使用します。 たとえば、テレビ入力サービスがストレージ容量の制約などの理由によりタイムシフトをサポートできない場合は、notifyTimeShiftStatusChanged(TvInputManager.TIME_SHIFT_STATUS_UNAVAILABLE) を呼び出します。

テレビ入力サービスがタイムシフトをまったくサポートできない場合は、再生セッションが作成されたときに notifyTimeShiftStatusChanged(TvInputManager.TIME_SHIFT_STATUS_UNSUPPORTED) を呼び出します。システムは、notifyTimeShiftStatusChanged() を呼び出すことのない入力サービスを、タイムシフトをサポートできない入力サービスとして扱います。API レベル 22 以前を使用している入力サービスがこれに該当します。

再生時間をトラッキングする

タイムシフト録画の開始時点は、ユーザーが移動できる最も早い絶対時点(エポックからの経過時間をミリ秒で表したもの)です。これは通常、onTune() が呼び出された後に動画の再生が開始された時点です。 ただし、ユーザーがアプリで録画できる量を上回るコンテンツを視聴する場合、状況によっては、タイムシフトのために新しいセグメントの録画を開始し、それに応じて開始時刻を更新する必要があります。

タイムシフト録画の現在の時点とは、エポックからの経過時間をミリ秒で表した現在の再生時点です。この時点は、再生中に刻々と変化します。通常は、再生エンジンを使用してこの値を判定することができます。次に例を示します。

Kotlin

    override fun onTimeShiftGetCurrentPosition(): Long =
            tvPlayer?.run {
                currentProgram?.let { program ->
                    currentPosition + program.startTimeUtcMillis
                }
            } ?: TvInputManager.TIME_SHIFT_INVALID_TIME
    

Java

    @Override
    public long onTimeShiftGetCurrentPosition() {
      if (getTvPlayer() != null && currentProgram != null) {
        return getTvPlayer().getCurrentPosition() +
          currentProgram.getStartTimeUtcMillis();
      }
      return TvInputManager.TIME_SHIFT_INVALID_TIME;
    }
    

システムによって onTimeShiftGetStartPosition() が呼び出されるときに指定する開始時刻は、onTimeShiftGetCurrentPosition() で指定する現在時点よりも大きくならないようにしてください。システムはこれらの呼び出しを使用して、再生コントロール UI に表示されるタイムシフトの時間枠を更新します。

再生パラメータをサポートする

タイムシフト中に再生速度を変更する際には再生パラメータが使用されます。たとえば、ユーザーが現在の再生を巻き戻すことにした場合、マイナスの再生速度が指定された新しい再生パラメータがアプリに渡されます。 タイムシフトでは、巻き戻しまたは早送りの再生速度を複数のレベル(2 倍、3 倍)から選択することもできます。

システムは、現在のセッションのパラメータを含む PlaybackParams オブジェクトを使用して onTimeShiftSetPlaybackParams(PlaybackParams) メソッドを呼び出します。この情報を使用して、メディア再生エンジンを適切に設定します。

再生エンジンがパラメータをサポートしていない場合は、予想される動作を可能な限りエミュレートします。たとえば、再生エンジンが 2 倍の速度をサポートしていない場合は、再生エンジンで移動を繰り返す操作を使用して、再生速度が約 2 倍になるようにします。

パラメータを設定したら、ユーザーが別のパラメータを必要とする再生コマンドを発行するか、新しいチャンネルに切り替えるまで、設定を変更しないでください。