Ihrer Android-App erweiterte Funktionen hinzufügen

Werbeunterbrechungen

Das Android Sender SDK unterstützt Werbeunterbrechungen und Companion-Anzeigen in einer einen bestimmten Mediastream zu erstellen.

Weitere Informationen zur Funktionsweise von Werbeunterbrechungen findest du unter Übersicht über Werbeunterbrechungen für Webreceiver.

Pausen können zwar sowohl beim Sender als auch beim Empfänger angegeben werden, es wird jedoch empfohlen, Web Receiver und Android TV-Receiver für einheitliches Design auf verschiedenen Plattformen.

Auf Android-Geräten kannst du in einem Ladebefehl AdBreakClipInfo und AdBreakInfo:

Kotlin
val breakClip1: AdBreakClipInfo =
    AdBreakClipInfo.Builder("bc0")
        .setTitle("Clip title")
        .setPosterUrl("https://www.some.url")
        .setDuration(60000)
        .setWhenSkippableInMs(5000)  // Set this field so that the ad is skippable
        .build()

val breakClip2: AdBreakClipInfo = 
val breakClip3: AdBreakClipInfo = 

val break1: AdBreakClipInfo =
    AdBreakInfo.Builder(/* playbackPositionInMs= */ 10000)
        .setId("b0")
        .setBreakClipIds({"bc0","bc1","bc2"})
        
        .build()

val mediaInfo: MediaInfo = MediaInfo.Builder()
    
    .setAdBreaks({break1})
    .setAdBreakClips({breakClip1, breakClip2, breakClip3})
    .build()

val mediaLoadRequestData: MediaLoadRequestData = MediaInfo.Builder()
    
    .setMediaInfo(mediaInfo)
    .build()

remoteMediaClient.load(mediaLoadRequestData)
Java
AdBreakClipInfo breakClip1 =
    new AdBreakClipInfo.Builder("bc0")
        .setTitle("Clip title")
        .setPosterUrl("https://www.some.url")
        .setDuration(60000)
        .setWhenSkippableInMs(5000)  // Set this field so that the ad is skippable
        .build();

AdBreakClipInfo breakClip2 = 
AdBreakClipInfo breakClip3 = 

AdBreakInfo break1 =
    new AdBreakInfo.Builder(/* playbackPositionInMs= */ 10000)
        .setId("b0")
        .setBreakClipIds({"bc0","bc1","bc2"})
        
        .build();

MediaInfo mediaInfo = new MediaInfo.Builder()
    
    .setAdBreaks({break1})
    .setAdBreakClips({breakClip1, breakClip2, breakClip3})
    .build();

MediaLoadRequestData mediaLoadRequestData = new MediaInfo.Builder()
    
    .setMediaInfo(mediaInfo)
    .build();

remoteMediaClient.load(mediaLoadRequestData);

Benutzerdefinierte Aktionen hinzufügen

Eine Absender-App kann MediaIntentReceiver benutzerdefinierte Aktionen verarbeiten oder ihr Verhalten überschreiben. Wenn Sie Ihre MediaIntentReceiver besitzt, musst du es dem Manifest hinzufügen und auch seine Namen in CastMediaOptions ein. Dieses Beispiel bietet benutzerdefinierte Aktionen, Remote-Medienwiedergabe überschreiben, Medientaste drücken und andere Arten von Handlungen.

// In AndroidManifest.xml
<receiver android:name="com.example.MyMediaIntentReceiver" />
Kotlin
// In your OptionsProvider
var mediaOptions = CastMediaOptions.Builder()
    .setMediaIntentReceiverClassName(MyMediaIntentReceiver::class.java.name)
    .build()

// Implementation of MyMediaIntentReceiver
internal class MyMediaIntentReceiver : MediaIntentReceiver() {
    override fun onReceiveActionTogglePlayback(currentSession: Session) {
    }

    override fun onReceiveActionMediaButton(currentSession: Session, intent: Intent) {
    }

    override fun onReceiveOtherAction(context: Context?, action: String, intent: Intent) {
    }
}
Java
// In your OptionsProvider
CastMediaOptions mediaOptions = new CastMediaOptions.Builder()
        .setMediaIntentReceiverClassName(MyMediaIntentReceiver.class.getName())
        .build();

// Implementation of MyMediaIntentReceiver
class MyMediaIntentReceiver extends MediaIntentReceiver {
    @Override
    protected void onReceiveActionTogglePlayback(Session currentSession) {
    }

    @Override
    protected void onReceiveActionMediaButton(Session currentSession, Intent intent) {
    }

    @Override
    protected void onReceiveOtherAction(Context context, String action, Intent intent) {
    }
}

Benutzerdefinierten Channel hinzufügen

Damit die Absender-App mit der Empfänger-App kommunizieren kann, muss die App einen benutzerdefinierten Channel erstellen. Der Absender kann über den benutzerdefinierten Channel Strings an den Empfänger senden. Jeder benutzerdefinierte Channel wird durch einen eindeutigen Namespace und muss mit dem Präfix urn:x-cast: beginnen. Beispiel: urn:x-cast:com.example.custom. Es ist möglich, mehrere benutzerdefinierte Channels mit einem eindeutigen Namespace. Die Empfänger-App kann auch Nachrichten senden und empfangen mit demselben Namespace.

Der benutzerdefinierte Channel wird mit dem Cast.MessageReceivedCallback Schnittstelle:

