Closed bennettpeter closed 2 weeks ago
2. Any video with DVB subtitles
Please can you provide a clip that we can use to reproduce this. Please either upload it here or send it to android-media-github@google.com with the subject Issue #1655
. Please also update this issue to indicate you’ve done this.
It's not true that all DVB subtitles have an issue with 1.4.0, e.g. the media provided in https://github.com/androidx/media/issues/1621 works on phones (and has an issue on TV/STB devices, but not related to 'Legacy decoding is disabled' error)
I have uploaded a short video here: https://drive.google.com/file/d/10-fJIsPH1LawJRdMgLNbkHMf_X9wdowr/view
Are you able to reproduce this issue in the demo app? I built it at 1.4.0 and played the file you provided. When I enable the subtitles I don't see any errors in logcat, and subtitle text appears on screen. It seems everything works.
I will try that. I assume the demo app is not using legacy subtitle support?
The demo app is not using legacy subtitle support.
The clip plays and the subtitles work with the demo application, as you said
I have found the trigger for this exception. In order to cater for possible closed captions, I pass a List of closedCaptionFormats into the DefaultTsPayloadReaderFactory.
List<Format> closedCaptionFormats = new ArrayList<>();
closedCaptionFormats.add(
new Format.Builder()
.setAccessibilityChannel(1)
.setSampleMimeType(MimeTypes.APPLICATION_CEA608)
.build());
closedCaptionFormats.add(
new Format.Builder()
.setAccessibilityChannel(2)
.setSampleMimeType(MimeTypes.APPLICATION_CEA608)
.build());
TsPayloadReader.Factory payloadReaderFactory
= new DefaultTsPayloadReaderFactory(
0,
closedCaptionFormats);
TsExtractor ts = new TsExtractor(
TsExtractor.MODE_SINGLE_PMT,
0,
new DefaultSubtitleParserFactory(),
new TimestampAdjuster(0),
payloadReaderFactory,
Settings.getInt("pref_tweak_ts_search_pkts") * TsExtractor.TS_PACKET_SIZE);
Playing the clip, I see a choice of two Closed Captions and one English subtitle. If I select either of the Closed Caption items, it carries on playing as there are no closed captions in the clip. If I select the English subtitle, there is an Exception.
If I comment the two closedCaptionFormats.add(... statemenets above and play the clip, it shows only one subtitle choice, and selecting it works and I see the subtitles.
My applications always adds two CEA608 formats to TS videos in case they have closed captions. Perhaps there is a better way to do this?
Thanks for the extra info. I tried to reproduce this in the demo app at 1.4.0 by changing the code in PlayerActivity.createMediaSourceFactory
from:
To:
return new DefaultMediaSourceFactory(/* context= */ this,
new DefaultExtractorsFactory()
.setTsSubtitleFormats(
ImmutableList.of(
new Format.Builder()
.setAccessibilityChannel(1)
.setSampleMimeType(MimeTypes.APPLICATION_CEA608)
.build(),
new Format.Builder()
.setAccessibilityChannel(2)
.setSampleMimeType(MimeTypes.APPLICATION_CEA608)
.build())))
.setDataSourceFactory(dataSourceFactory)
.setDrmSessionManagerProvider(drmSessionManagerProvider)
.setLocalAdInsertionComponents(
this::getClientSideAdsLoader, /* adViewProvider= */ playerView)
.setServerSideAdInsertionMediaSourceFactory(imaServerSideAdInsertionMediaSourceFactory);
I saw the two 'Unknown' subtitles appear in the track selector, and the 'English' one. I tried selecting all three, and didn't see any playback failures, and I see subtitles appear for the 'English' (DVB) case.
My code change should be equivalent to yours, so I'm not sure what is causing your different experience.
The only 'unknown' difference I can see is what value you're using for Settings.getInt("pref_tweak_ts_search_pkts")
? The demo app is using the default value of 600
:
https://github.com/androidx/media/blob/b01c6ffcb3fca3d038476dab5d3bc9c9f2010781/libraries/extractor/src/main/java/androidx/media3/extractor/ts/TsExtractor.java#L123
My default value for pref_tweak_ts_search_pkts is 2600.
I tried my program again and it is working correctly.
What happened is, I was using a deprecated constructor for TsExtractor
TsExtractor ts = new TsExtractor(
TsExtractor.MODE_SINGLE_PMT,
new TimestampAdjuster(0),
payloadReaderFactory,
Settings.getInt("pref_tweak_ts_search_pkts") * TsExtractor.TS_PACKET_SIZE);
If you try this version of the constructor (by deleting the 0 and the new DefaultSubtitleParserFactory() parameters), you get the exception.
I must have noticed the deprecated constructor after doing my analysis and fixed it, not re-tested, and not realizing that fixing it was also fixing the problem. I inadvertently fixed the problem myself without realizing it. Sorry for the trouble.
Will you still look into the Error in supportsFormat API or advise on whether I am doing something wrong?
Thanks for the help.
Thanks for the update.
If you try this version of the constructor (by deleting the 0 and the new DefaultSubtitleParserFactory() parameters), you get the exception.
This is somewhat working as intended - as this constructor doesn't do any transcoding of subtitles during extraction, and therefore is relying on leagcy decoding.
Will you still look into the Error in supportsFormat API or advise on whether I am doing something wrong?
I think this is just a misunderstanding/confusing API. In the new way of handling subtitles, SubtitleParser
is invoked during extraction, before the sample queue. It transforms subtitles from (in this case) application/dvbsubs
to an internal representation (CuesWithTiming
), and the extractor then serializes this into the sample queue in the application/x-media3-cues
format using CueEncoder
. Therefore the format of the data written to the sample queue (which is returned by TrackGroup.getFormat(ixTrack)
) is the format after the subtitles have been transcoded (application/x-media3-cues
). It's correct that DefaultSubtitleParserFactory.supportsFormat(..)
returns false
for this MIME type because, this is effectively the output format for SubtitleParser
implementations.
The application/x-media3-cues
data is decoded on the Renderer
side of the sample queue by CueDecoder
.
Thank you for the clarification. Also thank you for the great level of support that you and your team provides.
Version
Media3 1.4.0
More version details
No response
Devices that reproduce the issue
Amazon Fire stick, onn 4K streaming box
Devices that do not reproduce the issue
No response
Reproducible in the demo app?
Not tested
Reproduction steps
Expected result
Actual result
This was working fine in prior versions.
The methods DefaultSubtitleParserFactory.supportsFormat() and SubtitleDecoderFactory.DEFAULT.supportsFormat() are inconsistent with the new methodology of decoding subtitles in the extractor. The Format objects returned by TrackGroup.getFormat(ixTrack) have application/x-media3-cues in the sampleMimeType and the actual subtitle type (e.g. text/x-ssa) in the codecs field. However, the two supportsFormat() methods are still checking the sampleMimeType and returning false for subtitle support when the sampleMimeType is application/x-media3-cues.
My work-around is to check for hardcoded application/x-media3-cues or application/cea-608
My streams are all progressive, based on video files (ts, mkv, mp4, etc) served with http.
I am able to enable subtitles for most types, except for dvbsubs. In the case of dvbsubs, TrackGroup.getFormat(ixTrack) returns a Format object with sampleMimeType of application/dvbsubs and codecs of null. Upon enabling the subtitle, there is an exception java.lang.IllegalStateException: Legacy decoding is disabled, can't handle application/dvbsubs samples (expected application/x-media3-cues).
I attempted to fix this by changing /androidx/media3/extractor/ts/DvbSubtitleReader.java commented out .setSampleMimeType(MimeTypes.APPLICATION_DVBSUBS) replaced with
.setSampleMimeType(MimeTypes.APPLICATION_MEDIA3_CUES) .setCodecs(MimeTypes.APPLICATION_DVBSUBS) This was unsuccessful, java.lang.IllegalStateException: Bundle length is not aligned by 4: 33559567
I prefer not to enable legacy decoding, I can stay on the prior version of exoplayer until it is fixed.
The source code for my application with V1.4.0 is in the media-upgrade branch at https://github.com/bennettpeter/android-MythTV-Leanfront/tree/media-upgrade
I have tried the changes suggested in https://github.com/androidx/media/issues/1644 and others. I originally was using ProgressiveMediaSource.Factory, and I changed to use DefaultMediaSourceFactory as suggested. The subtitles other than dvbsubs were already playing correctly with ProgressiveMediaSource.Factory. The change to DefaultMediaSourceFactory made no difference.
I have tested the following subtitle types:
Text: OK DVB: Fail: java.lang.IllegalStateException: Legacy decoding is disabled, can't handle application/dvbsubs samples (expected application/x-media3-cues). PGS: OK ASS: OK CEA-608: OK: note this works in spite of the fact that in this case sampleMimeType is application/cea-608 and codecs is null
Media
Bug Report
adb bugreport
to android-media-github@google.com after filing this issue.