/*
* Copyright (C) 2014 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.google.android.exoplayer;
import com.google.android.exoplayer.BufferingPolicy.LoadControl;
import com.google.android.exoplayer.upstream.Allocator;
import com.google.android.exoplayer.upstream.DefaultAllocator;
import com.google.android.exoplayer.upstream.NetworkLock;
import com.google.android.exoplayer.util.Util;
import android.os.Handler;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
/**
* A {@link LoadControl} implementation that allows loads to continue in a sequence that prevents
* any loader from getting too far ahead or behind any of the other loaders.
*
* Loads are scheduled so as to fill the available buffer space as rapidly as possible. Once the
* duration of buffered media and the buffer utilization both exceed respective thresholds, the
* control switches to a draining state during which no loads are permitted to start. During
* draining periods, resources such as the device radio have an opportunity to switch into low
* power modes. The control reverts back to the loading state when either the duration of buffered
* media or the buffer utilization fall below respective thresholds.
*
* This implementation of {@link LoadControl} integrates with {@link NetworkLock}, by registering
* itself as a task with priority {@link NetworkLock#STREAMING_PRIORITY} during loading periods,
* and unregistering itself during draining periods.
*/
public final class DefaultBufferingPolicy implements BufferingPolicy, LoadControl {
/**
* Interface definition for a callback to be notified of {@link DefaultBufferingPolicy} events.
*/
public interface EventListener {
/**
* Invoked when the control transitions from a loading to a draining state, or vice versa.
*
* @param loading Whether the control is now in a loading state.
*/
void onLoadingChanged(boolean loading);
}
/**
* The default minimum duration of media that the player will attempt to ensure is buffered at all
* times, in milliseconds.
*/
public static final int DEFAULT_MIN_BUFFER_MS = 15000;
/**
* The default maximum duration of media that the player will attempt to buffer, in milliseconds.
*/
public static final int DEFAULT_MAX_BUFFER_MS = 30000;
/**
* The default duration of media that must be buffered for playback to start or resume following a
* user action such as a seek, in milliseconds.
*/
public static final int DEFAULT_BUFFER_FOR_PLAYBACK_MS = 2500;
/**
* The default duration of media that must be buffered for playback to resume after a
* player-invoked rebuffer (i.e. a rebuffer that occurs due to buffer depletion rather than a user
* action), in milliseconds.
*/
public static final int DEFAULT_BUFFER_FOR_PLAYBACK_AFTER_REBUFFER_MS = 5000;
private static final int ABOVE_HIGH_WATERMARK = 0;
private static final int BETWEEN_WATERMARKS = 1;
private static final int BELOW_LOW_WATERMARK = 2;
private final DefaultAllocator allocator;
private final List