Closed GoogleCodeExporter closed 9 years ago
So the code that's currently there doesn't necessarily add all samples to the
stss:
void MP4Track::UpdateSyncSamples(MP4SampleId sampleId, bool isSyncSample)
{
if (isSyncSample) {
// if stss atom exists, add entry
if (m_pStssCountProperty) {
m_pStssSampleProperty->AddValue(sampleId);
m_pStssCountProperty->IncrementValue();
} // else nothing to do (yet)
} else { // !isSyncSample
// if stss atom doesn't exist, create one
if (m_pStssCountProperty == NULL) {
MP4Atom* pStssAtom = AddAtom("trak.mdia.minf.stbl", "stss");
ASSERT(pStssAtom->FindProperty(
"stss.entryCount",
(MP4Property**)&m_pStssCountProperty));
ASSERT(pStssAtom->FindProperty(
"stss.entries.sampleNumber",
(MP4Property**)&m_pStssSampleProperty));
// set values for all samples that came before this one
uint32_t samples = GetNumberOfSamples();
for (MP4SampleId sid = 1; sid < samples; sid++) {
m_pStssSampleProperty->AddValue(sid);
m_pStssCountProperty->IncrementValue();
}
} // else nothing to do
}
}
So, two things:
1. If a track consists only of sync samples, then there should be no stss atom.
Your code would always create an stss atom, including for tracks that are
entirely "sync points," such as most audio tracks.
2. The above code seems to presume the first sample given in each track is
always a sync point. So the first non-sync point sample (which, if there are
any, would generally be the _second_ sample) would add an stss atom and flag
all previous samples (in normal operation, should only be the _first_ sample)
as sync points. From that point on, only sync points would be added.
It isn't clear to me what you're doing in your writing application to end up
with all your samples in the stss. Could you post a code-snippet showing how
you're writing files? I checked a few files from a project I wrote that uses
mp4v2, and my stss atoms were definitely correct.
Original comment by kid...@gmail.com
on 19 Mar 2012 at 2:36
Please reopen this if you still have an issue, but the code (so far as I can
see) is correct. See
https://developer.apple.com/library/mac/#documentation/QuickTime/QTFF/QTFFChap2/
qtff2.html - in particular,
The sync sample atom identifies the key frames in the media. In a media that
contains compressed data, key frames define starting points for portions of a
temporally compressed sequence. The key frame is self-contained—that is, it
is independent of preceding frames. Subsequent frames may depend on the key
frame.
The sync sample atom provides a compact marking of the random access points
within a stream. The table is arranged in strictly increasing order of sample
number. If this table is not present, every sample is implicitly a random
access point.
Sync sample atoms have an atom type of 'stss'. The sync sample atom contains a
table of sample numbers. Each entry in the table identifies a sample that is a
key frame for the media. If no sync sample atom exists, then all the samples
are key frames.
...the last line, "if no sync sample atom exists, then all the samples are key
frames," is what makes the code as-is correct. The code doesn't bother adding
an stss atom until a non-sync sample comes along. If a non-sync sample comes
along, that implies all previous samples _must_ be sync samples, and should be
marked as such in the stss.
Closing, please re-open the issue if you still have a problem and I'll help you
work through it. Thanks.
Original comment by kid...@gmail.com
on 20 May 2012 at 8:48
Original issue reported on code.google.com by
wdwwh1717
on 6 Mar 2012 at 8:19