diff --git a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/PlayerTestRule.java b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/PlayerTestRule.java index 4838319f48..345985f862 100644 --- a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/PlayerTestRule.java +++ b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/PlayerTestRule.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import android.content.Context; diff --git a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilderTest.java b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilderTest.java index df15d706f6..f7098941fb 100644 --- a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilderTest.java +++ b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilderTest.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import static com.google.android.exoplayer2.ext.media2.TestUtils.assertPlayerResultSuccess; diff --git a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnectorTest.java b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnectorTest.java index 766c584ad3..f9f65c8701 100644 --- a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnectorTest.java +++ b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnectorTest.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import static androidx.media2.common.SessionPlayer.PLAYER_STATE_PAUSED; diff --git a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/TestUtils.java b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/TestUtils.java index 5a8e87de22..a7eb058ee6 100644 --- a/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/TestUtils.java +++ b/extensions/media2/src/androidTest/java/com/google/android/exoplayer2/ext/media2/TestUtils.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import static androidx.media2.common.SessionPlayer.PlayerResult.RESULT_SUCCESS; diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/DefaultMediaItemConverter.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/DefaultMediaItemConverter.java index f405d650e6..c23bdd5669 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/DefaultMediaItemConverter.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/DefaultMediaItemConverter.java @@ -13,20 +13,29 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; +import static androidx.media2.common.MediaMetadata.METADATA_KEY_DISPLAY_TITLE; +import static androidx.media2.common.MediaMetadata.METADATA_KEY_MEDIA_ID; +import static androidx.media2.common.MediaMetadata.METADATA_KEY_MEDIA_URI; +import static androidx.media2.common.MediaMetadata.METADATA_KEY_TITLE; + import android.net.Uri; import androidx.annotation.Nullable; import androidx.media2.common.CallbackMediaItem; import androidx.media2.common.FileMediaItem; -import androidx.media2.common.MediaMetadata; import androidx.media2.common.UriMediaItem; +import com.google.android.exoplayer2.C; import com.google.android.exoplayer2.MediaItem; import com.google.android.exoplayer2.util.Assertions; -/** Default implementation of {@link MediaItemConverter}. */ -public final class DefaultMediaItemConverter implements MediaItemConverter { +/** + * Default implementation of {@link MediaItemConverter}. + * + *

Note that {@link #getMetadata} can be overridden to fill in additional metadata when + * converting {@link MediaItem ExoPlayer MediaItems} to their AndroidX equivalents. + */ +public class DefaultMediaItemConverter implements MediaItemConverter { @Override public MediaItem convertToExoPlayerMediaItem(androidx.media2.common.MediaItem media2MediaItem) { @@ -36,44 +45,52 @@ public final class DefaultMediaItemConverter implements MediaItemConverter { if (media2MediaItem instanceof CallbackMediaItem) { throw new IllegalStateException("CallbackMediaItem isn't supported"); } - - MediaItem.Builder exoPlayerMediaItemBuilder = new MediaItem.Builder(); - - // Set mediaItem as tag for creating MediaSource via MediaSourceFactory methods. - exoPlayerMediaItemBuilder.setTag(media2MediaItem); - - // Media ID or URI must be present. Get it from media2 MediaItem if possible. + @Nullable Uri uri = null; @Nullable String mediaId = null; + @Nullable String title = null; if (media2MediaItem instanceof UriMediaItem) { UriMediaItem uriMediaItem = (UriMediaItem) media2MediaItem; uri = uriMediaItem.getUri(); } - @Nullable MediaMetadata metadata = media2MediaItem.getMetadata(); + @Nullable androidx.media2.common.MediaMetadata metadata = media2MediaItem.getMetadata(); if (metadata != null) { - mediaId = metadata.getString(MediaMetadata.METADATA_KEY_MEDIA_ID); - @Nullable String uriString = metadata.getString(MediaMetadata.METADATA_KEY_MEDIA_URI); - if (uri == null && uriString != null) { - uri = Uri.parse(uriString); + @Nullable String uriString = metadata.getString(METADATA_KEY_MEDIA_URI); + mediaId = metadata.getString(METADATA_KEY_MEDIA_ID); + if (uri == null) { + if (uriString != null) { + uri = Uri.parse(uriString); + } else if (mediaId != null) { + uri = Uri.parse("media2:///" + mediaId); + } + } + title = metadata.getString(METADATA_KEY_DISPLAY_TITLE); + if (title == null) { + title = metadata.getString(METADATA_KEY_TITLE); } } if (uri == null) { - // Generate a Uri to make it non-null. If not, tag will be ignored. - uri = Uri.parse("exoplayer://" + media2MediaItem.hashCode()); + // Generate a URI to make it non-null. If not, then the tag passed to setTag will be ignored. + uri = Uri.parse("media2:///"); } - exoPlayerMediaItemBuilder.setUri(uri); - exoPlayerMediaItemBuilder.setMediaId(mediaId); - - if (media2MediaItem.getStartPosition() != androidx.media2.common.MediaItem.POSITION_UNKNOWN) { - exoPlayerMediaItemBuilder.setClipStartPositionMs(media2MediaItem.getStartPosition()); - exoPlayerMediaItemBuilder.setClipRelativeToDefaultPosition(true); + long startPositionMs = media2MediaItem.getStartPosition(); + if (startPositionMs == androidx.media2.common.MediaItem.POSITION_UNKNOWN) { + startPositionMs = 0; } - if (media2MediaItem.getEndPosition() != androidx.media2.common.MediaItem.POSITION_UNKNOWN) { - exoPlayerMediaItemBuilder.setClipEndPositionMs(media2MediaItem.getEndPosition()); - exoPlayerMediaItemBuilder.setClipRelativeToDefaultPosition(true); + long endPositionMs = media2MediaItem.getEndPosition(); + if (endPositionMs == androidx.media2.common.MediaItem.POSITION_UNKNOWN) { + endPositionMs = C.TIME_END_OF_SOURCE; } - return exoPlayerMediaItemBuilder.build(); + return new MediaItem.Builder() + .setUri(uri) + .setMediaId(mediaId) + .setMediaMetadata( + new com.google.android.exoplayer2.MediaMetadata.Builder().setTitle(title).build()) + .setTag(media2MediaItem) + .setClipStartPositionMs(startPositionMs) + .setClipEndPositionMs(endPositionMs) + .build(); } @Override @@ -81,11 +98,40 @@ public final class DefaultMediaItemConverter implements MediaItemConverter { Assertions.checkNotNull(exoPlayerMediaItem); MediaItem.PlaybackProperties playbackProperties = Assertions.checkNotNull(exoPlayerMediaItem.playbackProperties); + @Nullable Object tag = playbackProperties.tag; if (tag instanceof androidx.media2.common.MediaItem) { return (androidx.media2.common.MediaItem) tag; } - return new UriMediaItem.Builder(playbackProperties.uri).build(); + androidx.media2.common.MediaMetadata metadata = getMetadata(exoPlayerMediaItem); + long startPositionMs = exoPlayerMediaItem.clippingProperties.startPositionMs; + long endPositionMs = exoPlayerMediaItem.clippingProperties.endPositionMs; + if (endPositionMs == C.TIME_END_OF_SOURCE) { + endPositionMs = androidx.media2.common.MediaItem.POSITION_UNKNOWN; + } + + return new androidx.media2.common.MediaItem.Builder() + .setMetadata(metadata) + .setStartPosition(startPositionMs) + .setEndPosition(endPositionMs) + .build(); + } + + /** + * Returns a {@link androidx.media2.common.MediaMetadata} corresponding to the given {@link + * MediaItem ExoPlayer MediaItem}. + */ + protected androidx.media2.common.MediaMetadata getMetadata(MediaItem exoPlayerMediaItem) { + @Nullable String title = exoPlayerMediaItem.mediaMetadata.title; + + androidx.media2.common.MediaMetadata.Builder metadataBuilder = + new androidx.media2.common.MediaMetadata.Builder() + .putString(METADATA_KEY_MEDIA_ID, exoPlayerMediaItem.mediaId); + if (title != null) { + metadataBuilder.putString(METADATA_KEY_TITLE, title); + metadataBuilder.putString(METADATA_KEY_DISPLAY_TITLE, title); + } + return metadataBuilder.build(); } } diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/MediaItemConverter.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/MediaItemConverter.java index bfa635699e..218c2a737e 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/MediaItemConverter.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/MediaItemConverter.java @@ -13,24 +13,23 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import com.google.android.exoplayer2.MediaItem; /** - * Converter between {@link MediaItem Media2 MediaItem} and {@link - * com.google.android.exoplayer2.MediaItem ExoPlayer MediaItem}. + * Converts between {@link androidx.media2.common.MediaItem Media2 MediaItem} and {@link MediaItem + * ExoPlayer MediaItem}. */ public interface MediaItemConverter { /** - * Converts {@link androidx.media2.common.MediaItem Media2 MediaItem} to {@link MediaItem + * Converts an {@link androidx.media2.common.MediaItem Media2 MediaItem} to an {@link MediaItem * ExoPlayer MediaItem}. */ MediaItem convertToExoPlayerMediaItem(androidx.media2.common.MediaItem media2MediaItem); /** - * Converts {@link MediaItem ExoPlayer MediaItem} to {@link androidx.media2.common.MediaItem + * Converts an {@link MediaItem ExoPlayer MediaItem} to an {@link androidx.media2.common.MediaItem * Media2 MediaItem}. */ androidx.media2.common.MediaItem convertToMedia2MediaItem(MediaItem exoPlayerMediaItem); diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/PlayerWrapper.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/PlayerWrapper.java index fd5163b76e..f6cdb1e243 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/PlayerWrapper.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/PlayerWrapper.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import androidx.annotation.IntRange; diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallback.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallback.java index 986478f1a9..1f60db947e 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallback.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallback.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import static java.util.concurrent.TimeUnit.MILLISECONDS; diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilder.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilder.java index e334dbd0ad..746aad92e9 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilder.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionCallbackBuilder.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import android.Manifest; @@ -45,7 +44,7 @@ import java.util.ArrayList; import java.util.List; /** - * Builds {@link MediaSession.SessionCallback} with various collaborators. + * Builds a {@link MediaSession.SessionCallback} with various collaborators. * * @see MediaSession.SessionCallback */ diff --git a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnector.java b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnector.java index 3e19c99946..ae85dc4511 100644 --- a/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnector.java +++ b/extensions/media2/src/main/java/com/google/android/exoplayer2/ext/media2/SessionPlayerConnector.java @@ -13,7 +13,6 @@ * See the License for the specific language governing permissions and * limitations under the License. */ - package com.google.android.exoplayer2.ext.media2; import androidx.annotation.FloatRange;