Un'app web compatibile con Google Cast

1. Panoramica

Logo di Google Cast

Questo codelab ti spiegherà come modificare un'app web web esistente per trasmettere contenuti su un dispositivo compatibile con Google Cast.

Che cos'è Google Cast?

Google Cast consente agli utenti di trasmettere contenuti da un dispositivo mobile alla TV. Gli utenti possono quindi utilizzare il dispositivo mobile come telecomando per la riproduzione di contenuti multimediali sulla TV.

L'SDK Google Cast ti consente di estendere l'app per controllare una TV o un sistema audio. L'SDK Cast ti consente di aggiungere i componenti necessari all'interfaccia utente in base all'elenco di controllo per la progettazione di Google Cast.

L'elenco di controllo per la progettazione di Google Cast viene fornito per semplificare e prevedere l'esperienza utente con tutte le piattaforme supportate.

Cosa realizzeremo?

Dopo aver completato il codelab, avrai a disposizione un'app web Chrome per la trasmissione di video su un dispositivo Google Cast.

Obiettivi didattici

  • Come aggiungere l'SDK Google Cast a un'app video di esempio.
  • Come aggiungere il pulsante Trasmetti per selezionare un dispositivo Google Cast.
  • Come connettersi a un dispositivo di trasmissione e avviare un ricevitore multimediale.
  • Come trasmettere un video.
  • Come integrare Cast Connect

Che cosa ti serve

  • Il browser Google Chrome più recente.
  • Servizio di hosting HTTPS come Firebase Hosting o ngrok.
  • Un dispositivo Google Cast, ad esempio Chromecast o Android TV, configurato con accesso a Internet.
  • Una TV o un monitor con ingresso HDMI.
  • Per testare l'integrazione di Cast Connect è necessario Chromecast con Google TV, ma facoltativo per il resto del codelab. Se non ne hai uno, puoi saltare il passaggio Aggiungi assistenza per la trasmissione alla fine di questo tutorial.

Esperienza

  • Devi conoscere già le nozioni di sviluppo del Web.
  • Avrai anche bisogno di una conoscenza precedente della TV.

Come utilizzerai questo tutorial?

Leggilo solo per te Leggilo e completa gli esercizi

Come valuteresti la tua esperienza con la creazione di app web?

Principiante Intermedio Esperto

Come giudichi la tua esperienza con la visione della TV?

Principiante Intermedio Esperto

2. Recupera il codice campione

Puoi scaricare tutto il codice campione sul tuo computer...

e decomprimi il file ZIP scaricato.

3. Esegui l'app di esempio

Logo di Google Chrome

Innanzitutto, vediamo come si presenta l'app di esempio completata. L'app è un video player di base. L'utente può selezionare un video da un elenco, quindi riprodurlo localmente sul dispositivo o trasmetterlo a un dispositivo Google Cast.

Per utilizzare l'app completata, questa deve essere ospitata.

Se non hai un server disponibile, puoi utilizzare Firebase Hosting o ngrok.

Esegui il server.

Dopo aver configurato il servizio che preferisci, vai a app-done e avvia il server.

Nel browser, visita l'URL https dell'esempio ospitato.

  1. Dovresti vedere l'app video.
  2. Fai clic sul pulsante Trasmetti e seleziona il tuo dispositivo Google Cast.
  3. Seleziona un video, fai clic sul pulsante di riproduzione.
  4. La riproduzione del video inizierà sul tuo dispositivo Google Cast.

Immagine di un video in riproduzione su un dispositivo di trasmissione

Fai clic sul pulsante di pausa nell'elemento video per sospendere la riproduzione del video sul ricevitore. Fai clic sul pulsante di riproduzione nell'elemento video per continuare a riprodurre il video.

Fai clic sul pulsante Trasmetti per interrompere la trasmissione al dispositivo Google Cast.

Prima di andare avanti, arresta il server.

4. Prepara il progetto di avvio

Immagine di un video in riproduzione su un dispositivo di trasmissione

Dobbiamo aggiungere il supporto per Google Cast all'app iniziale che hai scaricato. Di seguito sono riportate alcune terminologia di Google Cast che utilizzeremo in questo codelab:

  • L'app mittente sia eseguita su un dispositivo mobile o laptop
  • L'app destinatario viene eseguita sul dispositivo Google Cast.

Ora puoi creare il progetto di base utilizzando il tuo editor di testo preferito:

  1. Seleziona la directory Icona di una cartellaapp-start dal download del codice campione.
  2. Esegui l'app utilizzando il tuo server ed esplora l'interfaccia utente.

Tieni presente che, mentre lavori con questo codelab, devi ospitare nuovamente l'esempio sul tuo server, a seconda del servizio.

Progettazione di app

L'app recupera un elenco di video da un server web remoto e fornisce un elenco all'utente. Gli utenti possono selezionare un video per visualizzarne i dettagli oppure riprodurlo localmente sul dispositivo mobile.

L'app è composta da una vista principale, definita in index.html, e nel controller principale, CastVideos.js.

index.html

Questo file HTML dichiara quasi tutta l'UI dell'app web.

Ci sono alcune sezioni di visualizzazioni, che hanno il nostro div#main_video, che contiene l'elemento video. Relativamente al nostro div video, abbiamo div#media_control, che definisce tutti i controlli per l'elemento video. Sotto si trova media_info, che mostra i dettagli del video visualizzato. Infine, il div carousel mostra un elenco di video in un div.

Il file index.html esegue il bootstrap dell'SDK Cast e indica alla funzione CastVideos di caricarsi.

La maggior parte dei contenuti che popoleranno questi elementi è definita, inserita e controllata in CastVideos.js. Vediamo come funziona.

CastVideo.js

Questo script gestisce tutta la logica per l'app web Cast Video. L'elenco dei video e i relativi metadati definiti in CastVideos.js sono contenuti in un oggetto denominato mediaJSON.

Ci sono alcune sezioni principali che insieme sono responsabili della gestione e della riproduzione del video, sia a livello locale che da remoto. Nel complesso, si tratta di un'applicazione web abbastanza semplice.

CastPlayer è la classe principale che gestisce l'intera app, configurando il player, selezionando i contenuti multimediali e associando gli eventi a PlayerHandler per la riproduzione di contenuti multimediali. CastPlayer.prototype.initializeCastPlayer è il metodo che configura tutte le funzionalità di trasmissione. CastPlayer.prototype.switchPlayer cambia lo stato tra player locali e remoti. CastPlayer.prototype.setupLocalPlayer e CastPlayer.prototype.setupRemotePlayer inizializzano i player locali e remoti.

PlayerHandler è la classe responsabile della gestione della riproduzione dei contenuti multimediali. Esistono diversi altri metodi responsabili dei dettagli relativi alla gestione dei contenuti multimediali e della riproduzione.

Domande frequenti

5. Aggiungere il pulsante Trasmetti

Immagine di un'app compatibile con Google Cast

In un'applicazione compatibile con Google Cast, nell'elemento video viene visualizzato il pulsante Trasmetti. Se fai clic sul pulsante Trasmetti, viene visualizzato un elenco di dispositivi di trasmissione che possono essere selezionati da un utente. Se l'utente stava riproducendo i contenuti localmente sul dispositivo di trasmissione, selezionando o avviando la riproduzione di un dispositivo di trasmissione verrà avviata la riproduzione sul dispositivo in questione. Durante una sessione di trasmissione, l'utente può fare clic sul pulsante Trasmetti in qualsiasi momento e interrompere la trasmissione dell'applicazione al dispositivo di trasmissione. L'utente deve essere in grado di connettersi o disconnettersi dal dispositivo di trasmissione in qualsiasi schermata dell'applicazione, come descritto nell'Elenco di controllo per la progettazione di Google Cast.

