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
:
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)
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" />
// 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) { } }
// 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:
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") } }
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
:
try { mCastSession.setMessageReceivedCallbacks( mHelloWorldChannel.namespace, mHelloWorldChannel) } catch (e: IOException) { Log.e(TAG, "Exception while creating channel", e) }
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:
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) } } }
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:
- Rufe im Dialogfeld für die Routenauswahl
MediaRouter.selectRoute(MediaRouter.RouteInfo)
auf, wenn ein Nutzer ein Gerät auswählt. - Rufe im Dialogfeld „Routencontroller“ (entweder im Verbunden-Status oder im Streaming-Status)
MediaRouter.unselect(int)
auf, wenn der Nutzer das Streaming beendet.
Je nachdem, wie Sie die Dialogfelder für das Streamen erstellt haben, müssen möglicherweise weitere Aktionen Fertig:
- Wenn Sie Streaming-Dialogfelder mit
MediaRouteChooserDialog
undMediaRouteControllerDialog
, wird die Routenauswahl inMediaRouter
in diesen Dialogfeldern automatisch aktualisiert. Es muss also nichts unternommen werden. - Wenn Sie das Cast-Symbol mit
CastButtonFactory.setUpMediaRouteButton(Context, Menu, int)
oderCastButtonFactory.setUpMediaRouteButton(Context, MediaRouteButton)
, werden die Dialogfelder erstellt mitMediaRouteChooserDialog
undMediaRouteControllerDialog
. muss auch nichts erledigt werden. - In anderen Fällen erstellen Sie benutzerdefinierte Streaming-Dialogfelder.
Folgen Sie der Anleitung oben, um den Status der Routenauswahl in
MediaRouter
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