Kotlin
class HelloWorldChannel : MessageReceivedCallback {
    val namespace: String
        get() = "urn:x-cast:com.example.custom"

    override fun onMessageReceived(castDevice: CastDevice, namespace: String, message: String) {
        Log.d(TAG, "onMessageReceived: $message")
    }
}
Java
class HelloWorldChannel implements Cast.MessageReceivedCallback {
    public String getNamespace() {
        return "urn:x-cast:com.example.custom";
    }
    @Override
    public void onMessageReceived(CastDevice castDevice, String namespace, String message) {
        Log.d(TAG, "onMessageReceived: " + message);
    }
}

Sobald die Absender-App mit der Empfänger-App verbunden ist, kann der benutzerdefinierte Channel werden mithilfe der setMessageReceivedCallbacks :

Kotlin
try {
    mCastSession.setMessageReceivedCallbacks(
        mHelloWorldChannel.namespace,
        mHelloWorldChannel)
} catch (e: IOException) {
    Log.e(TAG, "Exception while creating channel", e)
}
Java
try {
    mCastSession.setMessageReceivedCallbacks(
            mHelloWorldChannel.getNamespace(),
            mHelloWorldChannel);
} catch (IOException e) {
    Log.e(TAG, "Exception while creating channel", e);
}

Sobald der benutzerdefinierte Channel erstellt wurde, kann der Absender die sendMessage , um Zeichenfolgennachrichten über diesen Kanal an den Empfänger zu senden:

Kotlin
private fun sendMessage(message: String) {
    if (mHelloWorldChannel != null) {
        try {
            mCastSession.sendMessage(mHelloWorldChannel.namespace, message)
                .setResultCallback { status ->
                    if (!status.isSuccess) {
                        Log.e(TAG, "Sending message failed")
                    }
                }
        } catch (e: Exception) {
            Log.e(TAG, "Exception while sending message", e)
        }
    }
}
Java
private void sendMessage(String message) {
    if (mHelloWorldChannel != null) {
        try {
            mCastSession.sendMessage(mHelloWorldChannel.getNamespace(), message)
                .setResultCallback( status -> {
                    if (!status.isSuccess()) {
                        Log.e(TAG, "Sending message failed");
                    }
                });
        } catch (Exception e) {
            Log.e(TAG, "Exception while sending message", e);
        }
    }
}

Unterstützung für Autoplay

Weitere Informationen finden Sie im Abschnitt Autoplay und Queueing APIs (Warteschlangen-APIs).

Bildauswahl für UX-Widgets überschreiben

In verschiedenen Komponenten des Frameworks (nämlich im Übertragungsdialogfeld, im Minicontroller und im UIMediaController, sofern konfiguriert) wird Artwork für die aktuell gestreamten Medien angezeigt. Die URLs zu den Bildern sind in der Regel im MediaMetadata für die Medien enthalten. Die Absender-App kann jedoch eine alternative Quelle für die URLs.

Die ImagePicker -Klasse definiert ein Mittel zur Auswahl eines geeigneten Bildes aus der Liste der Bilder in einem MediaMetadata, basierend auf der Verwendung des Bildes, z. B. Benachrichtigung Thumbnail oder Vollbildhintergrund anzuzeigen. Standardimplementierung von ImagePicker wählt immer das erste Bild aus oder gibt null zurück, wenn kein Bild in der MediaMetadata. Ihre Anwendung kann ImagePicker abgeleitet und die onPickImage(MediaMetadata, ImageHints) , um eine alternative Implementierung bereitzustellen, und wählen Sie dann diese abgeleitete Klasse aus. mit dem setImagePicker CastMediaOptions.Builder-Methode. ImageHints gibt ImagePicker Hinweise auf den Typ und die Größe eines Bilds an. die auf der Benutzeroberfläche ausgewählt sind.

Cast-Dialogfelder anpassen

Sitzungslebenszyklus verwalten

SessionManager ist die zentrale Stelle für die Verwaltung des Sitzungslebenszyklus. SessionManager überwacht die Änderungen des Status der Routenauswahl unter AndroidMediaRouter, um Sitzungen zu starten, fortzusetzen und zu beenden. Wenn eine Route ausgewählt, SessionManager erstellt ein Session und versucht, es zu starten oder fortzusetzen. Wenn eine Route nicht ausgewählt ist, SessionManager beendet die aktuelle Sitzung.

Um sicherzustellen, dass SessionManager Sitzungslebenszyklen richtig verwaltet, müssen Sie muss Folgendes gewährleistet sein:

Je nachdem, wie Sie die Dialogfelder für das Streamen erstellt haben, müssen möglicherweise weitere Aktionen Fertig:

Null-Gerätestatus

Wenn Sie benutzerdefinierte Streaming-Dialogfelder erstellen, MediaRouteChooserDialog sollte auch für den Fall geeignet sein, dass keine Geräte gefunden. Das Dialogfeld sollte Indikatoren enthalten, die für Ihre Nutzer klar erkennbar sind, Die App versucht immer noch, Geräte zu finden, aber der Erkennungsversuch ist nicht erfolgreich länger aktiv ist.

Wenn Sie die Standardeinstellung MediaRouteChooserDialog verwenden, wird der Status „Keine Geräte“ angezeigt. bereits bearbeitet wird.

Nächste Schritte

Damit sind die Funktionen beendet, die Sie Ihrer Android Sender App hinzufügen können. Du kannst jetzt eine Absender-App für eine andere Plattform erstellen (iOS oder Web) oder eine Web Receiver-App erstellen