1

I have integrated Exoplayer to one of my Android App, I can play all type of videos with it but .mkv videos are not playing. I am getting 2 different exceptions for all the URLs I have.

Here is the code snippet I am using:

    private void initializePlayer() {

    TrackSelection.Factory videoTrackSelectionFactory = new AdaptiveTrackSelection.Factory(bandwidthMeter);
    trackSelector = new DefaultTrackSelector(videoTrackSelectionFactory);
    player = ExoPlayerFactory.newSimpleInstance(this, trackSelector);
    mPlayerView.setPlayer(player);

    player.setPlayWhenReady(shouldAutoPlay);
    player.addAnalyticsListener(this);

    MediaSource mediaSource = buildMediaSource(Uri.parse(getIntent().getStringExtra(KEY_URL)));

    boolean haveStartPosition = currentWindow != C.INDEX_UNSET;
    if (haveStartPosition) {
        player.seekTo(currentWindow, playbackPosition);
    }

    player.seekTo(getResumePosition());
    Logger.d(TAG, "mResumePosition >> " + getResumePosition());
    player.prepare(mediaSource, !haveStartPosition, false);
    
}


    private MediaSource buildMediaSource(Uri uri) {

    String userAgent = Util.getUserAgent(this, getString(R.string.app_name));

    if (uri.getLastPathSegment().contains("mp3") || uri.getLastPathSegment().contains("mp4")) {
        return new ExtractorMediaSource.Factory(new DefaultHttpDataSourceFactory(userAgent))
                .createMediaSource(uri);
    } else if (uri.getLastPathSegment().contains("m3u8")) {
        return new HlsMediaSource.Factory(new DefaultHttpDataSourceFactory(userAgent))
                .createMediaSource(uri);
    } else if (uri.getLastPathSegment().contains("mpd")) {
        DashMediaSource mediaSource = new DashMediaSource.Factory(
                new DefaultDashChunkSource.Factory(mediaDataSourceFactory),
                buildDataSourceFactory(true))
                .setManifestParser(
                        new FilteringManifestParser<>(
                                new DashManifestParser(), null))
                .createMediaSource(uri);
        return mediaSource;
    } else {
        DashChunkSource.Factory dashChunkSourceFactory = new DefaultDashChunkSource.Factory(
                new DefaultHttpDataSourceFactory("ua", new DefaultBandwidthMeter()));
        DataSource.Factory manifestDataSourceFactory = new DefaultHttpDataSourceFactory(userAgent);
        return new DashMediaSource.Factory(dashChunkSourceFactory, manifestDataSourceFactory).
                createMediaSource(uri);
    }
}

Video URL: http://tivixtv.net:80/movie/Qquzu5/MBGaYNMY4Q/75988.mkv

Exception I am getting:

2020-08-07 19:17:54.867 5721-6862/com.zeenews.tv E/ExoPlayerImplInternal: Source error
  com.google.android.exoplayer2.ParserException: org.xmlpull.v1.XmlPullParserException: Unexpected token (position:TEXT Eߣ������������#B��...@1:98 in java.io.InputStreamReader@5dd061d) 
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:96)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:61)
    at com.google.android.exoplayer2.upstream.ParsingLoadable.load(ParsingLoadable.java:172)
    at com.google.android.exoplayer2.upstream.Loader$LoadTask.run(Loader.java:415)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
    at java.lang.Thread.run(Thread.java:764)
 Caused by: org.xmlpull.v1.XmlPullParserException: Unexpected token (position:TEXT Eߣ������������#B��...@1:98 in java.io.InputStreamReader@5dd061d) 
    at org.kxml2.io.KXmlParser.next(KXmlParser.java:432)
    at org.kxml2.io.KXmlParser.next(KXmlParser.java:313)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:89)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:61) 
    at com.google.android.exoplayer2.upstream.ParsingLoadable.load(ParsingLoadable.java:172) 
    at com.google.android.exoplayer2.upstream.Loader$LoadTask.run(Loader.java:415) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641) 
    at java.lang.Thread.run(Thread.java:764) 

Video URL : http://tivixtv.net:80/movie/Qquzu5/MBGaYNMY4Q/88512.mkv

Exception I am getting:

