diff --git a/extensions/cast/src/main/java/com/google/android/exoplayer2/ext/cast/CastPlayer.java b/extensions/cast/src/main/java/com/google/android/exoplayer2/ext/cast/CastPlayer.java index 3c91b7ad4d..29108ba04b 100644 --- a/extensions/cast/src/main/java/com/google/android/exoplayer2/ext/cast/CastPlayer.java +++ b/extensions/cast/src/main/java/com/google/android/exoplayer2/ext/cast/CastPlayer.java @@ -15,6 +15,7 @@ */ package com.google.android.exoplayer2.ext.cast; +import android.os.Looper; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.util.Log; @@ -298,6 +299,11 @@ public final class CastPlayer implements Player { return null; } + @Override + public Looper getApplicationLooper() { + return Looper.getMainLooper(); + } + @Override public void addListener(EventListener listener) { listeners.add(listener); diff --git a/extensions/ima/README.md b/extensions/ima/README.md index c5ef1af35f..e13cd85590 100644 --- a/extensions/ima/README.md +++ b/extensions/ima/README.md @@ -30,7 +30,9 @@ To play ads alongside a single-window content `MediaSource`, prepare the player with an `AdsMediaSource` constructed using an `ImaAdsLoader`, the content `MediaSource` and an overlay `ViewGroup` on top of the player. Pass an ad tag URI from your ad campaign when creating the `ImaAdsLoader`. The IMA -documentation includes some [sample ad tags][] for testing. +documentation includes some [sample ad tags][] for testing. Note that the IMA +extension only supports players which are accessed on the application's main +thread. Resuming the player after entering the background requires some special handling when playing ads. The player and its media source are released on entering the diff --git a/extensions/ima/src/main/java/com/google/android/exoplayer2/ext/ima/ImaAdsLoader.java b/extensions/ima/src/main/java/com/google/android/exoplayer2/ext/ima/ImaAdsLoader.java index 56d62f26a9..8af15a0cfa 100644 --- a/extensions/ima/src/main/java/com/google/android/exoplayer2/ext/ima/ImaAdsLoader.java +++ b/extensions/ima/src/main/java/com/google/android/exoplayer2/ext/ima/ImaAdsLoader.java @@ -17,6 +17,7 @@ package com.google.android.exoplayer2.ext.ima; import android.content.Context; import android.net.Uri; +import android.os.Looper; import android.os.SystemClock; import android.support.annotation.IntDef; import android.support.annotation.Nullable; @@ -478,6 +479,7 @@ public final class ImaAdsLoader @Override public void attachPlayer(ExoPlayer player, EventListener eventListener, ViewGroup adUiViewGroup) { + Assertions.checkArgument(player.getApplicationLooper() == Looper.getMainLooper()); this.player = player; this.eventListener = eventListener; lastVolumePercentage = 0; diff --git a/extensions/mediasession/src/main/java/com/google/android/exoplayer2/ext/mediasession/MediaSessionConnector.java b/extensions/mediasession/src/main/java/com/google/android/exoplayer2/ext/mediasession/MediaSessionConnector.java index f1d3e8fbd0..4a2464fdaa 100644 --- a/extensions/mediasession/src/main/java/com/google/android/exoplayer2/ext/mediasession/MediaSessionConnector.java +++ b/extensions/mediasession/src/main/java/com/google/android/exoplayer2/ext/mediasession/MediaSessionConnector.java @@ -19,6 +19,7 @@ import android.graphics.Bitmap; import android.net.Uri; import android.os.Bundle; import android.os.Handler; +import android.os.Looper; import android.os.ResultReceiver; import android.os.SystemClock; import android.support.annotation.NonNull; @@ -36,6 +37,7 @@ import com.google.android.exoplayer2.ExoPlayerLibraryInfo; import com.google.android.exoplayer2.PlaybackParameters; import com.google.android.exoplayer2.Player; import com.google.android.exoplayer2.Timeline; +import com.google.android.exoplayer2.util.Assertions; import com.google.android.exoplayer2.util.ErrorMessageProvider; import com.google.android.exoplayer2.util.RepeatModeUtil; import com.google.android.exoplayer2.util.Util; @@ -367,8 +369,7 @@ public final class MediaSessionConnector { } /** - * Creates an instance. Must be called on the same thread that is used to construct the player - * instances passed to {@link #setPlayer(Player, PlaybackPreparer, CustomActionProvider...)}. + * Creates an instance. * * @param mediaSession The {@link MediaSessionCompat} to connect to. * @param playbackController A {@link PlaybackController} for handling playback actions, or {@code @@ -400,15 +401,17 @@ public final class MediaSessionConnector { *

The order in which any {@link CustomActionProvider}s are passed determines the order of the * actions published with the playback state of the session. * - * @param player The player to be connected to the {@code MediaSession}. + * @param player The player to be connected to the {@code MediaSession}, or {@link null} to + * disconnect the current player. * @param playbackPreparer An optional {@link PlaybackPreparer} for preparing the player. * @param customActionProviders Optional {@link CustomActionProvider}s to publish and handle * custom actions. */ public void setPlayer( - Player player, + @Nullable Player player, @Nullable PlaybackPreparer playbackPreparer, CustomActionProvider... customActionProviders) { + Assertions.checkArgument(player == null || player.getApplicationLooper() == Looper.myLooper()); if (this.player != null) { this.player.removeListener(exoPlayerEventListener); mediaSession.setCallback(null); diff --git a/library/core/src/main/java/com/google/android/exoplayer2/ExoPlayer.java b/library/core/src/main/java/com/google/android/exoplayer2/ExoPlayer.java index d1f6977eac..0e8c176486 100644 --- a/library/core/src/main/java/com/google/android/exoplayer2/ExoPlayer.java +++ b/library/core/src/main/java/com/google/android/exoplayer2/ExoPlayer.java @@ -89,10 +89,15 @@ import com.google.android.exoplayer2.video.MediaCodecVideoRenderer; * model"> * *