Use Looper.getMainLooper() in Handler constructors in ExoPlayer when needed.

Looper.myLooper(), the default looper, may be null in background threads. This adds a fallback to use the main app looper.

This will allow ExoPlayer instances to be built in background threads in Photos.

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=154845446
This commit is contained in:
falhassen 2017-05-02 10:09:55 -07:00 committed by Oliver Woodman
parent e90e2caec4
commit 60bf31ff24
4 changed files with 23 additions and 24 deletions

View File

@ -15,6 +15,8 @@
*/
package com.google.android.exoplayer2;
import android.os.Looper;
import android.support.annotation.IntDef;
import android.support.annotation.Nullable;
import com.google.android.exoplayer2.audio.MediaCodecAudioRenderer;
import com.google.android.exoplayer2.metadata.MetadataRenderer;
@ -88,7 +90,9 @@ import com.google.android.exoplayer2.video.MediaCodecVideoRenderer;
* thread. The application's main thread is ideal. Accessing an instance from multiple threads is
* discouraged, however if an application does wish to do this then it may do so provided that it
* ensures accesses are synchronized.</li>
* <li>Registered listeners are called on the thread that created the ExoPlayer instance.</li>
* <li>Registered listeners are called on the thread that created the ExoPlayer instance, unless
* the thread that created the ExoPlayer instance does not have a {@link Looper}. In that case,
* registered listeners will be called on the application's main thread.</li>
* <li>An internal playback thread is responsible for playback. Injected player components such as
* Renderers, MediaSources, TrackSelectors and LoadControls are called by the player on this
* thread.</li>
@ -253,7 +257,8 @@ public interface ExoPlayer {
/**
* Register a listener to receive events from the player. The listener's methods will be called on
* the thread that was used to construct the player.
* the thread that was used to construct the player. However, if the thread used to construct the
* player does not have a {@link Looper}, then the listener will be called on the main thread.
*
* @param listener The listener to register.
*/

View File

@ -16,7 +16,6 @@
package com.google.android.exoplayer2;
import android.content.Context;
import android.os.Looper;
import com.google.android.exoplayer2.drm.DrmSessionManager;
import com.google.android.exoplayer2.drm.FrameworkMediaCrypto;
import com.google.android.exoplayer2.trackselection.TrackSelector;
@ -29,8 +28,7 @@ public final class ExoPlayerFactory {
private ExoPlayerFactory() {}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param context A {@link Context}.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -45,8 +43,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}. Available extension renderers are not used.
* Creates a {@link SimpleExoPlayer} instance. Available extension renderers are not used.
*
* @param context A {@link Context}.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -63,8 +60,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param context A {@link Context}.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -86,8 +82,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param context A {@link Context}.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -112,8 +107,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param context A {@link Context}.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -123,8 +117,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param renderersFactory A factory for creating {@link Renderer}s to be used by the instance.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -135,8 +128,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates a {@link SimpleExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates a {@link SimpleExoPlayer} instance.
*
* @param renderersFactory A factory for creating {@link Renderer}s to be used by the instance.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -148,8 +140,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates an {@link ExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates an {@link ExoPlayer} instance.
*
* @param renderers The {@link Renderer}s that will be used by the instance.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.
@ -159,8 +150,7 @@ public final class ExoPlayerFactory {
}
/**
* Creates an {@link ExoPlayer} instance. Must be called from a thread that has an associated
* {@link Looper}.
* Creates an {@link ExoPlayer} instance.
*
* @param renderers The {@link Renderer}s that will be used by the instance.
* @param trackSelector The {@link TrackSelector} that will be used by the instance.

View File

@ -92,7 +92,8 @@ import java.util.concurrent.CopyOnWriteArraySet;
trackGroups = TrackGroupArray.EMPTY;
trackSelections = emptyTrackSelections;
playbackParameters = PlaybackParameters.DEFAULT;
eventHandler = new Handler() {
Looper eventLooper = Looper.myLooper() != null ? Looper.myLooper() : Looper.getMainLooper();
eventHandler = new Handler(eventLooper) {
@Override
public void handleMessage(Message msg) {
ExoPlayerImpl.this.handleEvent(msg);

View File

@ -20,6 +20,7 @@ import android.graphics.SurfaceTexture;
import android.media.MediaCodec;
import android.media.PlaybackParams;
import android.os.Handler;
import android.os.Looper;
import android.support.annotation.Nullable;
import android.util.Log;
import android.view.Surface;
@ -111,8 +112,10 @@ public class SimpleExoPlayer implements ExoPlayer {
protected SimpleExoPlayer(RenderersFactory renderersFactory, TrackSelector trackSelector,
LoadControl loadControl) {
componentListener = new ComponentListener();
renderers = renderersFactory.createRenderers(new Handler(), componentListener,
componentListener, componentListener, componentListener);
Looper eventLooper = Looper.myLooper() != null ? Looper.myLooper() : Looper.getMainLooper();
Handler eventHandler = new Handler(eventLooper);
renderers = renderersFactory.createRenderers(eventHandler, componentListener, componentListener,
componentListener, componentListener);
// Obtain counts of video and audio renderers.
int videoRendererCount = 0;