isomp4: Update edit list when re-writing moov

Correctly update any edit lists each time the moov is recalculated,
updating existing table entries if they already exist instead of just
adding new ones.
This commit is contained in:
Jan Schmidt 2015-04-01 00:58:52 +11:00
parent 0c1bcc629d
commit 3d7b343525
3 changed files with 34 additions and 21 deletions

View file

@ -3279,31 +3279,41 @@ atom_tkhd_set_subtitle (AtomTKHD * tkhd, AtomsContext * context, guint32 width,
static void
atom_edts_add_entry (AtomEDTS * edts, EditListEntry * entry)
atom_edts_add_entry (AtomEDTS * edts, gint index, EditListEntry * entry)
{
edts->elst.entries = g_slist_append (edts->elst.entries, entry);
EditListEntry *e =
(EditListEntry *) g_slist_nth_data (edts->elst.entries, index);
/* Create a new entry if missing (appends to the list if index is larger) */
if (e == NULL) {
e = g_new (EditListEntry, 1);
edts->elst.entries = g_slist_insert (edts->elst.entries, e, index);
}
/* Update the entry */
*e = *entry;
}
/*
* Adds a new entry to this trak edits list
/*
* Update an entry in this trak edits list, creating it if needed.
* index is the index of the entry to update, or create if it's past the end.
* duration is in the moov's timescale
* media_time is the offset in the media time to start from (media's timescale)
* rate is a 32 bits fixed-point
*/
void
atom_trak_add_elst_entry (AtomTRAK * trak, guint32 duration, guint32 media_time,
guint32 rate)
atom_trak_set_elst_entry (AtomTRAK * trak, gint index,
guint32 duration, guint32 media_time, guint32 rate)
{
EditListEntry *entry = g_new (EditListEntry, 1);
EditListEntry entry;
entry->duration = duration;
entry->media_time = media_time;
entry->media_rate = rate;
entry.duration = duration;
entry.media_time = media_time;
entry.media_rate = rate;
if (trak->edts == NULL) {
if (trak->edts == NULL)
trak->edts = atom_edts_new ();
}
atom_edts_add_entry (trak->edts, entry);
atom_edts_add_entry (trak->edts, index, &entry);
}
/* re-negotiation is prevented at top-level, so only 1 entry expected.

View file

@ -828,7 +828,7 @@ AtomTRAK* atom_trak_new (AtomsContext *context);
void atom_trak_add_samples (AtomTRAK * trak, guint32 nsamples, guint32 delta,
guint32 size, guint64 chunk_offset, gboolean sync,
gint64 pts_offset);
void atom_trak_add_elst_entry (AtomTRAK * trak, guint32 duration,
void atom_trak_set_elst_entry (AtomTRAK * trak, gint index, guint32 duration,
guint32 media_time, guint32 rate);
guint32 atom_trak_get_timescale (AtomTRAK *trak);
guint32 atom_trak_get_id (AtomTRAK * trak);

View file

@ -249,7 +249,6 @@ enum
#define DEFAULT_DTS_METHOD DTS_METHOD_REORDER
#endif
static void gst_qt_mux_finalize (GObject * object);
static GstStateChangeReturn gst_qt_mux_change_state (GstElement * element,
@ -2110,25 +2109,29 @@ gst_qt_mux_stop_file (GstQTMux * qtmux)
first_ts = qtpad->first_ts;
}
}
GST_DEBUG_OBJECT (qtmux, "Media first ts selected: %" GST_TIME_FORMAT,
GST_TIME_ARGS (first_ts));
/* add EDTSs for late streams */
/* add/update EDTSs for late streams. configure_moov will have
* set the trak durations above by summing the sample tables */
for (walk = qtmux->collect->data; walk; walk = g_slist_next (walk)) {
GstCollectData *cdata = (GstCollectData *) walk->data;
GstQTPad *qtpad = (GstQTPad *) cdata;
guint32 lateness;
guint32 duration;
if (GST_CLOCK_TIME_IS_VALID (qtpad->first_ts) && qtpad->first_ts > first_ts) {
if (GST_CLOCK_TIME_IS_VALID (qtpad->first_ts)
&& qtpad->first_ts > first_ts) {
GST_DEBUG_OBJECT (qtmux, "Pad %s is a late stream by %" GST_TIME_FORMAT,
GST_PAD_NAME (qtpad->collect.pad),
GST_TIME_ARGS (qtpad->first_ts - first_ts));
lateness = gst_util_uint64_scale_round (qtpad->first_ts - first_ts,
timescale, GST_SECOND);
lateness =
gst_util_uint64_scale_round (qtpad->first_ts - first_ts, timescale,
GST_SECOND);
duration = qtpad->trak->tkhd.duration;
atom_trak_add_elst_entry (qtpad->trak, lateness, (guint32) - 1,
atom_trak_set_elst_entry (qtpad->trak, 0, lateness, (guint32) - 1,
(guint32) (1 * 65536.0));
atom_trak_add_elst_entry (qtpad->trak, duration, 0,
atom_trak_set_elst_entry (qtpad->trak, 1, duration, 0,
(guint32) (1 * 65536.0));
/* need to add the empty time to the trak duration */