diff --git a/library/common/src/main/java/com/google/android/exoplayer2/MediaMetadata.java b/library/common/src/main/java/com/google/android/exoplayer2/MediaMetadata.java index 0da1c8271c..baf916c3c9 100644 --- a/library/common/src/main/java/com/google/android/exoplayer2/MediaMetadata.java +++ b/library/common/src/main/java/com/google/android/exoplayer2/MediaMetadata.java @@ -18,6 +18,7 @@ package com.google.android.exoplayer2; import android.os.Bundle; import androidx.annotation.IntDef; import androidx.annotation.Nullable; +import com.google.android.exoplayer2.metadata.Metadata; import com.google.android.exoplayer2.util.Util; import java.lang.annotation.Documented; import java.lang.annotation.Retention; @@ -29,20 +30,37 @@ public final class MediaMetadata implements Bundleable { /** A builder for {@link MediaMetadata} instances. */ public static final class Builder { + @Nullable private String title; + public Builder() {} private Builder(MediaMetadata mediaMetadata) { this.title = mediaMetadata.title; } - @Nullable private String title; - /** Sets the optional title. */ public Builder setTitle(@Nullable String title) { this.title = title; return this; } + /** + * Sets all fields supported by the {@link Metadata.Entry entries} within the {@link Metadata}. + * + *
Fields are only set if the {@link Metadata.Entry} has an implementation for {@link + * Metadata.Entry#populateMediaMetadata(Builder)}. + * + *
In the event that multiple {@link Metadata.Entry} objects within the {@link Metadata}
+ * relate to the same {@link MediaMetadata} field, then the last one will be used.
+ */
+ public Builder populateFromMetadata(Metadata metadata) {
+ for (int i = 0; i < metadata.length(); i++) {
+ Metadata.Entry entry = metadata.get(i);
+ entry.populateMediaMetadata(this);
+ }
+ return this;
+ }
+
/** Returns a new {@link MediaMetadata} instance with the current builder values. */
public MediaMetadata build() {
return new MediaMetadata(/* builder= */ this);
diff --git a/library/common/src/main/java/com/google/android/exoplayer2/Player.java b/library/common/src/main/java/com/google/android/exoplayer2/Player.java
index 66121aa6ee..1813963453 100644
--- a/library/common/src/main/java/com/google/android/exoplayer2/Player.java
+++ b/library/common/src/main/java/com/google/android/exoplayer2/Player.java
@@ -150,6 +150,17 @@ public interface Player {
*/
default void onStaticMetadataChanged(List The provided {@link MediaMetadata} is a combination of the {@link MediaItem#mediaMetadata}
+ * and the static and dynamic metadata sourced from {@link
+ * EventListener#onStaticMetadataChanged(List)} and {@link MetadataOutput#onMetadata(Metadata)}.
+ *
+ * @param mediaMetadata The combined {@link MediaMetadata}.
+ */
+ default void onMediaMetadataChanged(MediaMetadata mediaMetadata) {}
+
/**
* Called when the player starts or stops loading the source.
*
diff --git a/library/common/src/main/java/com/google/android/exoplayer2/metadata/Metadata.java b/library/common/src/main/java/com/google/android/exoplayer2/metadata/Metadata.java
index 0c038b2a72..01ae340609 100644
--- a/library/common/src/main/java/com/google/android/exoplayer2/metadata/Metadata.java
+++ b/library/common/src/main/java/com/google/android/exoplayer2/metadata/Metadata.java
@@ -51,6 +51,10 @@ public final class Metadata implements Parcelable {
/**
* Updates the {@link MediaMetadata.Builder} with the type specific values stored in this Entry.
*
+ * The order of the {@link Entry} objects in the {@link Metadata} matters. If two {@link
+ * Entry} entries attempt to populate the same {@link MediaMetadata} field, then the last one in
+ * the list is used.
+ *
* @param builder The builder to be updated.
*/
default void populateMediaMetadata(MediaMetadata.Builder builder) {}
diff --git a/library/core/src/main/java/com/google/android/exoplayer2/SimpleExoPlayer.java b/library/core/src/main/java/com/google/android/exoplayer2/SimpleExoPlayer.java
index 60a29f678c..6e1b434f52 100644
--- a/library/core/src/main/java/com/google/android/exoplayer2/SimpleExoPlayer.java
+++ b/library/core/src/main/java/com/google/android/exoplayer2/SimpleExoPlayer.java
@@ -2067,6 +2067,14 @@ public class SimpleExoPlayer extends BasePlayer
return keepSessionIdAudioTrack.getAudioSessionId();
}
+ private void setMediaMetadata(MediaMetadata mediaMetadata) {
+ if (this.currentMediaMetadata.equals(mediaMetadata)) {
+ return;
+ }
+ this.currentMediaMetadata = mediaMetadata;
+ componentListener.onMediaMetadataChanged(this.currentMediaMetadata);
+ }
+
private static DeviceInfo createDeviceInfo(StreamVolumeManager streamVolumeManager) {
return new DeviceInfo(
DeviceInfo.PLAYBACK_TYPE_LOCAL,
@@ -2242,6 +2250,7 @@ public class SimpleExoPlayer extends BasePlayer
@Override
public void onMetadata(Metadata metadata) {
analyticsCollector.onMetadata(metadata);
+ setMediaMetadata(getMediaMetadata().buildUpon().populateFromMetadata(metadata).build());
for (MetadataOutput metadataOutput : metadataOutputs) {
metadataOutput.onMetadata(metadata);
}
@@ -2371,6 +2380,16 @@ public class SimpleExoPlayer extends BasePlayer
currentMediaMetadata = mediaItem == null ? MediaMetadata.EMPTY : mediaItem.mediaMetadata;
}
+ @Override
+ public void onStaticMetadataChanged(List