Configurazione

Il progetto iniziale richiede le stesse dipendenze e configurazione di quelle usate per l'app di esempio completata, ma questa volta ospita i contenuti di app-start.

Nel browser, visita l'URL https per l'esempio ospitato.

Ricorda che, man mano che apporti le modifiche, dovrai ospitare nuovamente l'esempio sul server, a seconda del servizio.

Inizializzazione

Il framework Cast ha un oggetto singleton globale, CastContext, che coordina tutte le attività del framework. Questo oggetto deve essere inizializzato nelle prime fasi del ciclo di vita dell'applicazione, generalmente chiamato da un callback assegnato a window['__onGCastApiAvailable'], che viene richiamato dopo il caricamento dell'SDK Cast ed è disponibile per l'uso. In questo caso, CastContext viene richiamato in CastPlayer.prototype.initializeCastPlayer, richiamato dal callback indicato.

Quando si inizializza CastContext, è necessario specificare un oggetto JSON options. Questa classe contiene opzioni che influiscono sul comportamento del framework. Il più importante è l'ID applicazione del ricevitore, che viene utilizzato per filtrare l'elenco dei dispositivi di trasmissione disponibili e mostrare solo quelli in grado di eseguire l'app specificata e per avviare l'applicazione di ricezione all'avvio di una sessione di trasmissione.

Se sviluppi la tua app compatibile con Google Cast, devi registrarti come sviluppatore e poi ottenere un ID applicazione per l'app. Per questo codelab, utilizzeremo un ID app di esempio.

Aggiungi il codice seguente a index.html alla fine della sezione body:

<script type="text/javascript" src="https://www.gstatic.com/cv/js/sender/v1/cast_sender.js?loadCastFramework=1"></script>

Aggiungi il seguente codice a index.html per inizializzare l'app CastVideos e per CastContext:

<script src="CastVideos.js"></script>
<script type="text/javascript">
var castPlayer = new CastPlayer();
window['__onGCastApiAvailable'] = function(isAvailable) {
  if (isAvailable) {
    castPlayer.initializeCastPlayer();
  }
};
</script>

Ora dobbiamo aggiungere un nuovo metodo in CastVideos.js, che corrisponda al metodo appena chiamato in index.html. Aggiungiamo un nuovo metodo, initializeCastPlayer, che imposta le opzioni su CastContext e inizializza le nuove RemotePlayer e RemotePlayerControllers:

/**
 * This method sets up the CastContext, and a few other members
 * that are necessary to play and control videos on a Cast
 * device.
 */
CastPlayer.prototype.initializeCastPlayer = function() {

    var options = {};

    // Set the receiver application ID to your own (created in
    // the Google Cast Developer Console), or optionally
    // use the chrome.cast.media.DEFAULT_MEDIA_RECEIVER_APP_ID
    options.receiverApplicationId = 'C0868879';

    // Auto join policy can be one of the following three:
    // ORIGIN_SCOPED - Auto connect from same appId and page origin
    // TAB_AND_ORIGIN_SCOPED - Auto connect from same appId, page origin, and tab
    // PAGE_SCOPED - No auto connect
    options.autoJoinPolicy = chrome.cast.AutoJoinPolicy.ORIGIN_SCOPED;

    cast.framework.CastContext.getInstance().setOptions(options);

    this.remotePlayer = new cast.framework.RemotePlayer();
    this.remotePlayerController = new cast.framework.RemotePlayerController(this.remotePlayer);
    this.remotePlayerController.addEventListener(
        cast.framework.RemotePlayerEventType.IS_CONNECTED_CHANGED,
        this.switchPlayer.bind(this)
    );
};

Infine, dobbiamo creare le variabili per RemotePlayer e RemotePlayerController:

