a35f70c6 by David LaPalomento

Add tfdt to track fragment boxes

According to the byte stream format registry, a media segment should contain at least one track fragment decode timestamp box.
1 parent 31946efc
......@@ -37,6 +37,7 @@ DataView = window.DataView;
stsz: [],
stts: [],
styp: [],
tfdt: [],
tfhd: [],
traf: [],
trak: [],
......@@ -406,7 +407,12 @@ traf = function(track) {
(track.id & 0xFF000000) >> 24,
(track.id & 0xFF0000) >> 16,
(track.id & 0xFF00) >> 8,
(track.id & 0xFF),
(track.id & 0xFF) // track_ID
])),
box(types.tfdt, new Uint8Array([
0x00, // version 0
0x00, 0x00, 0x00, // flags
0x00, 0x00, 0x00, 0x00 // baseMediaDecodeTime
])),
trun(track));
};
......@@ -445,11 +451,12 @@ trun = function(track) {
bytes = [
0x00, // version 0
0x00, 0x0f, 0x00, // flags
0x00, 0x0f, 0x01, // flags
(samples.length & 0xFF000000) >>> 24,
(samples.length & 0xFF0000) >>> 16,
(samples.length & 0xFF00) >>> 8,
samples.length & 0xFF // sample_count
samples.length & 0xFF, // sample_count
0x00, 0x00, 0x00, 0x00 // data_offset
];
for (i = 0; i < samples.length; i++) {
......
......@@ -339,12 +339,19 @@ test('generates a minimal moof', function() {
equal(moof[0].boxes[0].type, 'mfhd', 'generated an mfhd box');
equal(moof[0].boxes[0].sequenceNumber, 7, 'included the sequence_number');
equal(moof[0].boxes[1].type, 'traf', 'generated a traf box');
equal(moof[0].boxes[1].boxes.length, 2, 'generated track fragment info');
equal(moof[0].boxes[1].boxes.length, 3, 'generated track fragment info');
equal(moof[0].boxes[1].boxes[0].type, 'tfhd', 'generated a tfhd box');
equal(moof[0].boxes[1].boxes[0].trackId, 17, 'wrote the first track id');
equal(moof[0].boxes[1].boxes[0].type, 'tfhd', 'generated a tfhd box');
trun = moof[0].boxes[1].boxes[1];
equal(moof[0].boxes[1].boxes[0].baseDataOffset, undefined, 'did not set a base data offset');
equal(moof[0].boxes[1].boxes[1].type, 'tfdt', 'generated a tfdt box');
ok(moof[0].boxes[1].boxes[1].baseMediaDecodeTime >= 0,
'media decode time is non-negative');
trun = moof[0].boxes[1].boxes[2];
equal(trun.type, 'trun', 'generated a trun box');
equal(typeof trun.dataOffset, 'number', 'has a data offset');
ok(trun.dataOffset >= 0, 'has a non-negative data offset');
equal(trun.samples.length, 2, 'wrote two samples');
equal(trun.samples[0].duration, 9000, 'wrote a sample duration');
......@@ -381,7 +388,7 @@ test('can generate a traf without samples', function() {
}]),
moof = videojs.inspectMp4(data);
equal(moof[0].boxes[1].boxes[1].samples.length, 0, 'generated no samples');
equal(moof[0].boxes[1].boxes[2].samples.length, 0, 'generated no samples');
});
test('generates an mdat', function() {
......
......@@ -671,7 +671,7 @@ test('can parse a moof', function() {
type: 'tfhd',
version: 0,
size: 40,
flags: new Uint8Array([0, 0, 0x3b]),
flags: new Uint8Array([0x00, 0, 0x3b]),
trackId: 1,
baseDataOffset: 1,
sampleDescriptionIndex: 2,
......
......@@ -880,7 +880,13 @@ validateTrackFragment = function(track, metadata) {
equal(tfhd.type, 'tfhd', 'wrote a track fragment header');
equal(tfhd.trackId, metadata.trackId, 'wrote the track id');
trun = track.boxes[1];
equal(track.boxes[1].type,
'tfdt',
'wrote a track fragment decode time box');
ok(track.boxes[1].baseMediaDecodeTime >= 0, 'base decode time is valid');
trun = track.boxes[2];
ok(trun.dataOffset >= 0, 'set data offset');
ok(trun.samples.length > 0, 'generated media samples');
for (i = 0; i < trun.samples.length; i++) {
sample = trun.samples[i];
......