Search in sources :

Example 11 with Chunk

use of com.google.android.exoplayer2.source.chunk.Chunk in project ExoPlayer by google.

the class DefaultDashChunkSource method newMediaChunk.

private static Chunk newMediaChunk(RepresentationHolder representationHolder, DataSource dataSource, Format trackFormat, int trackSelectionReason, Object trackSelectionData, int firstSegmentNum, int maxSegmentCount) {
    Representation representation = representationHolder.representation;
    long startTimeUs = representationHolder.getSegmentStartTimeUs(firstSegmentNum);
    RangedUri segmentUri = representationHolder.getSegmentUrl(firstSegmentNum);
    String baseUrl = representation.baseUrl;
    if (representationHolder.extractorWrapper == null) {
        long endTimeUs = representationHolder.getSegmentEndTimeUs(firstSegmentNum);
        DataSpec dataSpec = new DataSpec(segmentUri.resolveUri(baseUrl), segmentUri.start, segmentUri.length, representation.getCacheKey());
        return new SingleSampleMediaChunk(dataSource, dataSpec, trackFormat, trackSelectionReason, trackSelectionData, startTimeUs, endTimeUs, firstSegmentNum, representationHolder.trackType, trackFormat);
    } else {
        int segmentCount = 1;
        for (int i = 1; i < maxSegmentCount; i++) {
            RangedUri nextSegmentUri = representationHolder.getSegmentUrl(firstSegmentNum + i);
            RangedUri mergedSegmentUri = segmentUri.attemptMerge(nextSegmentUri, baseUrl);
            if (mergedSegmentUri == null) {
                // Unable to merge segment fetches because the URIs do not merge.
                break;
            }
            segmentUri = mergedSegmentUri;
            segmentCount++;
        }
        long endTimeUs = representationHolder.getSegmentEndTimeUs(firstSegmentNum + segmentCount - 1);
        DataSpec dataSpec = new DataSpec(segmentUri.resolveUri(baseUrl), segmentUri.start, segmentUri.length, representation.getCacheKey());
        long sampleOffsetUs = -representation.presentationTimeOffsetUs;
        return new ContainerMediaChunk(dataSource, dataSpec, trackFormat, trackSelectionReason, trackSelectionData, startTimeUs, endTimeUs, firstSegmentNum, segmentCount, sampleOffsetUs, representationHolder.extractorWrapper);
    }
}
Also used : SingleSampleMediaChunk(com.google.android.exoplayer2.source.chunk.SingleSampleMediaChunk) RangedUri(com.google.android.exoplayer2.source.dash.manifest.RangedUri) DataSpec(com.google.android.exoplayer2.upstream.DataSpec) Representation(com.google.android.exoplayer2.source.dash.manifest.Representation) ContainerMediaChunk(com.google.android.exoplayer2.source.chunk.ContainerMediaChunk)

Example 12 with Chunk

use of com.google.android.exoplayer2.source.chunk.Chunk in project ExoPlayer by google.

the class ChunkSampleStream method onLoadCanceled.

@Override
public void onLoadCanceled(Chunk loadable, long elapsedRealtimeMs, long loadDurationMs, boolean released) {
    eventDispatcher.loadCanceled(loadable.dataSpec, loadable.type, primaryTrackType, loadable.trackFormat, loadable.trackSelectionReason, loadable.trackSelectionData, loadable.startTimeUs, loadable.endTimeUs, elapsedRealtimeMs, loadDurationMs, loadable.bytesLoaded());
    if (!released) {
        primarySampleQueue.reset(true);
        for (DefaultTrackOutput embeddedSampleQueue : embeddedSampleQueues) {
            embeddedSampleQueue.reset(true);
        }
        callback.onContinueLoadingRequested(this);
    }
}
Also used : DefaultTrackOutput(com.google.android.exoplayer2.extractor.DefaultTrackOutput)

Example 13 with Chunk

use of com.google.android.exoplayer2.source.chunk.Chunk in project ExoPlayer by google.

the class AdaptiveTrackSelection method evaluateQueueSize.