var CastPlayer = function() {
  //...
  /* Cast player variables */
  /** @type {cast.framework.RemotePlayer} */
  this.remotePlayer = null;
  /** @type {cast.framework.RemotePlayerController} */
  this.remotePlayerController = null;
  //...
};

Pulsante Trasmetti

Ora che CastContext è inizializzato, dobbiamo aggiungere il pulsante Trasmetti per consentire all'utente di selezionare un dispositivo di trasmissione. L'SDK Cast fornisce un componente del pulsante Trasmetti denominato google-cast-launcher con ID "castbutton"". Può essere aggiunto all'elemento video dell'applicazione semplicemente aggiungendo un elemento button nella sezione media_control.

L'elemento pulsante avrà il seguente aspetto:

<google-cast-launcher id="castbutton"></google-cast-launcher>

Aggiungi il codice seguente a index.html nella sezione media_control:

<div id="media_control">
  <div id="play"></div>
  <div id="pause"></div>
  <div id="progress_bg"></div>
  <div id="progress"></div>
  <div id="progress_indicator"></div>
  <div id="fullscreen_expand"></div>
  <div id="fullscreen_collapse"></div>
  <google-cast-launcher id="castbutton"></google-cast-launcher>
  <div id="audio_bg"></div>
  <div id="audio_bg_track"></div>
  <div id="audio_indicator"></div>
  <div id="audio_bg_level"></div>
  <div id="audio_on"></div>
  <div id="audio_off"></div>
  <div id="duration">00:00:00</div>
</div>

Ora aggiorna la pagina nel browser Chrome. Dovresti vedere un pulsante Trasmetti nell'elemento video e, quando ci fai clic, vengono elencati i dispositivi di trasmissione sulla tua rete locale. La funzionalità di rilevamento dei dispositivi viene gestita automaticamente dal browser Chrome. Seleziona il tuo dispositivo di trasmissione per caricare l'app del ricevitore di esempio.

Non abbiamo ancora collegato alcun supporto per la riproduzione di contenuti multimediali, quindi non puoi ancora riprodurre video sul dispositivo di trasmissione. Fai clic sul pulsante Trasmetti per interrompere la trasmissione.

6. Trasmissione di contenuti video

Immagine dell&#39;app compatibile con Google Cast con menu di selezione del dispositivo di trasmissione

Estenderemo l'app di esempio anche per riprodurre video da remoto su un dispositivo di trasmissione. Per farlo, dobbiamo ascoltare i vari eventi generati dal framework Cast.

Trasmissione di contenuti multimediali

Se vuoi riprodurre contenuti multimediali su un dispositivo di trasmissione a livello generale, devi procedere come segue:

  1. Crea un oggetto MediaInfo JSON dall'SDK Cast che modella un elemento multimediale.
  2. L'utente si connette al dispositivo di trasmissione per avviare l'applicazione del ricevitore.
  3. Carica l'oggetto MediaInfo nel ricevitore e riproduci i contenuti.
  4. Monitora lo stato dei contenuti multimediali.
  5. Invia comandi di riproduzione al ricevitore in base alle interazioni degli utenti.

Il passaggio 1 corrisponde alla mappatura di un oggetto a un altro; MediaInfo è riconosciuto dall'SDK di Cast, mentre mediaJSON è l'incapsulamento della nostra app per un elemento multimediale; possiamo mappare facilmente un mediaJSON a un MediaInfo. Abbiamo già eseguito il passaggio 2 nella sezione precedente. Il passaggio 3 è semplice con l'SDK Cast.

L'app di esempio CastPlayer già distingue tra riproduzione locale e remota nel metodo switchPlayer:

