ExoPlayer as the name suggests is a type of media player built on top of Android’s low level media API’s. It is a better replacement for traditional MediaPlayer that Android framework provides as it has some enhanced features such as Dynamic Adaptive Streaming over HTTP (DASH), HLS adaptive streams etc. It can be used to play audio and video both locally and over the internet.
ExoPlayer is an open source project, can be found on the ExoPlayer project on GitHub.
Advantages over Android’s built in MediaPlayer:
There are a number of advantages of ExoPlayer over Android’s built in MediaPlayer-
1) The problem with traditional Android MediaPlayer was its inability to support DASH(Dynamic Adaptive Streaming over HTTP) and SmoothStreaming which is the reason why ExoPlayer came in existence. It also provides support for HTTP Live Streaming (HLS).
2) ExoPlayer supports a variety of media formats which are MP4, MP3, WebM, M4A, MPEG-TS and AAC.
3) It provides advanced HLS features, such as correct handling of #EXT-X-DISCONTINUITY tags.
4) One more very good feature of ExoPlayer is the ability that we can customize and extend the player as per the requirement allowing many components to be replaced with custom implementations.
5) Updation is not a headache as its a library project included in application apk, you can easily update by managing versions in Build.Gradle file of your project.
Apart from the above advantages there is a disdvantage also-
ExoPlayer’s audio and video components rely on Android’s MediaCodec API, which was made available in Android 4.1(API level 16). So it can’t be used for earlier versions.
Comparison of traditional MediaPlayer and ExoPlayer:
Using traditional MediaPlayer in your code was a lot more easy. You just have to create MediaPlayer instance and call start as below-
MediaPlayer player = MediaPlayer.create(context, uri, display); player.start(); ........ player.release(); // don't forget to do this
So we don’t know what internal functionality is going on in background and we don’t have any control on any of the methods so customization was a tough nut to crack.
Here comes the existence of ExoPlayer. As shown in below figure, It provides control over the methods thus making customization a lot more easier.
Play MP4 Streams using ExoPlayer:
ExoPlayer library has a class named ExoPlayer that takes care of media format, how media data is obtained etc. These fields are provided when we call ExoPlayer’s prepare method.
ExoPlayer provides default audio and video renderers, which make use of the MediaCodec and AudioTrack classes in Android framework. Both require an injected sampleSource object, from which they obtain individual media samples for playback.
Figure shows the high level object model for an ExoPlayer configured to play MP4 streams. As the figure demonstrates that DataSource and Extractor instances are injected into the ExtractorSampleSource to allow it load the media stream and extract samples from the loaded data. An instance of a class called ExtractorSampleSource is injected into the renderers to provide them with media samples. Default audio and video renderers are injected into the ExoPlayer instance.
Hence we can say that there are 3 important interfaces in this model:
A TrackRenderer can be used to play any specific type of media such as video, audio or text. The ExoPlayer library provides MediaCodecVideoTrackRenderer as the default implementation for rendering video, and MediaCodecAudioTrackRenderer for audio. The base for both to decode individual media samples is Android’s MediaCodec class.
The code below shows a glimpse of how to instantiate and use ExoPlayer to play video/audio.
// 1. Instantiate the player. ExoPlayer player = ExoPlayer.Factory.newInstance(RENDERER_COUNT); // 2. Construct renderers. MediaCodecVideoTrackRenderer videoRenderer = ... MediaCodecAudioTrackRenderer audioRenderer = ... // 3. Inject the renderers through prepare. player.prepare(videoRenderer, audioRenderer); // 4. Pass the surface to the video renderer. player.sendMessage(videoRenderer, MediaCodecVideoTrackRenderer.MSG_SET_SURFACE, surface); // 5. Start playback. player.setPlayWhenReady(true); ... player.release(); // Don’t forget to release when done!
A SampleSource object provides format information and media samples to be rendered. SampleSource object is required to be inserted in the TrackRenderer constructors.
There are different types of concrete SampleSource implementations as per the use cases
-> ExtractorSampleSource – For formats such as MP3, M4A, MP4, WebM, MPEG-TS and AAC.
-> ChunkSampleSource – For DASH and SmoothStreaming playbacks.
-> HlsSampleSource – For HLS playbacks.
The SampleSource implementations uses DataSource instances for loading media data. The most commonly used implementations are:
-> DefaultUriDataSource – For playing media that can be either local or loaded over the network.
-> AssetDataSource – For playing media stored in the assets folder of the application’s apk.
So these were the basics covered for ExoPlayer. For DASH and SmoothStreaming using ExoPlayer Stay tuned !!!