@Override
public int evaluateQueueSize(long playbackPositionUs, List<? extends MediaChunk> queue) {
    if (queue.isEmpty()) {
        return 0;
    }
    int queueSize = queue.size();
    long bufferedDurationUs = queue.get(queueSize - 1).endTimeUs - playbackPositionUs;
    if (bufferedDurationUs < minDurationToRetainAfterDiscardUs) {
        return queueSize;
    }
    int idealSelectedIndex = determineIdealSelectedIndex(SystemClock.elapsedRealtime());
    Format idealFormat = getFormat(idealSelectedIndex);
    // track.
    for (int i = 0; i < queueSize; i++) {
        MediaChunk chunk = queue.get(i);
        Format format = chunk.trackFormat;
        long durationBeforeThisChunkUs = chunk.startTimeUs - playbackPositionUs;
        if (durationBeforeThisChunkUs >= minDurationToRetainAfterDiscardUs && format.bitrate < idealFormat.bitrate && format.height != Format.NO_VALUE && format.height < 720 && format.width != Format.NO_VALUE && format.width < 1280 && format.height < idealFormat.height) {
            return i;
        }
    }
    return queueSize;
}
Also used : Format(com.google.android.exoplayer2.Format) MediaChunk(com.google.android.exoplayer2.source.chunk.MediaChunk)

Example 14 with Chunk

use of com.google.android.exoplayer2.source.chunk.Chunk in project ExoPlayer by google.

the class WavHeaderReader method skipToData.

/**
   * Skips to the data in the given WAV input stream and returns its data size. After calling, the
   * input stream's position will point to the start of sample data in the WAV.
   * <p>
   * If an exception is thrown, the input position will be left pointing to a chunk header.
   *
   * @param input Input stream to skip to the data chunk in. Its peek position must be pointing to
   *     a valid chunk header.
   * @param wavHeader WAV header to populate with data bounds.
   * @throws ParserException If an error occurs parsing chunks.
   * @throws IOException If reading from the input fails.
   * @throws InterruptedException If interrupted while reading from input.
   */
public static void skipToData(ExtractorInput input, WavHeader wavHeader) throws IOException, InterruptedException {
    Assertions.checkNotNull(input);
    Assertions.checkNotNull(wavHeader);
    // Make sure the peek position is set to the read position before we peek the first header.
    input.resetPeekPosition();
    ParsableByteArray scratch = new ParsableByteArray(ChunkHeader.SIZE_IN_BYTES);
    // Skip all chunks until we hit the data header.
    ChunkHeader chunkHeader = ChunkHeader.peek(input, scratch);
    while (chunkHeader.id != Util.getIntegerCodeForString("data")) {
        Log.w(TAG, "Ignoring unknown WAV chunk: " + chunkHeader.id);
        long bytesToSkip = ChunkHeader.SIZE_IN_BYTES + chunkHeader.size;
        // Override size of RIFF chunk, since it describes its size as the entire file.
        if (chunkHeader.id == Util.getIntegerCodeForString("RIFF")) {
            bytesToSkip = ChunkHeader.SIZE_IN_BYTES + 4;
        }
        if (bytesToSkip > Integer.MAX_VALUE) {
            throw new ParserException("Chunk is too large (~2GB+) to skip; id: " + chunkHeader.id);
        }
        input.skipFully((int) bytesToSkip);
        chunkHeader = ChunkHeader.peek(input, scratch);
    }
    // Skip past the "data" header.
    input.skipFully(ChunkHeader.SIZE_IN_BYTES);
    wavHeader.setDataBounds(input.getPosition(), chunkHeader.size);
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray) ParserException(com.google.android.exoplayer2.ParserException)

Example 15 with Chunk

use of com.google.android.exoplayer2.source.chunk.Chunk in project ExoPlayer by google.

the class HlsSampleStreamWrapper method selectTracks.

