mirror of
https://github.com/samsonjs/media.git
synced 2026-04-27 15:07:40 +00:00
add DefaultMediaSourceFactory and use it in PlayerActivity
PiperOrigin-RevId: 298879027
This commit is contained in:
parent
b5976a55ff
commit
4517829610
11 changed files with 772 additions and 118 deletions
|
|
@ -32,7 +32,6 @@ import androidx.annotation.NonNull;
|
||||||
import androidx.annotation.Nullable;
|
import androidx.annotation.Nullable;
|
||||||
import androidx.appcompat.app.AppCompatActivity;
|
import androidx.appcompat.app.AppCompatActivity;
|
||||||
import com.google.android.exoplayer2.C;
|
import com.google.android.exoplayer2.C;
|
||||||
import com.google.android.exoplayer2.C.ContentType;
|
|
||||||
import com.google.android.exoplayer2.ExoPlaybackException;
|
import com.google.android.exoplayer2.ExoPlaybackException;
|
||||||
import com.google.android.exoplayer2.Format;
|
import com.google.android.exoplayer2.Format;
|
||||||
import com.google.android.exoplayer2.MediaItem;
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
|
@ -41,28 +40,18 @@ import com.google.android.exoplayer2.Player;
|
||||||
import com.google.android.exoplayer2.RenderersFactory;
|
import com.google.android.exoplayer2.RenderersFactory;
|
||||||
import com.google.android.exoplayer2.SimpleExoPlayer;
|
import com.google.android.exoplayer2.SimpleExoPlayer;
|
||||||
import com.google.android.exoplayer2.demo.Sample.UriSample;
|
import com.google.android.exoplayer2.demo.Sample.UriSample;
|
||||||
import com.google.android.exoplayer2.drm.DefaultDrmSessionManager;
|
|
||||||
import com.google.android.exoplayer2.drm.DrmSessionManager;
|
|
||||||
import com.google.android.exoplayer2.drm.ExoMediaCrypto;
|
|
||||||
import com.google.android.exoplayer2.drm.FrameworkMediaDrm;
|
|
||||||
import com.google.android.exoplayer2.drm.HttpMediaDrmCallback;
|
|
||||||
import com.google.android.exoplayer2.drm.MediaDrmCallback;
|
|
||||||
import com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.DecoderInitializationException;
|
import com.google.android.exoplayer2.mediacodec.MediaCodecRenderer.DecoderInitializationException;
|
||||||
import com.google.android.exoplayer2.mediacodec.MediaCodecUtil.DecoderQueryException;
|
import com.google.android.exoplayer2.mediacodec.MediaCodecUtil.DecoderQueryException;
|
||||||
import com.google.android.exoplayer2.offline.DownloadHelper;
|
import com.google.android.exoplayer2.offline.DownloadHelper;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.source.BehindLiveWindowException;
|
import com.google.android.exoplayer2.source.BehindLiveWindowException;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
import com.google.android.exoplayer2.source.MediaSource;
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceFactory;
|
|
||||||
import com.google.android.exoplayer2.source.MergingMediaSource;
|
import com.google.android.exoplayer2.source.MergingMediaSource;
|
||||||
import com.google.android.exoplayer2.source.ProgressiveMediaSource;
|
|
||||||
import com.google.android.exoplayer2.source.SingleSampleMediaSource;
|
import com.google.android.exoplayer2.source.SingleSampleMediaSource;
|
||||||
import com.google.android.exoplayer2.source.TrackGroupArray;
|
import com.google.android.exoplayer2.source.TrackGroupArray;
|
||||||
import com.google.android.exoplayer2.source.ads.AdsLoader;
|
import com.google.android.exoplayer2.source.ads.AdsLoader;
|
||||||
import com.google.android.exoplayer2.source.ads.AdsMediaSource;
|
import com.google.android.exoplayer2.source.ads.AdsMediaSource;
|
||||||
import com.google.android.exoplayer2.source.dash.DashMediaSource;
|
|
||||||
import com.google.android.exoplayer2.source.hls.HlsMediaSource;
|
|
||||||
import com.google.android.exoplayer2.source.smoothstreaming.SsMediaSource;
|
|
||||||
import com.google.android.exoplayer2.trackselection.AdaptiveTrackSelection;
|
import com.google.android.exoplayer2.trackselection.AdaptiveTrackSelection;
|
||||||
import com.google.android.exoplayer2.trackselection.DefaultTrackSelector;
|
import com.google.android.exoplayer2.trackselection.DefaultTrackSelector;
|
||||||
import com.google.android.exoplayer2.trackselection.MappingTrackSelector.MappedTrackInfo;
|
import com.google.android.exoplayer2.trackselection.MappingTrackSelector.MappedTrackInfo;
|
||||||
|
|
@ -75,7 +64,6 @@ import com.google.android.exoplayer2.ui.PlayerView;
|
||||||
import com.google.android.exoplayer2.ui.spherical.SphericalGLSurfaceView;
|
import com.google.android.exoplayer2.ui.spherical.SphericalGLSurfaceView;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
||||||
import com.google.android.exoplayer2.util.Assertions;
|
|
||||||
import com.google.android.exoplayer2.util.ErrorMessageProvider;
|
import com.google.android.exoplayer2.util.ErrorMessageProvider;
|
||||||
import com.google.android.exoplayer2.util.EventLogger;
|
import com.google.android.exoplayer2.util.EventLogger;
|
||||||
import com.google.android.exoplayer2.util.Util;
|
import com.google.android.exoplayer2.util.Util;
|
||||||
|
|
@ -85,7 +73,9 @@ import java.net.CookieManager;
|
||||||
import java.net.CookiePolicy;
|
import java.net.CookiePolicy;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/** An activity that plays media using {@link SimpleExoPlayer}. */
|
/** An activity that plays media using {@link SimpleExoPlayer}. */
|
||||||
public class PlayerActivity extends AppCompatActivity
|
public class PlayerActivity extends AppCompatActivity
|
||||||
|
|
@ -156,7 +146,7 @@ public class PlayerActivity extends AppCompatActivity
|
||||||
private DefaultTrackSelector.Parameters trackSelectorParameters;
|
private DefaultTrackSelector.Parameters trackSelectorParameters;
|
||||||
private DebugTextViewHelper debugViewHelper;
|
private DebugTextViewHelper debugViewHelper;
|
||||||
private TrackGroupArray lastSeenTrackGroupArray;
|
private TrackGroupArray lastSeenTrackGroupArray;
|
||||||
|
private DefaultMediaSourceFactory mediaSourceFactory;
|
||||||
private boolean startAutoPlay;
|
private boolean startAutoPlay;
|
||||||
private int startWindow;
|
private int startWindow;
|
||||||
private long startPosition;
|
private long startPosition;
|
||||||
|
|
@ -177,6 +167,8 @@ public class PlayerActivity extends AppCompatActivity
|
||||||
}
|
}
|
||||||
super.onCreate(savedInstanceState);
|
super.onCreate(savedInstanceState);
|
||||||
dataSourceFactory = buildDataSourceFactory();
|
dataSourceFactory = buildDataSourceFactory();
|
||||||
|
mediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(/* context= */ this, dataSourceFactory);
|
||||||
if (CookieHandler.getDefault() != DEFAULT_COOKIE_MANAGER) {
|
if (CookieHandler.getDefault() != DEFAULT_COOKIE_MANAGER) {
|
||||||
CookieHandler.setDefault(DEFAULT_COOKIE_MANAGER);
|
CookieHandler.setDefault(DEFAULT_COOKIE_MANAGER);
|
||||||
}
|
}
|
||||||
|
|
@ -480,30 +472,28 @@ public class PlayerActivity extends AppCompatActivity
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private MediaSource createLeafMediaSource(UriSample parameters) {
|
private MediaSource createLeafMediaSource(UriSample parameters) {
|
||||||
Sample.DrmInfo drmInfo = parameters.drmInfo;
|
MediaItem.Builder builder = new MediaItem.Builder().setSourceUri(parameters.uri);
|
||||||
int errorStringId = R.string.error_drm_unknown;
|
if (parameters.extension != null) {
|
||||||
DrmSessionManager<ExoMediaCrypto> drmSessionManager = null;
|
builder.setExtension(parameters.extension);
|
||||||
if (drmInfo == null) {
|
|
||||||
drmSessionManager = DrmSessionManager.getDummyDrmSessionManager();
|
|
||||||
} else if (Util.SDK_INT < 18) {
|
|
||||||
errorStringId = R.string.error_drm_unsupported_before_api_18;
|
|
||||||
} else if (!MediaDrm.isCryptoSchemeSupported(drmInfo.drmScheme)) {
|
|
||||||
errorStringId = R.string.error_drm_unsupported_scheme;
|
|
||||||
} else {
|
|
||||||
MediaDrmCallback mediaDrmCallback =
|
|
||||||
createMediaDrmCallback(drmInfo.drmLicenseUrl, drmInfo.drmKeyRequestProperties);
|
|
||||||
drmSessionManager =
|
|
||||||
new DefaultDrmSessionManager.Builder()
|
|
||||||
.setUuidAndExoMediaDrmProvider(drmInfo.drmScheme, FrameworkMediaDrm.DEFAULT_PROVIDER)
|
|
||||||
.setMultiSession(drmInfo.drmMultiSession)
|
|
||||||
.setUseDrmSessionsForClearContent(drmInfo.drmSessionForClearTypes)
|
|
||||||
.build(mediaDrmCallback);
|
|
||||||
}
|
}
|
||||||
|
int[] drmSessionForClearTypes = new int[0];
|
||||||
if (drmSessionManager == null) {
|
HttpDataSource.Factory drmDataSourceFactory = null;
|
||||||
showToast(errorStringId);
|
if (parameters.drmInfo != null) {
|
||||||
finish();
|
if (Util.SDK_INT < 18) {
|
||||||
return null;
|
showToast(R.string.error_drm_unsupported_before_api_18);
|
||||||
|
finish();
|
||||||
|
return null;
|
||||||
|
} else if (!MediaDrm.isCryptoSchemeSupported(parameters.drmInfo.drmScheme)) {
|
||||||
|
showToast(R.string.error_drm_unsupported_scheme);
|
||||||
|
finish();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
builder
|
||||||
|
.setDrmLicenseUri(createLicenseUriBundle(parameters.drmInfo))
|
||||||
|
.setDrmUuid(parameters.drmInfo.drmScheme)
|
||||||
|
.setDrmMultiSession(parameters.drmInfo.drmMultiSession);
|
||||||
|
drmSessionForClearTypes = parameters.drmInfo.drmSessionForClearTypes;
|
||||||
|
drmDataSourceFactory = ((DemoApplication) getApplication()).buildHttpDataSourceFactory();
|
||||||
}
|
}
|
||||||
|
|
||||||
DownloadRequest downloadRequest =
|
DownloadRequest downloadRequest =
|
||||||
|
|
@ -513,47 +503,22 @@ public class PlayerActivity extends AppCompatActivity
|
||||||
if (downloadRequest != null) {
|
if (downloadRequest != null) {
|
||||||
return DownloadHelper.createMediaSource(downloadRequest, dataSourceFactory);
|
return DownloadHelper.createMediaSource(downloadRequest, dataSourceFactory);
|
||||||
}
|
}
|
||||||
return createLeafMediaSource(parameters.uri, parameters.extension, drmSessionManager);
|
return mediaSourceFactory
|
||||||
|
.setDrmHttpDataSourceFactory(drmDataSourceFactory)
|
||||||
|
.setUseDrmSessionForClearContent(drmSessionForClearTypes)
|
||||||
|
.createMediaSource(builder.build());
|
||||||
}
|
}
|
||||||
|
|
||||||
private MediaSource createLeafMediaSource(
|
private static MediaItem.UriBundle createLicenseUriBundle(Sample.DrmInfo drmInfo) {
|
||||||
Uri uri, String extension, DrmSessionManager<?> drmSessionManager) {
|
Uri licenseUri = Uri.parse(drmInfo.drmLicenseUrl);
|
||||||
@ContentType int type = Util.inferContentType(uri, extension);
|
if (drmInfo.drmKeyRequestProperties == null || drmInfo.drmKeyRequestProperties.length == 0) {
|
||||||
switch (type) {
|
return new MediaItem.UriBundle(licenseUri);
|
||||||
case C.TYPE_DASH:
|
|
||||||
return new DashMediaSource.Factory(dataSourceFactory)
|
|
||||||
.setDrmSessionManager(drmSessionManager)
|
|
||||||
.createMediaSource(uri);
|
|
||||||
case C.TYPE_SS:
|
|
||||||
return new SsMediaSource.Factory(dataSourceFactory)
|
|
||||||
.setDrmSessionManager(drmSessionManager)
|
|
||||||
.createMediaSource(uri);
|
|
||||||
case C.TYPE_HLS:
|
|
||||||
return new HlsMediaSource.Factory(dataSourceFactory)
|
|
||||||
.setDrmSessionManager(drmSessionManager)
|
|
||||||
.createMediaSource(uri);
|
|
||||||
case C.TYPE_OTHER:
|
|
||||||
return new ProgressiveMediaSource.Factory(dataSourceFactory)
|
|
||||||
.setDrmSessionManager(drmSessionManager)
|
|
||||||
.createMediaSource(uri);
|
|
||||||
default:
|
|
||||||
throw new IllegalStateException("Unsupported type: " + type);
|
|
||||||
}
|
}
|
||||||
}
|
Map<String, String> headers = new HashMap<>();
|
||||||
|
for (int i = 0; i < drmInfo.drmKeyRequestProperties.length; i += 2) {
|
||||||
private HttpMediaDrmCallback createMediaDrmCallback(
|
headers.put(drmInfo.drmKeyRequestProperties[i], drmInfo.drmKeyRequestProperties[i + 1]);
|
||||||
String licenseUrl, String[] keyRequestPropertiesArray) {
|
|
||||||
HttpDataSource.Factory licenseDataSourceFactory =
|
|
||||||
((DemoApplication) getApplication()).buildHttpDataSourceFactory();
|
|
||||||
HttpMediaDrmCallback drmCallback =
|
|
||||||
new HttpMediaDrmCallback(licenseUrl, licenseDataSourceFactory);
|
|
||||||
if (keyRequestPropertiesArray != null) {
|
|
||||||
for (int i = 0; i < keyRequestPropertiesArray.length - 1; i += 2) {
|
|
||||||
drmCallback.setKeyRequestProperty(keyRequestPropertiesArray[i],
|
|
||||||
keyRequestPropertiesArray[i + 1]);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return drmCallback;
|
return new MediaItem.UriBundle(licenseUri, headers);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void releasePlayer() {
|
private void releasePlayer() {
|
||||||
|
|
@ -623,35 +588,7 @@ public class PlayerActivity extends AppCompatActivity
|
||||||
// LINT.ThenChange(../../../../../../../../proguard-rules.txt)
|
// LINT.ThenChange(../../../../../../../../proguard-rules.txt)
|
||||||
adsLoader = loaderConstructor.newInstance(this, adTagUri);
|
adsLoader = loaderConstructor.newInstance(this, adTagUri);
|
||||||
}
|
}
|
||||||
MediaSourceFactory adMediaSourceFactory =
|
return new AdsMediaSource(mediaSource, mediaSourceFactory, adsLoader, playerView);
|
||||||
new MediaSourceFactory() {
|
|
||||||
|
|
||||||
private DrmSessionManager<?> drmSessionManager =
|
|
||||||
DrmSessionManager.getDummyDrmSessionManager();
|
|
||||||
|
|
||||||
@Override
|
|
||||||
@NonNull
|
|
||||||
public MediaSourceFactory setDrmSessionManager(DrmSessionManager<?> drmSessionManager) {
|
|
||||||
this.drmSessionManager = drmSessionManager;
|
|
||||||
return this;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
@NonNull
|
|
||||||
public MediaSource createMediaSource(@NonNull MediaItem mediaItem) {
|
|
||||||
Assertions.checkNotNull(mediaItem.playbackProperties);
|
|
||||||
return PlayerActivity.this.createLeafMediaSource(
|
|
||||||
mediaItem.playbackProperties.sourceUri,
|
|
||||||
mediaItem.playbackProperties.extension,
|
|
||||||
drmSessionManager);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int[] getSupportedTypes() {
|
|
||||||
return new int[] {C.TYPE_DASH, C.TYPE_SS, C.TYPE_HLS, C.TYPE_OTHER};
|
|
||||||
}
|
|
||||||
};
|
|
||||||
return new AdsMediaSource(mediaSource, adMediaSourceFactory, adsLoader, playerView);
|
|
||||||
} catch (ClassNotFoundException e) {
|
} catch (ClassNotFoundException e) {
|
||||||
// IMA extension not loaded.
|
// IMA extension not loaded.
|
||||||
return null;
|
return null;
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,329 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2020 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package com.google.android.exoplayer2.source;
|
||||||
|
|
||||||
|
import android.content.Context;
|
||||||
|
import android.util.SparseArray;
|
||||||
|
import androidx.annotation.Nullable;
|
||||||
|
import com.google.android.exoplayer2.C;
|
||||||
|
import com.google.android.exoplayer2.ExoPlayerLibraryInfo;
|
||||||
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
import com.google.android.exoplayer2.drm.DefaultDrmSessionManager;
|
||||||
|
import com.google.android.exoplayer2.drm.DrmSessionManager;
|
||||||
|
import com.google.android.exoplayer2.drm.FrameworkMediaDrm;
|
||||||
|
import com.google.android.exoplayer2.drm.HttpMediaDrmCallback;
|
||||||
|
import com.google.android.exoplayer2.drm.MediaDrmCallback;
|
||||||
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
|
import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
|
||||||
|
import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
|
||||||
|
import com.google.android.exoplayer2.upstream.DefaultLoadErrorHandlingPolicy;
|
||||||
|
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
||||||
|
import com.google.android.exoplayer2.upstream.LoadErrorHandlingPolicy;
|
||||||
|
import com.google.android.exoplayer2.util.Assertions;
|
||||||
|
import com.google.android.exoplayer2.util.Util;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The default {@link MediaSourceFactory} implementation.
|
||||||
|
*
|
||||||
|
* <p>This implementation delegates calls to {@link #createMediaSource(MediaItem)} to the following
|
||||||
|
* factories:
|
||||||
|
*
|
||||||
|
* <ul>
|
||||||
|
* <li>{@code DashMediaSource.Factory} if the item's {@link MediaItem.PlaybackProperties#sourceUri
|
||||||
|
* sourceUri} ends in '.mpd' or if its {@link MediaItem.PlaybackProperties#extension extension
|
||||||
|
* field} is explicitly set to 'mpd' (Requires the <a
|
||||||
|
* href="https://exoplayer.dev/hello-world.html#add-exoplayer-modules">exoplayer-dash module
|
||||||
|
* to be added</a> to the app).
|
||||||
|
* <li>{@code HlsMediaSource.Factory} if the item's {@link MediaItem.PlaybackProperties#sourceUri
|
||||||
|
* sourceUri} ends in '.m3u8' or if its {@link MediaItem.PlaybackProperties#extension
|
||||||
|
* extension field} is explicitly set to 'hls' (Requires the <a
|
||||||
|
* href="https://exoplayer.dev/hello-world.html#add-exoplayer-modules">exoplayer-hls module to
|
||||||
|
* be added</a> to the app).
|
||||||
|
* <li>{@code SsMediaSource.Factory} if the item's {@link MediaItem.PlaybackProperties#sourceUri
|
||||||
|
* sourceUri} ends in '.ism', '.ism/Manifest' or if its {@link
|
||||||
|
* MediaItem.PlaybackProperties#extension extension field} is explicitly set to 'ism'
|
||||||
|
* (Requires the <a href="https://exoplayer.dev/hello-world.html#add-exoplayer-modules">
|
||||||
|
* exoplayer-smoothstreaming module to be added</a> to the app).
|
||||||
|
* <li>{@link ProgressiveMediaSource.Factory} serves as a fallback if the item's {@link
|
||||||
|
* MediaItem.PlaybackProperties#sourceUri sourceUri} doesn't match one of the above. It tries
|
||||||
|
* to infer the required extractor by using the {@link
|
||||||
|
* com.google.android.exoplayer2.extractor.DefaultExtractorsFactory}. An {@link
|
||||||
|
* UnrecognizedInputFormatException} is thrown if none of the available extractors can read
|
||||||
|
* the stream.
|
||||||
|
* </ul>
|
||||||
|
*
|
||||||
|
* <h3>DrmSessionManager creation for protected content</h3>
|
||||||
|
*
|
||||||
|
* <p>For a media item with a valid {@link
|
||||||
|
* com.google.android.exoplayer2.MediaItem.DrmConfiguration}, a {@link DefaultDrmSessionManager} is
|
||||||
|
* created. The following setters can be used to optionally configure the creation:
|
||||||
|
*
|
||||||
|
* <ul>
|
||||||
|
* <li>{@link #setPlayClearContentWithoutKey(boolean)}: See {@link
|
||||||
|
* DefaultDrmSessionManager.Builder#setPlayClearSamplesWithoutKeys(boolean)} (default: {@code
|
||||||
|
* false}).
|
||||||
|
* <li>{@link #setUseDrmSessionForClearContent(int...)}: See {@link
|
||||||
|
* DefaultDrmSessionManager.Builder#setUseDrmSessionsForClearContent(int...)} (default: none).
|
||||||
|
* <li>{@link #setDrmHttpDataSourceFactory(HttpDataSource.Factory)}: Sets the data source factory
|
||||||
|
* to be used by the {@link HttpMediaDrmCallback} for network requests (default: {@link
|
||||||
|
* DefaultHttpDataSourceFactory}).
|
||||||
|
* </ul>
|
||||||
|
*
|
||||||
|
* <p>For media items without a drm configuration {@link DrmSessionManager#DUMMY} is used. To use an
|
||||||
|
* alternative dummy, apps can pass a drm session manager to {@link
|
||||||
|
* #setDrmSessionManager(DrmSessionManager)} which will be used for all items without a drm
|
||||||
|
* configuration.
|
||||||
|
*/
|
||||||
|
public final class DefaultMediaSourceFactory implements MediaSourceFactory {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A media source factory to which calls to {@link #createMediaSource(MediaItem)} calls are
|
||||||
|
* delegated by the {@link DefaultMediaSourceFactory}.
|
||||||
|
*/
|
||||||
|
public interface Delegate extends MediaSourceFactory {
|
||||||
|
/**
|
||||||
|
* Sets an optional {@link LoadErrorHandlingPolicy}.
|
||||||
|
*
|
||||||
|
* @param loadErrorHandlingPolicy A {@link LoadErrorHandlingPolicy}.
|
||||||
|
* @return This factory, for convenience.
|
||||||
|
*/
|
||||||
|
MediaSourceFactory setLoadErrorHandlingPolicy(
|
||||||
|
@Nullable LoadErrorHandlingPolicy loadErrorHandlingPolicy);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a new instance with the given {@link Context}.
|
||||||
|
*
|
||||||
|
* <p>This is functionally equivalent with calling {@code #newInstance(Context,
|
||||||
|
* DefaultDataSourceFactory)}.
|
||||||
|
*
|
||||||
|
* @param context The {@link Context}.
|
||||||
|
*/
|
||||||
|
public static DefaultMediaSourceFactory newInstance(Context context) {
|
||||||
|
return newInstance(
|
||||||
|
context,
|
||||||
|
new DefaultDataSourceFactory(
|
||||||
|
context, Util.getUserAgent(context, ExoPlayerLibraryInfo.VERSION_SLASHY)));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates a new instance with the given {@link Context} and {@link DataSource.Factory}.
|
||||||
|
*
|
||||||
|
* @param context The {@link Context}.
|
||||||
|
* @param dataSourceFactory A {@link DataSource.Factory} to be used to create media sources.
|
||||||
|
*/
|
||||||
|
public static DefaultMediaSourceFactory newInstance(
|
||||||
|
Context context, DataSource.Factory dataSourceFactory) {
|
||||||
|
return new DefaultMediaSourceFactory(context, dataSourceFactory);
|
||||||
|
}
|
||||||
|
|
||||||
|
private final SparseArray<Delegate> mediaSourceFactories;
|
||||||
|
@C.ContentType private final int[] supportedTypes;
|
||||||
|
private final String userAgent;
|
||||||
|
|
||||||
|
private DrmSessionManager<?> drmSessionManager;
|
||||||
|
private HttpDataSource.Factory drmHttpDataSourceFactory;
|
||||||
|
private boolean playClearContentWithoutKey;
|
||||||
|
private int[] useDrmSessionsForClearContentTrackTypes;
|
||||||
|
@Nullable private List<StreamKey> streamKeys;
|
||||||
|
|
||||||
|
private DefaultMediaSourceFactory(Context context, DataSource.Factory dataSourceFactory) {
|
||||||
|
drmSessionManager = DrmSessionManager.getDummyDrmSessionManager();
|
||||||
|
userAgent = Util.getUserAgent(context, ExoPlayerLibraryInfo.VERSION_SLASHY);
|
||||||
|
drmHttpDataSourceFactory = new DefaultHttpDataSourceFactory(userAgent);
|
||||||
|
useDrmSessionsForClearContentTrackTypes = new int[0];
|
||||||
|
mediaSourceFactories = loadDelegates(dataSourceFactory);
|
||||||
|
supportedTypes = new int[mediaSourceFactories.size()];
|
||||||
|
for (int i = 0; i < mediaSourceFactories.size(); i++) {
|
||||||
|
supportedTypes[i] = mediaSourceFactories.keyAt(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sets the {@link HttpDataSource.Factory} to be used for creating {@link HttpMediaDrmCallback
|
||||||
|
* HttpMediaDrmCallbacks} which executes key and provisioning requests over HTTP. If {@code null}
|
||||||
|
* is passed the {@link DefaultHttpDataSourceFactory} is used.
|
||||||
|
*
|
||||||
|
* @param drmHttpDataSourceFactory The HTTP data source factory or {@code null} to use {@link
|
||||||
|
* DefaultHttpDataSourceFactory}.
|
||||||
|
* @return This factory, for convenience.
|
||||||
|
*/
|
||||||
|
public DefaultMediaSourceFactory setDrmHttpDataSourceFactory(
|
||||||
|
@Nullable HttpDataSource.Factory drmHttpDataSourceFactory) {
|
||||||
|
this.drmHttpDataSourceFactory =
|
||||||
|
drmHttpDataSourceFactory != null
|
||||||
|
? drmHttpDataSourceFactory
|
||||||
|
: new DefaultHttpDataSourceFactory(userAgent);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Used to create {@link DrmSessionManager DrmSessionManagers}. See {@link
|
||||||
|
* DefaultDrmSessionManager.Builder#setPlayClearSamplesWithoutKeys(boolean)}.
|
||||||
|
*
|
||||||
|
* @return This factory, for convenience.
|
||||||
|
*/
|
||||||
|
public DefaultMediaSourceFactory setPlayClearContentWithoutKey(
|
||||||
|
boolean playClearContentWithoutKey) {
|
||||||
|
this.playClearContentWithoutKey = playClearContentWithoutKey;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Used to create {@link DrmSessionManager DrmSessionManagers}. See {@link
|
||||||
|
* DefaultDrmSessionManager.Builder#setUseDrmSessionsForClearContent(int...)}.
|
||||||
|
*
|
||||||
|
* @return This factory, for convenience.
|
||||||
|
*/
|
||||||
|
public DefaultMediaSourceFactory setUseDrmSessionForClearContent(
|
||||||
|
int... useDrmSessionsForClearContentTrackTypes) {
|
||||||
|
for (int trackType : useDrmSessionsForClearContentTrackTypes) {
|
||||||
|
Assertions.checkArgument(trackType == C.TRACK_TYPE_VIDEO || trackType == C.TRACK_TYPE_AUDIO);
|
||||||
|
}
|
||||||
|
this.useDrmSessionsForClearContentTrackTypes = useDrmSessionsForClearContentTrackTypes.clone();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public DefaultMediaSourceFactory setDrmSessionManager(
|
||||||
|
@Nullable DrmSessionManager<?> drmSessionManager) {
|
||||||
|
this.drmSessionManager =
|
||||||
|
drmSessionManager != null
|
||||||
|
? drmSessionManager
|
||||||
|
: DrmSessionManager.getDummyDrmSessionManager();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
public DefaultMediaSourceFactory setLoadErrorHandlingPolicy(
|
||||||
|
@Nullable LoadErrorHandlingPolicy loadErrorHandlingPolicy) {
|
||||||
|
LoadErrorHandlingPolicy newLoadErrorHandlingPolicy =
|
||||||
|
loadErrorHandlingPolicy != null
|
||||||
|
? loadErrorHandlingPolicy
|
||||||
|
: new DefaultLoadErrorHandlingPolicy();
|
||||||
|
for (int i = 0; i < mediaSourceFactories.size(); i++) {
|
||||||
|
mediaSourceFactories.valueAt(i).setLoadErrorHandlingPolicy(newLoadErrorHandlingPolicy);
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @deprecated Use {@link MediaItem.Builder#setStreamKeys(List)} and {@link
|
||||||
|
* #createMediaSource(MediaItem)} instead.
|
||||||
|
*/
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
@Deprecated
|
||||||
|
@Override
|
||||||
|
public DefaultMediaSourceFactory setStreamKeys(@Nullable List<StreamKey> streamKeys) {
|
||||||
|
this.streamKeys = streamKeys != null && !streamKeys.isEmpty() ? streamKeys : null;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int[] getSupportedTypes() {
|
||||||
|
return Arrays.copyOf(supportedTypes, supportedTypes.length);
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
@Override
|
||||||
|
public MediaSource createMediaSource(MediaItem mediaItem) {
|
||||||
|
Assertions.checkNotNull(mediaItem.playbackProperties);
|
||||||
|
@C.ContentType
|
||||||
|
int type =
|
||||||
|
Util.inferContentType(
|
||||||
|
mediaItem.playbackProperties.sourceUri, mediaItem.playbackProperties.extension);
|
||||||
|
@Nullable MediaSourceFactory mediaSourceFactory = mediaSourceFactories.get(type);
|
||||||
|
Assertions.checkNotNull(
|
||||||
|
mediaSourceFactory, "No suitable media source factory found for content type: " + type);
|
||||||
|
mediaSourceFactory.setDrmSessionManager(createDrmSessionManager(mediaItem));
|
||||||
|
mediaSourceFactory.setStreamKeys(
|
||||||
|
!mediaItem.playbackProperties.streamKeys.isEmpty()
|
||||||
|
? mediaItem.playbackProperties.streamKeys
|
||||||
|
: streamKeys);
|
||||||
|
return mediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
}
|
||||||
|
|
||||||
|
// internal methods
|
||||||
|
|
||||||
|
private DrmSessionManager<?> createDrmSessionManager(MediaItem mediaItem) {
|
||||||
|
Assertions.checkNotNull(mediaItem.playbackProperties);
|
||||||
|
if (mediaItem.playbackProperties.drmConfiguration == null
|
||||||
|
|| mediaItem.playbackProperties.drmConfiguration.licenseUri == null
|
||||||
|
|| Util.SDK_INT < 18) {
|
||||||
|
return drmSessionManager;
|
||||||
|
}
|
||||||
|
return new DefaultDrmSessionManager.Builder()
|
||||||
|
.setUuidAndExoMediaDrmProvider(
|
||||||
|
mediaItem.playbackProperties.drmConfiguration.uuid, FrameworkMediaDrm.DEFAULT_PROVIDER)
|
||||||
|
.setMultiSession(mediaItem.playbackProperties.drmConfiguration.multiSession)
|
||||||
|
.setPlayClearSamplesWithoutKeys(playClearContentWithoutKey)
|
||||||
|
.setUseDrmSessionsForClearContent(useDrmSessionsForClearContentTrackTypes)
|
||||||
|
.build(createHttpMediaDrmCallback(mediaItem.playbackProperties.drmConfiguration));
|
||||||
|
}
|
||||||
|
|
||||||
|
private MediaDrmCallback createHttpMediaDrmCallback(MediaItem.DrmConfiguration drmConfiguration) {
|
||||||
|
Assertions.checkNotNull(drmConfiguration.licenseUri);
|
||||||
|
HttpMediaDrmCallback drmCallback =
|
||||||
|
new HttpMediaDrmCallback(
|
||||||
|
drmConfiguration.licenseUri.uri.toString(), drmHttpDataSourceFactory);
|
||||||
|
for (Map.Entry<String, String> entry : drmConfiguration.licenseUri.requestHeaders.entrySet()) {
|
||||||
|
drmCallback.setKeyRequestProperty(entry.getKey(), entry.getValue());
|
||||||
|
}
|
||||||
|
return drmCallback;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static SparseArray<Delegate> loadDelegates(DataSource.Factory dataSourceFactory) {
|
||||||
|
SparseArray<Delegate> delegates = new SparseArray<>();
|
||||||
|
// LINT.IfChange
|
||||||
|
try {
|
||||||
|
Class<? extends DefaultMediaSourceFactory.Delegate> factoryClazz =
|
||||||
|
Class.forName("com.google.android.exoplayer2.source.dash.DashMediaSource$Factory")
|
||||||
|
.asSubclass(DefaultMediaSourceFactory.Delegate.class);
|
||||||
|
delegates.put(
|
||||||
|
C.TYPE_DASH,
|
||||||
|
factoryClazz.getConstructor(DataSource.Factory.class).newInstance(dataSourceFactory));
|
||||||
|
} catch (Exception e) {
|
||||||
|
// Expected if the app was built without the dash module.
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
Class<? extends DefaultMediaSourceFactory.Delegate> factoryClazz =
|
||||||
|
Class.forName(
|
||||||
|
"com.google.android.exoplayer2.source.smoothstreaming.SsMediaSource$Factory")
|
||||||
|
.asSubclass(DefaultMediaSourceFactory.Delegate.class);
|
||||||
|
delegates.put(
|
||||||
|
C.TYPE_SS,
|
||||||
|
factoryClazz.getConstructor(DataSource.Factory.class).newInstance(dataSourceFactory));
|
||||||
|
} catch (Exception e) {
|
||||||
|
// Expected if the app was built without the smoothstreaming module.
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
Class<? extends DefaultMediaSourceFactory.Delegate> factoryClazz =
|
||||||
|
Class.forName("com.google.android.exoplayer2.source.hls.HlsMediaSource$Factory")
|
||||||
|
.asSubclass(DefaultMediaSourceFactory.Delegate.class);
|
||||||
|
delegates.put(
|
||||||
|
C.TYPE_HLS,
|
||||||
|
factoryClazz.getConstructor(DataSource.Factory.class).newInstance(dataSourceFactory));
|
||||||
|
} catch (Exception e) {
|
||||||
|
// Expected if the app was built without the hls module.
|
||||||
|
}
|
||||||
|
// LINT.ThenChange(../../../../../../../../proguard-rules.txt)
|
||||||
|
delegates.put(C.TYPE_OTHER, new ProgressiveMediaSource.Factory(dataSourceFactory));
|
||||||
|
return delegates;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -112,7 +112,7 @@ public final class ExtractorMediaSource extends CompositeMediaSource<Void> {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#tag} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setTag(Object)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
|
|
||||||
|
|
@ -47,7 +47,7 @@ public final class ProgressiveMediaSource extends BaseMediaSource
|
||||||
implements ProgressiveMediaPeriod.Listener {
|
implements ProgressiveMediaPeriod.Listener {
|
||||||
|
|
||||||
/** Factory for {@link ProgressiveMediaSource}s. */
|
/** Factory for {@link ProgressiveMediaSource}s. */
|
||||||
public static final class Factory implements MediaSourceFactory {
|
public static final class Factory implements DefaultMediaSourceFactory.Delegate {
|
||||||
|
|
||||||
private final DataSource.Factory dataSourceFactory;
|
private final DataSource.Factory dataSourceFactory;
|
||||||
|
|
||||||
|
|
@ -108,7 +108,7 @@ public final class ProgressiveMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#tag} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setTag(Object)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,92 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2020 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package com.google.android.exoplayer2.source;
|
||||||
|
|
||||||
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
|
import androidx.test.core.app.ApplicationProvider;
|
||||||
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
|
import com.google.android.exoplayer2.C;
|
||||||
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.runner.RunWith;
|
||||||
|
|
||||||
|
/** Unit test for {@link DefaultMediaSourceFactory}. */
|
||||||
|
@RunWith(AndroidJUnit4.class)
|
||||||
|
public final class DefaultMediaSourceFactoryTest {
|
||||||
|
|
||||||
|
private static final String URI_MEDIA = "http://exoplayer.dev/video";
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withExtension_progressiveSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("mp4").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(ProgressiveMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withTag_tagInSource() {
|
||||||
|
Object tag = new Object();
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA).setTag(tag).build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource.getTag()).isEqualTo(tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withPath_progressiveSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.mp3").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(ProgressiveMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withNull_usesNonNullDefaults() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA).build();
|
||||||
|
|
||||||
|
MediaSource mediaSource =
|
||||||
|
defaultMediaSourceFactory
|
||||||
|
.setDrmSessionManager(null)
|
||||||
|
.setDrmHttpDataSourceFactory(null)
|
||||||
|
.setLoadErrorHandlingPolicy(null)
|
||||||
|
.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isNotNull();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSupportedTypes_coreModule_onlyOther() {
|
||||||
|
int[] supportedTypes =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext())
|
||||||
|
.getSupportedTypes();
|
||||||
|
|
||||||
|
assertThat(supportedTypes).asList().containsExactly(C.TYPE_OTHER);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -33,11 +33,11 @@ import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.BaseMediaSource;
|
import com.google.android.exoplayer2.source.BaseMediaSource;
|
||||||
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
||||||
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
import com.google.android.exoplayer2.source.MediaPeriod;
|
import com.google.android.exoplayer2.source.MediaPeriod;
|
||||||
import com.google.android.exoplayer2.source.MediaSource;
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceFactory;
|
|
||||||
import com.google.android.exoplayer2.source.SequenceableLoader;
|
import com.google.android.exoplayer2.source.SequenceableLoader;
|
||||||
import com.google.android.exoplayer2.source.dash.PlayerEmsgHandler.PlayerEmsgCallback;
|
import com.google.android.exoplayer2.source.dash.PlayerEmsgHandler.PlayerEmsgCallback;
|
||||||
import com.google.android.exoplayer2.source.dash.manifest.AdaptationSet;
|
import com.google.android.exoplayer2.source.dash.manifest.AdaptationSet;
|
||||||
|
|
@ -79,7 +79,7 @@ public final class DashMediaSource extends BaseMediaSource {
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Factory for {@link DashMediaSource}s. */
|
/** Factory for {@link DashMediaSource}s. */
|
||||||
public static final class Factory implements MediaSourceFactory {
|
public static final class Factory implements DefaultMediaSourceFactory.Delegate {
|
||||||
|
|
||||||
private final DashChunkSource.Factory chunkSourceFactory;
|
private final DashChunkSource.Factory chunkSourceFactory;
|
||||||
@Nullable private final DataSource.Factory manifestDataSourceFactory;
|
@Nullable private final DataSource.Factory manifestDataSourceFactory;
|
||||||
|
|
@ -125,7 +125,7 @@ public final class DashMediaSource extends BaseMediaSource {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#tag} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setTag(Object)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
|
@ -135,7 +135,7 @@ public final class DashMediaSource extends BaseMediaSource {
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#streamKeys} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setStreamKeys(List)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("deprecation")
|
@SuppressWarnings("deprecation")
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,95 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2020 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package com.google.android.exoplayer2.source.dash;
|
||||||
|
|
||||||
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
|
import androidx.test.core.app.ApplicationProvider;
|
||||||
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
|
import com.google.android.exoplayer2.C;
|
||||||
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.runner.RunWith;
|
||||||
|
|
||||||
|
/** Unit test for creating DASH media sources with the {@link DefaultMediaSourceFactory}. */
|
||||||
|
@RunWith(AndroidJUnit4.class)
|
||||||
|
public class DefaultMediaSourceFactoryTest {
|
||||||
|
|
||||||
|
private static final String URI_MEDIA = "http://exoplayer.dev/video";
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withExtension_dashSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("mpd").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(DashMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withTag_tagInSource() {
|
||||||
|
Object tag = new Object();
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("mpd").setTag(tag).build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource.getTag()).isEqualTo(tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withPath_dashSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.mpd").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(DashMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withNull_usesNonNullDefaults() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.mpd").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource =
|
||||||
|
defaultMediaSourceFactory
|
||||||
|
.setDrmSessionManager(null)
|
||||||
|
.setDrmHttpDataSourceFactory(null)
|
||||||
|
.setLoadErrorHandlingPolicy(null)
|
||||||
|
.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isNotNull();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSupportedTypes_dashModule_containsTypeDash() {
|
||||||
|
int[] supportedTypes =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext())
|
||||||
|
.getSupportedTypes();
|
||||||
|
|
||||||
|
assertThat(supportedTypes).asList().containsExactly(C.TYPE_OTHER, C.TYPE_DASH);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -31,11 +31,11 @@ import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.BaseMediaSource;
|
import com.google.android.exoplayer2.source.BaseMediaSource;
|
||||||
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
||||||
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
import com.google.android.exoplayer2.source.MediaPeriod;
|
import com.google.android.exoplayer2.source.MediaPeriod;
|
||||||
import com.google.android.exoplayer2.source.MediaSource;
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceFactory;
|
|
||||||
import com.google.android.exoplayer2.source.SequenceableLoader;
|
import com.google.android.exoplayer2.source.SequenceableLoader;
|
||||||
import com.google.android.exoplayer2.source.SinglePeriodTimeline;
|
import com.google.android.exoplayer2.source.SinglePeriodTimeline;
|
||||||
import com.google.android.exoplayer2.source.hls.playlist.DefaultHlsPlaylistParserFactory;
|
import com.google.android.exoplayer2.source.hls.playlist.DefaultHlsPlaylistParserFactory;
|
||||||
|
|
@ -87,7 +87,7 @@ public final class HlsMediaSource extends BaseMediaSource
|
||||||
public static final int METADATA_TYPE_EMSG = 3;
|
public static final int METADATA_TYPE_EMSG = 3;
|
||||||
|
|
||||||
/** Factory for {@link HlsMediaSource}s. */
|
/** Factory for {@link HlsMediaSource}s. */
|
||||||
public static final class Factory implements MediaSourceFactory {
|
public static final class Factory implements DefaultMediaSourceFactory.Delegate {
|
||||||
|
|
||||||
private final HlsDataSourceFactory hlsDataSourceFactory;
|
private final HlsDataSourceFactory hlsDataSourceFactory;
|
||||||
|
|
||||||
|
|
@ -133,7 +133,7 @@ public final class HlsMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#tag} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setTag(Object)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
|
@ -299,7 +299,7 @@ public final class HlsMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#streamKeys} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setStreamKeys(List)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("deprecation")
|
@SuppressWarnings("deprecation")
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,95 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2020 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package com.google.android.exoplayer2.source.hls;
|
||||||
|
|
||||||
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
|
import androidx.test.core.app.ApplicationProvider;
|
||||||
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
|
import com.google.android.exoplayer2.C;
|
||||||
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.runner.RunWith;
|
||||||
|
|
||||||
|
/** Unit test for creating HLS media sources with the {@link DefaultMediaSourceFactory}. */
|
||||||
|
@RunWith(AndroidJUnit4.class)
|
||||||
|
public class DefaultMediaSourceFactoryTest {
|
||||||
|
|
||||||
|
private static final String URI_MEDIA = "http://exoplayer.dev/video";
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withExtension_hlsSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("m3u8").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(HlsMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withTag_tagInSource() {
|
||||||
|
Object tag = new Object();
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("m3u8").setTag(tag).build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource.getTag()).isEqualTo(tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testCreateMediaSource_withPath_hlsSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.m3u8").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(HlsMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withNull_usesNonNullDefaults() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.m3u8").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource =
|
||||||
|
defaultMediaSourceFactory
|
||||||
|
.setDrmSessionManager(null)
|
||||||
|
.setDrmHttpDataSourceFactory(null)
|
||||||
|
.setLoadErrorHandlingPolicy(null)
|
||||||
|
.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isNotNull();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSupportedTypes_hlsModule_containsTypeHls() {
|
||||||
|
int[] supportedTypes =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext())
|
||||||
|
.getSupportedTypes();
|
||||||
|
|
||||||
|
assertThat(supportedTypes).asList().containsExactly(C.TYPE_OTHER, C.TYPE_HLS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -30,11 +30,11 @@ import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.BaseMediaSource;
|
import com.google.android.exoplayer2.source.BaseMediaSource;
|
||||||
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.CompositeSequenceableLoaderFactory;
|
||||||
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
import com.google.android.exoplayer2.source.DefaultCompositeSequenceableLoaderFactory;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
import com.google.android.exoplayer2.source.MediaPeriod;
|
import com.google.android.exoplayer2.source.MediaPeriod;
|
||||||
import com.google.android.exoplayer2.source.MediaSource;
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
import com.google.android.exoplayer2.source.MediaSourceEventListener.EventDispatcher;
|
||||||
import com.google.android.exoplayer2.source.MediaSourceFactory;
|
|
||||||
import com.google.android.exoplayer2.source.SequenceableLoader;
|
import com.google.android.exoplayer2.source.SequenceableLoader;
|
||||||
import com.google.android.exoplayer2.source.SinglePeriodTimeline;
|
import com.google.android.exoplayer2.source.SinglePeriodTimeline;
|
||||||
import com.google.android.exoplayer2.source.smoothstreaming.manifest.SsManifest;
|
import com.google.android.exoplayer2.source.smoothstreaming.manifest.SsManifest;
|
||||||
|
|
@ -66,7 +66,7 @@ public final class SsMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Factory for {@link SsMediaSource}. */
|
/** Factory for {@link SsMediaSource}. */
|
||||||
public static final class Factory implements MediaSourceFactory {
|
public static final class Factory implements DefaultMediaSourceFactory.Delegate {
|
||||||
|
|
||||||
private final SsChunkSource.Factory chunkSourceFactory;
|
private final SsChunkSource.Factory chunkSourceFactory;
|
||||||
@Nullable private final DataSource.Factory manifestDataSourceFactory;
|
@Nullable private final DataSource.Factory manifestDataSourceFactory;
|
||||||
|
|
@ -111,7 +111,7 @@ public final class SsMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#tag} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setTag(Object)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
|
@ -206,7 +206,7 @@ public final class SsMediaSource extends BaseMediaSource
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @deprecated Use {@link MediaItem.PlaybackProperties#streamKeys} and {@link
|
* @deprecated Use {@link MediaItem.Builder#setStreamKeys(List)} and {@link
|
||||||
* #createMediaSource(MediaItem)} instead.
|
* #createMediaSource(MediaItem)} instead.
|
||||||
*/
|
*/
|
||||||
@SuppressWarnings("deprecation")
|
@SuppressWarnings("deprecation")
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,106 @@
|
||||||
|
/*
|
||||||
|
* Copyright 2020 The Android Open Source Project
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package com.google.android.exoplayer2.source.smoothstreaming;
|
||||||
|
|
||||||
|
import static com.google.common.truth.Truth.assertThat;
|
||||||
|
|
||||||
|
import androidx.test.core.app.ApplicationProvider;
|
||||||
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
|
import com.google.android.exoplayer2.C;
|
||||||
|
import com.google.android.exoplayer2.MediaItem;
|
||||||
|
import com.google.android.exoplayer2.source.DefaultMediaSourceFactory;
|
||||||
|
import com.google.android.exoplayer2.source.MediaSource;
|
||||||
|
import org.junit.Test;
|
||||||
|
import org.junit.runner.RunWith;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Unit test for creating SmoothStreaming media sources with the {@link DefaultMediaSourceFactory}.
|
||||||
|
*/
|
||||||
|
@RunWith(AndroidJUnit4.class)
|
||||||
|
public class DefaultMediaSourceFactoryTest {
|
||||||
|
|
||||||
|
private static final String URI_MEDIA = "http://exoplayer.dev/video";
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withExtension_smoothstreamingSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("ism").build();
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
assertThat(mediaSource).isInstanceOf(SsMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withTag_tagInSource() {
|
||||||
|
Object tag = new Object();
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem =
|
||||||
|
new MediaItem.Builder().setSourceUri(URI_MEDIA).setExtension("ism").setTag(tag).build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource.getTag()).isEqualTo(tag);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withIsmPath_smoothstreamingSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.ism").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(SsMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testCreateMediaSource_withManifestPath_smoothstreamingSource() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + ".ism/Manifest").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource = defaultMediaSourceFactory.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isInstanceOf(SsMediaSource.class);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void createMediaSource_withNull_usesNonNullDefaults() {
|
||||||
|
DefaultMediaSourceFactory defaultMediaSourceFactory =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext());
|
||||||
|
MediaItem mediaItem = new MediaItem.Builder().setSourceUri(URI_MEDIA + "/file.ism").build();
|
||||||
|
|
||||||
|
MediaSource mediaSource =
|
||||||
|
defaultMediaSourceFactory
|
||||||
|
.setDrmSessionManager(null)
|
||||||
|
.setDrmHttpDataSourceFactory(null)
|
||||||
|
.setLoadErrorHandlingPolicy(null)
|
||||||
|
.createMediaSource(mediaItem);
|
||||||
|
|
||||||
|
assertThat(mediaSource).isNotNull();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void getSupportedTypes_smoothstreamingModule_containsTypeSS() {
|
||||||
|
int[] supportedTypes =
|
||||||
|
DefaultMediaSourceFactory.newInstance(ApplicationProvider.getApplicationContext())
|
||||||
|
.getSupportedTypes();
|
||||||
|
|
||||||
|
assertThat(supportedTypes).asList().containsExactly(C.TYPE_OTHER, C.TYPE_SS);
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue