use of com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper in project ExoPlayer by google.
the class DashUtil method newWrappedExtractor.
private static ChunkExtractorWrapper newWrappedExtractor(Format format) {
String mimeType = format.containerMimeType;
boolean isWebm = mimeType.startsWith(MimeTypes.VIDEO_WEBM) || mimeType.startsWith(MimeTypes.AUDIO_WEBM);
Extractor extractor = isWebm ? new MatroskaExtractor() : new FragmentedMp4Extractor();
return new ChunkExtractorWrapper(extractor, format);
}
use of com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper in project ExoPlayer by google.
the class DashUtil method loadInitializationData.
/**
* Loads initialization data for the {@code representation} and optionally index data then
* returns a {@link ChunkExtractorWrapper} which contains the output.
*
* @param dataSource The source from which the data should be loaded.
* @param representation The representation which initialization chunk belongs to.
* @param loadIndex Whether to load index data too.
* @return A {@link ChunkExtractorWrapper} for the {@code representation}, or null if no
* initialization or (if requested) index data exists.
* @throws IOException Thrown when there is an error while loading.
* @throws InterruptedException Thrown if the thread was interrupted.
*/
private static ChunkExtractorWrapper loadInitializationData(DataSource dataSource, Representation representation, boolean loadIndex) throws IOException, InterruptedException {
RangedUri initializationUri = representation.getInitializationUri();
if (initializationUri == null) {
return null;
}
ChunkExtractorWrapper extractorWrapper = newWrappedExtractor(representation.format);
RangedUri requestUri;
if (loadIndex) {
RangedUri indexUri = representation.getIndexUri();
if (indexUri == null) {
return null;
}
// It's common for initialization and index data to be stored adjacently. Attempt to merge
// the two requests together to request both at once.
requestUri = initializationUri.attemptMerge(indexUri, representation.baseUrl);
if (requestUri == null) {
loadInitializationData(dataSource, representation, extractorWrapper, initializationUri);
requestUri = indexUri;
}
} else {
requestUri = initializationUri;
}
loadInitializationData(dataSource, representation, extractorWrapper, requestUri);
return extractorWrapper;
}
use of com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper in project ExoPlayer by google.
the class DashUtil method loadInitializationData.
private static void loadInitializationData(DataSource dataSource, Representation representation, ChunkExtractorWrapper extractorWrapper, RangedUri requestUri) throws IOException, InterruptedException {
DataSpec dataSpec = new DataSpec(requestUri.resolveUri(representation.baseUrl), requestUri.start, requestUri.length, representation.getCacheKey());
InitializationChunk initializationChunk = new InitializationChunk(dataSource, dataSpec, representation.format, C.SELECTION_REASON_UNKNOWN, null, /* trackSelectionData */
extractorWrapper);
initializationChunk.load();
}
use of com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper in project ExoPlayer by google.
the class DefaultSsChunkSource method getNextChunk.
@Override
public final void getNextChunk(MediaChunk previous, long playbackPositionUs, ChunkHolder out) {
if (fatalError != null) {
return;
}
long bufferedDurationUs = previous != null ? (previous.endTimeUs - playbackPositionUs) : 0;
trackSelection.updateSelectedTrack(bufferedDurationUs);
StreamElement streamElement = manifest.streamElements[elementIndex];
if (streamElement.chunkCount == 0) {
// There aren't any chunks for us to load.
out.endOfStream = !manifest.isLive;
return;
}
int chunkIndex;
if (previous == null) {
chunkIndex = streamElement.getChunkIndex(playbackPositionUs);
} else {
chunkIndex = previous.getNextChunkIndex() - currentManifestChunkOffset;
if (chunkIndex < 0) {
// This is before the first chunk in the current manifest.
fatalError = new BehindLiveWindowException();
return;
}
}
if (chunkIndex >= streamElement.chunkCount) {
// This is beyond the last chunk in the current manifest.
out.endOfStream = !manifest.isLive;
return;
}
long chunkStartTimeUs = streamElement.getStartTimeUs(chunkIndex);
long chunkEndTimeUs = chunkStartTimeUs + streamElement.getChunkDurationUs(chunkIndex);
int currentAbsoluteChunkIndex = chunkIndex + currentManifestChunkOffset;
int trackSelectionIndex = trackSelection.getSelectedIndex();
ChunkExtractorWrapper extractorWrapper = extractorWrappers[trackSelectionIndex];
int manifestTrackIndex = trackSelection.getIndexInTrackGroup(trackSelectionIndex);
Uri uri = streamElement.buildRequestUri(manifestTrackIndex, chunkIndex);
out.chunk = newMediaChunk(trackSelection.getSelectedFormat(), dataSource, uri, null, currentAbsoluteChunkIndex, chunkStartTimeUs, chunkEndTimeUs, trackSelection.getSelectionReason(), trackSelection.getSelectionData(), extractorWrapper);
}
use of com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper in project ExoPlayer by google.
the class DefaultSsChunkSource method newMediaChunk.
// Private methods.
private static MediaChunk newMediaChunk(Format format, DataSource dataSource, Uri uri, String cacheKey, int chunkIndex, long chunkStartTimeUs, long chunkEndTimeUs, int trackSelectionReason, Object trackSelectionData, ChunkExtractorWrapper extractorWrapper) {
DataSpec dataSpec = new DataSpec(uri, 0, C.LENGTH_UNSET, cacheKey);
// In SmoothStreaming each chunk contains sample timestamps relative to the start of the chunk.
// To convert them the absolute timestamps, we need to set sampleOffsetUs to chunkStartTimeUs.
long sampleOffsetUs = chunkStartTimeUs;
return new ContainerMediaChunk(dataSource, dataSpec, format, trackSelectionReason, trackSelectionData, chunkStartTimeUs, chunkEndTimeUs, chunkIndex, 1, sampleOffsetUs, extractorWrapper);
}
Aggregations