public boolean selectTracks(TrackSelection[] selections, boolean[] mayRetainStreamFlags, SampleStream[] streams, boolean[] streamResetFlags, boolean isFirstTrackSelection) {
    Assertions.checkState(prepared);
    // Disable old tracks.
    for (int i = 0; i < selections.length; i++) {
        if (streams[i] != null && (selections[i] == null || !mayRetainStreamFlags[i])) {
            int group = ((HlsSampleStream) streams[i]).group;
            setTrackGroupEnabledState(group, false);
            sampleQueues.valueAt(group).disable();
            streams[i] = null;
        }
    }
    // Enable new tracks.
    TrackSelection primaryTrackSelection = null;
    boolean selectedNewTracks = false;
    for (int i = 0; i < selections.length; i++) {
        if (streams[i] == null && selections[i] != null) {
            TrackSelection selection = selections[i];
            int group = trackGroups.indexOf(selection.getTrackGroup());
            setTrackGroupEnabledState(group, true);
            if (group == primaryTrackGroupIndex) {
                primaryTrackSelection = selection;
                chunkSource.selectTracks(selection);
            }
            streams[i] = new HlsSampleStream(this, group);
            streamResetFlags[i] = true;
            selectedNewTracks = true;
        }
    }
    if (isFirstTrackSelection) {
        // At the time of the first track selection all queues will be enabled, so we need to disable
        // any that are no longer required.
        int sampleQueueCount = sampleQueues.size();
        for (int i = 0; i < sampleQueueCount; i++) {
            if (!groupEnabledStates[i]) {
                sampleQueues.valueAt(i).disable();
            }
        }
        if (primaryTrackSelection != null && !mediaChunks.isEmpty()) {
            primaryTrackSelection.updateSelectedTrack(0);
            int chunkIndex = chunkSource.getTrackGroup().indexOf(mediaChunks.getLast().trackFormat);
            if (primaryTrackSelection.getSelectedIndexInTrackGroup() != chunkIndex) {
                // The loaded preparation chunk does match the selection. We discard it.
                seekTo(lastSeekPositionUs);
            }
        }
    }
    // Cancel requests if necessary.
    if (enabledTrackCount == 0) {
        chunkSource.reset();
        downstreamTrackFormat = null;
        mediaChunks.clear();
        if (loader.isLoading()) {
            loader.cancelLoading();
        }
    }
    return selectedNewTracks;
}
Also used : TrackSelection(com.google.android.exoplayer2.trackselection.TrackSelection)

Aggregations

DataSpec (com.google.android.exoplayer2.upstream.DataSpec)5 RangedUri (com.google.android.exoplayer2.source.dash.manifest.RangedUri)4 ParserException (com.google.android.exoplayer2.ParserException)3 BehindLiveWindowException (com.google.android.exoplayer2.source.BehindLiveWindowException)3 ParsableByteArray (com.google.android.exoplayer2.util.ParsableByteArray)3 Uri (android.net.Uri)2 Format (com.google.android.exoplayer2.Format)2 ChunkExtractorWrapper (com.google.android.exoplayer2.source.chunk.ChunkExtractorWrapper)2 ContainerMediaChunk (com.google.android.exoplayer2.source.chunk.ContainerMediaChunk)2 InitializationChunk (com.google.android.exoplayer2.source.chunk.InitializationChunk)2 Representation (com.google.android.exoplayer2.source.dash.manifest.Representation)2 HlsUrl (com.google.android.exoplayer2.source.hls.playlist.HlsMasterPlaylist.HlsUrl)2 TimestampAdjuster (com.google.android.exoplayer2.util.TimestampAdjuster)2 ChunkIndex (com.google.android.exoplayer2.extractor.ChunkIndex)1 DefaultExtractorInput (com.google.android.exoplayer2.extractor.DefaultExtractorInput)1 DefaultTrackOutput (com.google.android.exoplayer2.extractor.DefaultTrackOutput)1 Extractor (com.google.android.exoplayer2.extractor.Extractor)1 ExtractorInput (com.google.android.exoplayer2.extractor.ExtractorInput)1 SeekMap (com.google.android.exoplayer2.extractor.SeekMap)1 Mp3Extractor (com.google.android.exoplayer2.extractor.mp3.Mp3Extractor)1