if (cast && cast.framework) {
  if (this.remotePlayer.isConnected) {
    //...

Non è importante in questo codelab capire esattamente come funziona tutta la logica del player di esempio. È però importante capire che il media player della tua app dovrà essere modificato per essere consapevole sia della riproduzione locale che di quella remota.

Al momento il player locale è sempre in stato di riproduzione locale perché non sa ancora nulla sugli stati di trasmissione. Dobbiamo aggiornare l'UI in base alle transizioni di stato che si verificano nel framework di trasmissione. Ad esempio, se iniziamo a trasmettere, dobbiamo interrompere la riproduzione locale e disattivare alcuni controlli. Analogamente, se interrompiamo la trasmissione quando siamo in questo controller, dobbiamo passare alla riproduzione locale. Per gestirla dobbiamo ascoltare i vari eventi generati dal framework Cast.

Gestione della sessione di trasmissione

Per la struttura di trasmissione, una sessione di trasmissione combina i passaggi per connettersi a un dispositivo, avviarsi (o partecipare a una sessione esistente), collegarsi a un'applicazione di ricezione e inizializzare un canale di controllo dei contenuti multimediali, se opportuno. Il canale di controllo dei contenuti multimediali è il modo in cui il framework di trasmissione invia e riceve i messaggi relativi alla riproduzione di contenuti multimediali dal ricevitore.

La sessione di trasmissione viene avviata automaticamente quando l'utente seleziona un dispositivo dal pulsante Trasmetti e si interrompe automaticamente quando l'utente si disconnette. Anche la riconnessione a una sessione del destinatario a causa di problemi di rete viene gestita automaticamente dal framework di trasmissione.

Le sessioni di trasmissione sono gestite da CastSession, a cui è possibile accedere tramite cast.framework.CastContext.getInstance().getCurrentSession(). I callback EventListener possono essere utilizzati per monitorare gli eventi di sessione, come creazione, sospensione, ripresa e terminazione.

Nella nostra attuale applicazione, tutta la gestione di sessioni e stati viene gestita per noi nel metodo setupRemotePlayer. Iniziamo a configurarlo nella tua app aggiungendo il seguente codice al tuo CastVideos.js:

/**
 * Set the PlayerHandler target to use the remote player
 */
CastPlayer.prototype.setupRemotePlayer = function () {
    var castSession = cast.framework.CastContext.getInstance().getCurrentSession();

    this.playerHandler.setTarget(playerTarget);

    // Setup remote player volume right on setup
    // The remote player may have had a volume set from previous playback
    if (this.remotePlayer.isMuted) {
        this.playerHandler.mute();
    }
    var currentVolume = this.remotePlayer.volumeLevel * FULL_VOLUME_HEIGHT;
    var p = document.getElementById('audio_bg_level');
    p.style.height = currentVolume + 'px';
    p.style.marginTop = -currentVolume + 'px';

    this.hideFullscreenButton();

    this.playerHandler.play();
};

Dobbiamo comunque associare tutti gli eventi dai callback e gestire tutti gli eventi in arrivo. Si tratta di una procedura abbastanza semplice, quindi ci occupiamo subito del problema:

/**
 * Set the PlayerHandler target to use the remote player
 */
CastPlayer.prototype.setupRemotePlayer = function () {
    var castSession = cast.framework.CastContext.getInstance().getCurrentSession();

    // Add event listeners for player changes which may occur outside sender app
    this.remotePlayerController.addEventListener(
        cast.framework.RemotePlayerEventType.IS_PAUSED_CHANGED,
        function() {
            if (this.remotePlayer.isPaused) {
                this.playerHandler.pause();
            } else {
                this.playerHandler.play();
            }
        }.bind(this)
    );

    this.remotePlayerController.addEventListener(
        cast.framework.RemotePlayerEventType.IS_MUTED_CHANGED,
        function() {
            if (this.remotePlayer.isMuted) {
                this.playerHandler.mute();
            } else {
                this.playerHandler.unMute();
            }
        }.bind(this)
    );

    this.remotePlayerController.addEventListener(
        cast.framework.RemotePlayerEventType.VOLUME_LEVEL_CHANGED,
        function() {
            var newVolume = this.remotePlayer.volumeLevel * FULL_VOLUME_HEIGHT;
            var p = document.getElementById('audio_bg_level');
            p.style.height = newVolume + 'px';
            p.style.marginTop = -newVolume + 'px';
        }.bind(this)
    );

    // This object will implement PlayerHandler callbacks with
    // remotePlayerController, and makes necessary UI updates specific
    // to remote playback
    var playerTarget = {};

    playerTarget.play = function () {
        if (this.remotePlayer.isPaused) {
            this.remotePlayerController.playOrPause();
        }

        var vi = document.getElementById('video_image');
        vi.style.display = 'block';
        var localPlayer = document.getElementById('video_element');
        localPlayer.style.display = 'none';
    }.bind(this);

    playerTarget.pause = function () {
        if (!this.remotePlayer.isPaused) {
            this.remotePlayerController.playOrPause();
        }
    }.bind(this);

    playerTarget.stop = function () {
         this.remotePlayerController.stop();
    }.bind(this);

    playerTarget.getCurrentMediaTime = function() {
        return this.remotePlayer.currentTime;
    }.bind(this);

    playerTarget.getMediaDuration = function() {
        return this.remotePlayer.duration;
    }.bind(this);

    playerTarget.updateDisplayMessage = function () {
        document.getElementById('playerstate').style.display = 'block';
        document.getElementById('playerstatebg').style.display = 'block';
        document.getElementById('video_image_overlay').style.display = 'block';
        document.getElementById('playerstate').innerHTML =
            this.mediaContents[ this.currentMediaIndex]['title'] + ' ' +
            this.playerState + ' on ' + castSession.getCastDevice().friendlyName;
    }.bind(this);

    playerTarget.setVolume = function (volumeSliderPosition) {
        // Add resistance to avoid loud volume
        var currentVolume = this.remotePlayer.volumeLevel;
        var p = document.getElementById('audio_bg_level');
        if (volumeSliderPosition < FULL_VOLUME_HEIGHT) {
            var vScale =  this.currentVolume * FULL_VOLUME_HEIGHT;
            if (volumeSliderPosition > vScale) {
                volumeSliderPosition = vScale + (pos - vScale) / 2;
            }
            p.style.height = volumeSliderPosition + 'px';
            p.style.marginTop = -volumeSliderPosition + 'px';
            currentVolume = volumeSliderPosition / FULL_VOLUME_HEIGHT;
        } else {
            currentVolume = 1;
        }
        this.remotePlayer.volumeLevel = currentVolume;
        this.remotePlayerController.setVolumeLevel();
    }.bind(this);

    playerTarget.mute = function () {
        if (!this.remotePlayer.isMuted) {
            this.remotePlayerController.muteOrUnmute();
        }
    }.bind(this);

    playerTarget.unMute = function () {
        if (this.remotePlayer.isMuted) {
            this.remotePlayerController.muteOrUnmute();
        }
    }.bind(this);

    playerTarget.isMuted = function() {
        return this.remotePlayer.isMuted;
    }.bind(this);

    playerTarget.seekTo = function (time) {
        this.remotePlayer.currentTime = time;
        this.remotePlayerController.seek();
    }.bind(this);

    this.playerHandler.setTarget(playerTarget);

    // Setup remote player volume right on setup
    // The remote player may have had a volume set from previous playback
    if (this.remotePlayer.isMuted) {
        this.playerHandler.mute();
    }
    var currentVolume = this.remotePlayer.volumeLevel * FULL_VOLUME_HEIGHT;
    var p = document.getElementById('audio_bg_level');
    p.style.height = currentVolume + 'px';
    p.style.marginTop = -currentVolume + 'px';

    this.hideFullscreenButton();

    this.playerHandler.play();
};

Caricamento dell'elemento multimediale in corso...

In Cast SDK, RemotePlayer e RemotePlayerController forniscono una serie di pratiche API per gestire la riproduzione dei contenuti multimediali remoti sul ricevitore. Per un CastSession che supporta la riproduzione di contenuti multimediali, le istanze di RemotePlayer e RemotePlayerController verranno create automaticamente dall'SDK. Per accedere a queste istanze, crea istanze rispettivamente di cast.framework.RemotePlayer e cast.framework.RemotePlayerController, come mostrato in precedenza nel codelab.

Successivamente, dobbiamo caricare il video attualmente selezionato sul ricevitore creando un oggetto MediaInfo che l'SDK possa elaborare e trasferire la richiesta. Aggiungi il seguente codice a setupRemotePlayer per farlo:

/**
 * Set the PlayerHandler target to use the remote player
 */
CastPlayer.prototype.setupRemotePlayer = function () {
    //...

    playerTarget.load = function (mediaIndex) {
        console.log('Loading...' + this.mediaContents[mediaIndex]['title']);
        var mediaInfo = new chrome.cast.media.MediaInfo(
            this.mediaContents[mediaIndex]['sources'][0], 'video/mp4');

        mediaInfo.metadata = new chrome.cast.media.GenericMediaMetadata();
        mediaInfo.metadata.metadataType = chrome.cast.media.MetadataType.GENERIC;
        mediaInfo.metadata.title = this.mediaContents[mediaIndex]['title'];
        mediaInfo.metadata.images = [
            {'url': MEDIA_SOURCE_ROOT + this.mediaContents[mediaIndex]['thumb']}];

        var request = new chrome.cast.media.LoadRequest(mediaInfo);
        castSession.loadMedia(request).then(
            this.playerHandler.loaded.bind(this.playerHandler),
            function (errorCode) {
                this.playerState = PLAYER_STATE.ERROR;
                console.log('Remote media load error: ' +
                    CastPlayer.getErrorMessage(errorCode));
            }.bind(this));
    }.bind(this);

    //...
};

Ora aggiungi un metodo per passare dalla riproduzione locale a quella remota e viceversa:

/**
 * This is a method for switching between the local and remote
 * players. If the local player is selected, setupLocalPlayer()
 * is run. If there is a cast device connected we run
 * setupRemotePlayer().
 */
CastPlayer.prototype.switchPlayer = function() {
    this.stopProgressTimer();
    this.resetVolumeSlider();
    this.playerHandler.stop();
    this.playerState = PLAYER_STATE.IDLE;
    if (cast && cast.framework) {
        if (this.remotePlayer.isConnected) {
            this.setupRemotePlayer();
            return;
        }
    }
    this.setupLocalPlayer();
};

Infine, aggiungi un metodo per gestire gli eventuali messaggi di errore di trasmissione:

/**
 * Makes human-readable message from chrome.cast.Error
 * @param {chrome.cast.Error} error
 * @return {string} error message
 */
CastPlayer.getErrorMessage = function(error) {
  switch (error.code) {
    case chrome.cast.ErrorCode.API_NOT_INITIALIZED:
      return 'The API is not initialized.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.CANCEL:
      return 'The operation was canceled by the user' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.CHANNEL_ERROR:
      return 'A channel to the receiver is not available.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.EXTENSION_MISSING:
      return 'The Cast extension is not available.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.INVALID_PARAMETER:
      return 'The parameters to the operation were not valid.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.RECEIVER_UNAVAILABLE:
      return 'No receiver was compatible with the session request.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.SESSION_ERROR:
      return 'A session could not be created, or a session was invalid.' +
        (error.description ? ' :' + error.description : '');
    case chrome.cast.ErrorCode.TIMEOUT:
      return 'The operation timed out.' +
        (error.description ? ' :' + error.description : '');
  }
};

Ora esegui l'app. Collegati al tuo dispositivo di trasmissione e inizia a riprodurre un video. Dovresti vedere il video in riproduzione sul ricevitore.

7. Aggiungi il supporto per Cast Connect

La raccolta di Cast Connect consente alle applicazioni esistenti dei mittenti di comunicare con le applicazioni Android TV tramite il protocollo Cast. Cast Connect si basa sull'infrastruttura di trasmissione e la tua app per Android TV funge da ricevitore.

Dipendenze

  • Browser Chrome versione M87 o successive

Imposta il ricevitore Android compatibile

Per poter lanciare l'applicazione Android TV, chiamata anche Ricevitore Android, dobbiamo impostare il flag androidReceiverCompatible su true nell'oggetto CastOptions.

Aggiungi il seguente codice al tuo CastVideos.js nella funzione initializeCastPlayer:

var options = {};
...
options.androidReceiverCompatible = true;

cast.framework.CastContext.getInstance().setOptions(options);

Imposta credenziali di lancio

Per il mittente, puoi specificare CredentialsData per indicare chi partecipa alla sessione. credentials è una stringa che può essere definita dall'utente, purché l'app ATV possa riconoscerla. Il CredentialsData viene trasmesso alla tua app Android TV soltanto al momento del lancio o durante la registrazione. Se lo imposti di nuovo mentre sei connesso, non verrà trasmesso all'app Android TV.

Per impostare le credenziali di lancio, CredentialsData deve essere definito in qualsiasi momento dopo l'impostazione delle opzioni di lancio.

Aggiungi il seguente codice alla tua classe CastVideos.js sotto la funzione initializeCastPlayer:

cast.framework.CastContext.getInstance().setOptions(options);
...
let credentialsData = new chrome.cast.CredentialsData("{\"userId\": \"abc\"}");
cast.framework.CastContext.getInstance().setLaunchCredentialsData(credentialsData);
...

Imposta credenziali su richiesta di caricamento

Se l'app ricevitore web e l'app Android TV gestiscono credentials in modo diverso, potrebbe essere necessario definire credenziali separate per ciascuna. Per risolvere questo problema, aggiungi il seguente codice in CastVideos.js sotto playerTarget.load nella funzione setupRemotePlayer:

...
var request = new chrome.cast.media.LoadRequest(mediaInfo);
request.credentials = 'user-credentials';
request.atvCredentials = 'atv-user-credentials';
...

A seconda dell'app del destinatario a cui viene trasmesso il mittente, l'SDK gestisce automaticamente le credenziali da utilizzare per la sessione corrente.

Test di Cast Connect

Procedura per installare l'APK Android TV su Chromecast con Google TV:

  1. Trova l'indirizzo IP del tuo dispositivo Android TV. Di solito è disponibile in Impostazioni > Rete e Internet > (Nome della rete a cui è connesso il dispositivo). A destra vengono visualizzati i dettagli e l'IP del dispositivo sulla rete.
  2. Utilizza l'indirizzo IP del dispositivo per stabilire la connessione tramite ADB utilizzando il terminale:
$ adb connect <device_ip_address>:5555
  1. Dalla finestra del terminale, vai alla cartella di primo livello per gli esempi di codelab che hai scaricato all'inizio. Ad esempio:
$ cd Desktop/chrome_codelab_src
  1. Installa il file .apk in questa cartella su Android TV eseguendo questo comando:
$ adb -s <device_ip_address>:5555 install android-tv-app.apk
  1. Ora dovresti riuscire a vedere un'app chiamata Trasmetti video nel menu Le tue app del tuo dispositivo Android TV.
  2. Esegui il codice del mittente web aggiornato e stabilisci una sessione di trasmissione con il tuo dispositivo Android TV utilizzando l'icona Trasmetti o selezionando Cast.. dal menu a discesa del browser Chrome. A questo punto dovrebbe essere avviata l'app Android TV sul tuo ricevitore Android e potrai controllare la riproduzione usando il telecomando di Android TV.

8. Congratulazioni

Ora sai come attivare un'app video con Cast utilizzando i widget SDK di trasmissione su un'app web di Chrome.

Per ulteriori dettagli, consulta la guida per gli sviluppatori di Web Sender.