1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package com.google.android.exoplayer2.metadata; 17 18 import android.os.Parcel; 19 import android.os.Parcelable; 20 import androidx.annotation.Nullable; 21 import com.google.android.exoplayer2.Format; 22 import com.google.android.exoplayer2.util.Util; 23 import java.util.Arrays; 24 import java.util.List; 25 26 /** 27 * A collection of metadata entries. 28 */ 29 public final class Metadata implements Parcelable { 30 31 /** A metadata entry. */ 32 public interface Entry extends Parcelable { 33 34 /** 35 * Returns the {@link Format} that can be used to decode the wrapped metadata in {@link 36 * #getWrappedMetadataBytes()}, or null if this Entry doesn't contain wrapped metadata. 37 */ 38 @Nullable getWrappedMetadataFormat()39 default Format getWrappedMetadataFormat() { 40 return null; 41 } 42 43 /** 44 * Returns the bytes of the wrapped metadata in this Entry, or null if it doesn't contain 45 * wrapped metadata. 46 */ 47 @Nullable getWrappedMetadataBytes()48 default byte[] getWrappedMetadataBytes() { 49 return null; 50 } 51 } 52 53 private final Entry[] entries; 54 55 /** 56 * @param entries The metadata entries. 57 */ Metadata(Entry... entries)58 public Metadata(Entry... entries) { 59 this.entries = entries; 60 } 61 62 /** 63 * @param entries The metadata entries. 64 */ Metadata(List<? extends Entry> entries)65 public Metadata(List<? extends Entry> entries) { 66 this.entries = new Entry[entries.size()]; 67 entries.toArray(this.entries); 68 } 69 Metadata(Parcel in)70 /* package */ Metadata(Parcel in) { 71 entries = new Metadata.Entry[in.readInt()]; 72 for (int i = 0; i < entries.length; i++) { 73 entries[i] = in.readParcelable(Entry.class.getClassLoader()); 74 } 75 } 76 77 /** 78 * Returns the number of metadata entries. 79 */ length()80 public int length() { 81 return entries.length; 82 } 83 84 /** 85 * Returns the entry at the specified index. 86 * 87 * @param index The index of the entry. 88 * @return The entry at the specified index. 89 */ get(int index)90 public Metadata.Entry get(int index) { 91 return entries[index]; 92 } 93 94 /** 95 * Returns a copy of this metadata with the entries of the specified metadata appended. Returns 96 * this instance if {@code other} is null. 97 * 98 * @param other The metadata that holds the entries to append. If null, this methods returns this 99 * instance. 100 * @return The metadata instance with the appended entries. 101 */ copyWithAppendedEntriesFrom(@ullable Metadata other)102 public Metadata copyWithAppendedEntriesFrom(@Nullable Metadata other) { 103 if (other == null) { 104 return this; 105 } 106 return copyWithAppendedEntries(other.entries); 107 } 108 109 /** 110 * Returns a copy of this metadata with the specified entries appended. 111 * 112 * @param entriesToAppend The entries to append. 113 * @return The metadata instance with the appended entries. 114 */ copyWithAppendedEntries(Entry... entriesToAppend)115 public Metadata copyWithAppendedEntries(Entry... entriesToAppend) { 116 if (entriesToAppend.length == 0) { 117 return this; 118 } 119 return new Metadata(Util.nullSafeArrayConcatenation(entries, entriesToAppend)); 120 } 121 122 @Override equals(@ullable Object obj)123 public boolean equals(@Nullable Object obj) { 124 if (this == obj) { 125 return true; 126 } 127 if (obj == null || getClass() != obj.getClass()) { 128 return false; 129 } 130 Metadata other = (Metadata) obj; 131 return Arrays.equals(entries, other.entries); 132 } 133 134 @Override hashCode()135 public int hashCode() { 136 return Arrays.hashCode(entries); 137 } 138 139 @Override toString()140 public String toString() { 141 return "entries=" + Arrays.toString(entries); 142 } 143 144 // Parcelable implementation. 145 146 @Override describeContents()147 public int describeContents() { 148 return 0; 149 } 150 151 @Override writeToParcel(Parcel dest, int flags)152 public void writeToParcel(Parcel dest, int flags) { 153 dest.writeInt(entries.length); 154 for (Entry entry : entries) { 155 dest.writeParcelable(entry, 0); 156 } 157 } 158 159 public static final Parcelable.Creator<Metadata> CREATOR = 160 new Parcelable.Creator<Metadata>() { 161 @Override 162 public Metadata createFromParcel(Parcel in) { 163 return new Metadata(in); 164 } 165 166 @Override 167 public Metadata[] newArray(int size) { 168 return new Metadata[size]; 169 } 170 }; 171 } 172