2020-08-07 19:51:54.515 7989-8627/com.zeenews.tv E/ExoPlayerImplInternal: Source error
  com.google.android.exoplayer2.ParserException: org.xmlpull.v1.XmlPullParserException: unterminated entity ref (position:TEXT @2:2937 in java.io.InputStreamReader@265ea06) 
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:96)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:61)
    at com.google.android.exoplayer2.upstream.ParsingLoadable.load(ParsingLoadable.java:172)
    at com.google.android.exoplayer2.upstream.Loader$LoadTask.run(Loader.java:415)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
    at java.lang.Thread.run(Thread.java:764)
 Caused by: org.xmlpull.v1.XmlPullParserException: unterminated entity ref (position:TEXT @2:2937 in java.io.InputStreamReader@265ea06) 
    at org.kxml2.io.KXmlParser.readEntity(KXmlParser.java:1220)
    at org.kxml2.io.KXmlParser.readValue(KXmlParser.java:1402)
    at org.kxml2.io.KXmlParser.next(KXmlParser.java:393)
    at org.kxml2.io.KxmlParser.next(KXmlParser.java:313)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:89)
    at com.google.android.exoplayer2.source.dash.manifest.DashManifestParser.parse(DashManifestParser.java:61) 
    at com.google.android.exoplayer2.upstream.ParsingLoadable.load(ParsingLoadable.java:172) 
    at com.google.android.exoplayer2.upstream.Loader$LoadTask.run(Loader.java:415) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641) 
    at java.lang.Thread.run(Thread.java:764) 

Would appreciate if anyone can help me with this.

Shishupal Shakya
  • 1,632
  • 2
  • 18
  • 41

1 Answers1

0

I got this answer from my GitHub post:

https://github.com/google/ExoPlayer/issues/7725

MY code was trying to use DashMediaSource to play a Matroska file, when it should be using a ProgressiveMediaSource (or equivalently, ExtractorMediaSource, although that class is deprecated).

Here is the update buildMediaSource() code to play .mkv file :

    private MediaSource buildMediaSource(Uri uri) {

    String userAgent = Util.getUserAgent(this, getString(R.string.app_name));

    if (uri.getLastPathSegment().contains("mp3") || uri.getLastPathSegment().contains("mp4") || uri.getLastPathSegment().contains("mkv")) {
        return new ExtractorMediaSource.Factory(new DefaultHttpDataSourceFactory(userAgent))
                .createMediaSource(uri);
    } else if (uri.getLastPathSegment().contains("m3u8")) {
        return new HlsMediaSource.Factory(new DefaultHttpDataSourceFactory(userAgent))
                .createMediaSource(uri);
    } else if (uri.getLastPathSegment().contains("mpd")) {
        DashMediaSource mediaSource = new DashMediaSource.Factory(
                new DefaultDashChunkSource.Factory(mediaDataSourceFactory),
                buildDataSourceFactory(true))
                .setManifestParser(
                        new FilteringManifestParser<>(
                                new DashManifestParser(), null))
                .createMediaSource(uri);
        return mediaSource;
    } else {
        DashChunkSource.Factory dashChunkSourceFactory = new DefaultDashChunkSource.Factory(
                new DefaultHttpDataSourceFactory("ua", new DefaultBandwidthMeter()));
        DataSource.Factory manifestDataSourceFactory = new DefaultHttpDataSourceFactory(userAgent);
        return new DashMediaSource.Factory(dashChunkSourceFactory, manifestDataSourceFactory).
                createMediaSource(uri);
    }
}
Shishupal Shakya
  • 1,632
  • 2
  • 18
  • 41
  • I too had same problem https://stackoverflow.com/q/63101825/3836908 but when i tried your code none of the video is playing, Can share your code ? – sanoj lawrence Aug 10 '20 at 15:22
  • @sanojlawrence I have added my code above, let me know what exception you are getting when you try to play .mkv file. If you are trying on an emulator, please try once on a real device as well. Above code is working fine at my end for multiple .mkv files. – Shishupal Shakya Aug 11 '20 at 04:52
  • i tried `public static final String KEY_URL = "http://jell.yfish.us/media/jellyfish-3-mbps-hd-h264.mkv";` and i get `Unable to start activity ComponentInfo{com.example.jlplayer/Activities.VideoPlayerActivity}: java.lang.NullPointerException: uriString` – sanoj lawrence Aug 11 '20 at 08:50
  • @sanojlawrence Null Pointer exception is not related the code I have shared above, you may get it due to other reasons, please check the line of code at which this exception is occuring. – Shishupal Shakya Aug 11 '20 at 12:55