Skip to content

Most visited

Recently visited

navigation

MediaPlayer Enhancements

In Android O, MediaPlayer includes new methods implementing these new features:

Buffering

New MediaPlayer methods can help you tune buffering performance. MediaPlayer uses the new BufferingParams object to specify watermarks and buffering modes.

Three watermarks, initial, low, and high, control MediaPlayer's buffering behavior:

Each watermark can be specified by size (in kilobytes), or time (in milliseconds) or both. The buffering mode indicates which type is used. There are four choices:

Note that time-based buffering is available when a data source contains time-stamped frame information.

You can create BufferingParams from scratch. However, the recommended procedure is to start with the default BufferParams that Android assigns to data sources, as follows:

  1. Set the MediaPlayer's data source.
  2. Call getDefaultBufferingParams() and examine the BufferingParams object that is returned to see the default watermarks and available buffering modes defined for the data source.
  3. Optionally edit the BufferingParams. If you change the buffering mode, be sure to use a mode that the original default value permits. For example, if the default mode was BUFFERING_MODE_TIME_ONLY, your only other option is BUFFERING_MODE_NONE; you can't specify BUFFERING_MODE_SIZE_ONLY.
  4. Call setBufferingParams() to pass buffering settings to the MediaPlayer.
  5. Be sure to test the value that is returned. If any of the params are invalid or not supported, this method throws IllegalArgumentException.

Seek modes

The new method seekTo() includes a second argument that specifies a seekMode:

When seeking continuously, apps should use any of the "SEEK_*_SYNC" modes rather than SEEK_CLOSEST, which runs relatively slower but can be more precise.

DRM support

MediaPlayer includes new APIs that support the playback of DRM-protected material. They are similar to the low-level API provided by MediaDrm, but they operate at a higher level and do not expose the underlying Extractor, Drm, and Crypto objects.

Although the MediaPlayer DRM API does not provide the full functionality of MediaDrm, it supports the most common use cases. The current implementation can handle these content types:

The following code snippet demonstrates how to use the new DRM MediaPlayer methods in a simple synchronous implementation.

To manage DRM-controlled media, you need to include the new methods alongside the usual flow of MediaPlayer calls, as shown below:

setDataSource();
setOnDrmConfigListener(); // optional, for custom configuration
prepare();
if (getDrmInfo() != null) {
  prepareDrm();
  getKeyRequest();
  provideKeyResponse();
}

// MediaPlayer is now ready to use
start();
// ...play/pause/resume...
stop();
releaseDrm();

Start by initializing the MediaPlayer object and setting its source using setDataSource(), as usual. Then, to use DRM, perform these steps:

  1. If you want your app to perform custom configuration, define an MediaPlayer.OnDrmConfigListener and attach it to the player with setOnDrmConfigListener().
  2. Call prepare(), as usual.
  3. Call getDrmInfo(). If the source has DRM content, the method returns a non-null MediaPlayer.DrmInfo.

If MediaPlayer.DrmInfo exists:

  1. Examine the map of available UUIDs and choose one.
  2. Prepare the Drm configuration for the current source by calling prepareDrm().
    • If you created and registered an OnDrmConfigListener, it is called while prepareDrm() is executing. This callback lets you perform custom configuration of the DRM properties before opening the DRM session. The callback is called synchronously in the thread that called prepareDrm(). To access the DRM properties, call getDrmPropertyString() and setDrmPropertyString(). Avoid performing lengthy operations.
    • If the device has not yet been provisioned, prepareDrm() also accesses the provisioning server to provision the device. This can take a variable amount of time, depending on the network connectivity.
  3. To get an opaque key request byte array to send to a license server, call getKeyRequest(). For a full explanation of the method's arguments, see the refdocs. arguments.
  4. To inform the DRM engine about the key response received from the license server, call provideKeyResponse(). The result returned depends on the type of key request:
    • When the response is for an offline key request, a key-set identifier is returned. You can use this key-set identifier together with restoreKeys() to restore the keys to a new session.
    • When the response is for a streaming or release request, null is returned.

Running prepareDrm() asynchronously

By default, prepareDrm() runs synchronously, blocking until preparation is finished. However, the very first DRM preparation on a new device may also require provisioning, which is handled internally by prepareDrm(), and may take some time to finish due to the network operation involved. You can avoid blocking on prepareDrm() by defining and setting a MediaPlayer.OnDrmPreparedListener.

When you set an MediaPlayer.OnDrmPreparedListener, prepareDrm() performs the provisioning (if needed) and preparation in the background. When provisioning and preparation have finished, the listener is called. You should not make any assumption about the calling sequence or the thread in which the listener will run (unless the listener is registered with a handler thread). The listener can be called before or after prepareDrm() returns.

Setting up DRM asynchronously

You can initialize the DRM asynchronously by creating and registering the MediaPlayer.OnDrmInfoListener for DRM preparation and the MediaPlayer.OnDrmPreparedListener to start the player. They work in conjunction with prepareAsync(), as shown below:

setOnPreparedListener();
setOnDrmInfoListener();
setDataSource();
prepareAsync();
// ....

// If the data source content is protected you'll receive the onDrmInfo() callback.
onDrmInfo() {
  prepareDrm();
  getKeyRequest();
  provideKeyResponse();
}

// When prepareAsync() finishes, you'll receive the onPrepared() callback.
// If there is a DRM, onDrmInfo() will set it up before executing this callback, so you can start the player.
onPrepared() {

start();
}
This site uses cookies to store your preferences for site-specific language and display options.

Hooray!

This class requires API level or higher

This doc is hidden because your selected API level for the documentation is . You can change the documentation API level with the selector above the left navigation.

For more information about specifying the API level your app requires, read Supporting Different Platform Versions.

Take a one-minute survey?
Help us improve Android tools and documentation.