Merge pull request #942 from datdoantelus:CC_708_parser_fix
PiperOrigin-RevId: 596836615
This commit is contained in:
commit
6f8249184b
@ -93,6 +93,10 @@
|
||||
that contained Binder objects` error when using
|
||||
`DefaultExtractorsFactory.setTextTrackTranscodingEnabled`
|
||||
([#836](https://github.com/androidx/media/issues/836)).
|
||||
* CEA-708: Ignore `rowLock` value. The CEA-708-E S-2023 spec states that
|
||||
`rowLock` and `columnLock` should both be assumed to be true, regardless
|
||||
of the values present in the stream (`columnLock` support is not
|
||||
implemented, so it's effectively assumed to always be false).
|
||||
* Metadata:
|
||||
* Fix bug where `MediaMetadata` was only populated from Vorbis comments
|
||||
with upper-case keys
|
||||
|
@ -786,8 +786,11 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
// first byte
|
||||
captionChannelPacketData.skipBits(2); // null padding
|
||||
boolean visible = captionChannelPacketData.readBit();
|
||||
boolean rowLock = captionChannelPacketData.readBit();
|
||||
boolean columnLock = captionChannelPacketData.readBit();
|
||||
|
||||
// ANSI/CTA-708-E S-2023 spec (Section 8.4.7) indicates that rowLock and columnLock values in
|
||||
// the media should be ignored and assumed to be true.
|
||||
captionChannelPacketData.skipBits(2);
|
||||
|
||||
int priority = captionChannelPacketData.readBits(3);
|
||||
// second byte
|
||||
boolean relativePositioning = captionChannelPacketData.readBit();
|
||||
@ -799,7 +802,8 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
int rowCount = captionChannelPacketData.readBits(4);
|
||||
// fifth byte
|
||||
captionChannelPacketData.skipBits(2); // null padding
|
||||
int columnCount = captionChannelPacketData.readBits(6);
|
||||
// TODO: Add support for column count.
|
||||
captionChannelPacketData.skipBits(6); // column count
|
||||
// sixth byte
|
||||
captionChannelPacketData.skipBits(2); // null padding
|
||||
int windowStyle = captionChannelPacketData.readBits(3);
|
||||
@ -807,14 +811,11 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
|
||||
cueInfoBuilder.defineWindow(
|
||||
visible,
|
||||
rowLock,
|
||||
columnLock,
|
||||
priority,
|
||||
relativePositioning,
|
||||
verticalAnchor,
|
||||
horizontalAnchor,
|
||||
rowCount,
|
||||
columnCount,
|
||||
anchorId,
|
||||
windowStyle,
|
||||
penStyle);
|
||||
@ -975,7 +976,6 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
private int horizontalAnchor;
|
||||
private int anchorId;
|
||||
private int rowCount;
|
||||
private boolean rowLock;
|
||||
private int justification;
|
||||
private int windowStyleId;
|
||||
private int penStyleId;
|
||||
@ -1011,7 +1011,6 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
horizontalAnchor = 0;
|
||||
anchorId = 0;
|
||||
rowCount = MAXIMUM_ROW_COUNT;
|
||||
rowLock = true;
|
||||
justification = JUSTIFICATION_LEFT;
|
||||
windowStyleId = 0;
|
||||
penStyleId = 0;
|
||||
@ -1045,20 +1044,16 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
|
||||
public void defineWindow(
|
||||
boolean visible,
|
||||
boolean rowLock,
|
||||
boolean columnLock,
|
||||
int priority,
|
||||
boolean relativePositioning,
|
||||
int verticalAnchor,
|
||||
int horizontalAnchor,
|
||||
int rowCount,
|
||||
int columnCount,
|
||||
int anchorId,
|
||||
int windowStyleId,
|
||||
int penStyleId) {
|
||||
this.defined = true;
|
||||
this.visible = visible;
|
||||
this.rowLock = rowLock;
|
||||
this.priority = priority;
|
||||
this.relativePositioning = relativePositioning;
|
||||
this.verticalAnchor = verticalAnchor;
|
||||
@ -1070,14 +1065,12 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
this.rowCount = rowCount + 1;
|
||||
|
||||
// Trim any rolled up captions that are no longer valid, if applicable.
|
||||
while ((rowLock && (rolledUpCaptions.size() >= this.rowCount))
|
||||
while ((rolledUpCaptions.size() >= this.rowCount)
|
||||
|| (rolledUpCaptions.size() >= MAXIMUM_ROW_COUNT)) {
|
||||
rolledUpCaptions.remove(0);
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Add support for column lock and count.
|
||||
|
||||
if (windowStyleId != 0 && this.windowStyleId != windowStyleId) {
|
||||
this.windowStyleId = windowStyleId;
|
||||
// windowStyleId is 1-based.
|
||||
@ -1239,7 +1232,7 @@ public final class Cea708Parser implements SubtitleParser {
|
||||
backgroundColorStartPosition = 0;
|
||||
}
|
||||
|
||||
while ((rowLock && (rolledUpCaptions.size() >= rowCount))
|
||||
while ((rolledUpCaptions.size() >= rowCount)
|
||||
|| (rolledUpCaptions.size() >= MAXIMUM_ROW_COUNT)) {
|
||||
rolledUpCaptions.remove(0);
|
||||
}
|
||||
|
@ -115,6 +115,40 @@ public class Cea708ParserTest {
|
||||
.isEqualTo("test subtitle");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void singleServiceAndWindowDefinition_ignoreRowLock() throws Exception {
|
||||
Cea708Parser cea708Parser =
|
||||
new Cea708Parser(
|
||||
/* accessibilityChannel= */ Format.NO_VALUE, /* initializationData= */ null);
|
||||
byte[] windowDefinition =
|
||||
TestUtil.createByteArray(
|
||||
0x98, // DF0 command (define window 0)
|
||||
0b0010_0000, // visible=true, row lock and column lock disabled, priority=0
|
||||
0xF0 | 50, // relative positioning, anchor vertical
|
||||
50, // anchor horizontal
|
||||
1, // anchor point = 0, row count = 1
|
||||
30, // column count = 30
|
||||
0b0000_1001); // window style = 1, pen style = 1
|
||||
byte[] setCurrentWindow = TestUtil.createByteArray(0x80); // CW0 (set current window to 0)
|
||||
byte[] subtitleData =
|
||||
encodePacketIntoBytePairs(
|
||||
createPacket(
|
||||
/* sequenceNumber= */ 0,
|
||||
createServiceBlock(
|
||||
Bytes.concat(
|
||||
windowDefinition,
|
||||
setCurrentWindow,
|
||||
"row1\r\nrow2\r\nrow3\r\nrow4".getBytes(Charsets.UTF_8)))));
|
||||
|
||||
List<CuesWithTiming> result = new ArrayList<>();
|
||||
cea708Parser.parse(subtitleData, SubtitleParser.OutputOptions.allCues(), result::add);
|
||||
|
||||
// Row count is 1 (which means 2 rows should be kept). Row lock is disabled in the media,
|
||||
// but this is ignored and the result is still truncated to only the last two rows.
|
||||
assertThat(Iterables.getOnlyElement(Iterables.getOnlyElement(result).cues).text.toString())
|
||||
.isEqualTo("row3\nrow4");
|
||||
}
|
||||
|
||||
/** See section 4.4.1 of the CEA-708-B spec. */
|
||||
private static byte[] encodePacketIntoBytePairs(byte[] packet) {
|
||||
checkState(packet.length % 2 == 0);
|
||||
|
Loading…
x
Reference in New Issue
Block a user