qtmux: Add support for muxing svmi atom for stereoscopic video information

https://bugzilla.gnome.org/show_bug.cgi?id=793120
This commit is contained in:
Sebastian Dröge 2018-02-02 13:51:49 +02:00
parent 4fd8635983
commit e7177059e9
3 changed files with 99 additions and 0 deletions

View file

@ -728,6 +728,33 @@ atom_ctts_free (AtomCTTS * ctts)
g_free (ctts);
}
static void
atom_svmi_init (AtomSVMI * svmi)
{
guint8 flags[3] = { 0, 0, 0 };
atom_full_init (&svmi->header, FOURCC_svmi, 0, 0, 0, flags);
svmi->stereoscopic_composition_type = 0x00;
svmi->is_left_first = FALSE;
}
AtomSVMI *
atom_svmi_new (guint8 stereoscopic_composition_type, gboolean is_left_first)
{
AtomSVMI *svmi = g_new0 (AtomSVMI, 1);
atom_svmi_init (svmi);
svmi->stereoscopic_composition_type = stereoscopic_composition_type;
svmi->is_left_first = is_left_first;
return svmi;
}
static void
atom_svmi_free (AtomSVMI * svmi)
{
g_free (svmi);
}
static void
atom_stts_init (AtomSTTS * stts)
{
@ -822,6 +849,7 @@ atom_stbl_init (AtomSTBL * stbl)
atom_stsz_init (&stbl->stsz);
atom_stsc_init (&stbl->stsc);
stbl->ctts = NULL;
stbl->svmi = NULL;
atom_co64_init (&stbl->stco64);
}
@ -838,6 +866,9 @@ atom_stbl_clear (AtomSTBL * stbl)
if (stbl->ctts) {
atom_ctts_free (stbl->ctts);
}
if (stbl->svmi) {
atom_svmi_free (stbl->svmi);
}
atom_stco64_clear (&stbl->stco64);
}
@ -2292,6 +2323,25 @@ atom_ctts_copy_data (AtomCTTS * ctts, guint8 ** buffer, guint64 * size,
return *offset - original_offset;
}
guint64
atom_svmi_copy_data (AtomSVMI * svmi, guint8 ** buffer, guint64 * size,
guint64 * offset)
{
guint64 original_offset = *offset;
if (!atom_full_copy_data (&svmi->header, buffer, size, offset)) {
return 0;
}
prop_copy_uint8 (svmi->stereoscopic_composition_type, buffer, size, offset);
prop_copy_uint8 (svmi->is_left_first ? 1 : 0, buffer, size, offset);
/* stereo-mono change count */
prop_copy_uint32 (0, buffer, size, offset);
atom_write_size (buffer, size, offset, original_offset);
return *offset - original_offset;
}
guint64
atom_stco64_copy_data (AtomSTCO64 * stco64, guint8 ** buffer, guint64 * size,
guint64 * offset)
@ -2454,6 +2504,11 @@ atom_stbl_copy_data (AtomSTBL * stbl, guint8 ** buffer, guint64 * size,
return 0;
}
}
if (stbl->svmi) {
if (!atom_svmi_copy_data (stbl->svmi, buffer, size, offset)) {
return 0;
}
}
if (!atom_stco64_copy_data (&stbl->stco64, buffer, size, offset)) {
return 0;
}

View file

@ -563,6 +563,14 @@ typedef struct _AtomCTTS
gboolean do_pts;
} AtomCTTS;
typedef struct _AtomSVMI
{
AtomFull header;
guint8 stereoscopic_composition_type;
gboolean is_left_first;
} AtomSVMI;
typedef struct _AtomSTBL
{
Atom header;
@ -574,6 +582,8 @@ typedef struct _AtomSTBL
AtomSTSZ stsz;
/* NULL if not present */
AtomCTTS *ctts;
/* NULL if not present */
AtomSVMI *svmi;
AtomSTCO64 stco64;
} AtomSTBL;
@ -960,6 +970,9 @@ guint64 atom_stsz_copy_data (AtomSTSZ *atom, guint8 **buffer,
guint64 *size, guint64* offset);
guint64 atom_ctts_copy_data (AtomCTTS *atom, guint8 **buffer,
guint64 *size, guint64* offset);
guint64 atom_svmi_copy_data (AtomSVMI *atom, guint8 **buffer,
guint64 *size, guint64* offset);
AtomSVMI * atom_svmi_new (guint8 stereoscopic_composition_type, gboolean is_left_first);
guint64 atom_stco64_copy_data (AtomSTCO64 *atom, guint8 **buffer,
guint64 *size, guint64* offset);
AtomMOOF* atom_moof_new (AtomsContext *context, guint32 sequence_number);

View file

@ -5189,6 +5189,7 @@ gst_qt_mux_video_sink_set_caps (GstQTPad * qtpad, GstCaps * caps)
GList *ext_atom_list = NULL;
gboolean sync = FALSE;
int par_num, par_den;
const gchar *multiview_mode;
/* does not go well to renegotiate stream mid-way, unless
* the old caps are a subset of the new one (this means upstream
@ -5258,6 +5259,36 @@ gst_qt_mux_video_sink_set_caps (GstQTPad * qtpad, GstCaps * caps)
GST_DEBUG_OBJECT (qtmux, "Rate of video track selected: %" G_GUINT32_FORMAT,
rate);
multiview_mode = gst_structure_get_string (structure, "multiview-mode");
if (multiview_mode && !qtpad->trak->mdia.minf.stbl.svmi) {
GstVideoMultiviewMode mode;
GstVideoMultiviewFlags flags = 0;
mode = gst_video_multiview_mode_from_caps_string (multiview_mode);
gst_structure_get_flagset (structure, "multiview-flags", &flags, NULL);
switch (mode) {
case GST_VIDEO_MULTIVIEW_MODE_SIDE_BY_SIDE:
qtpad->trak->mdia.minf.stbl.svmi =
atom_svmi_new (0,
flags & GST_VIDEO_MULTIVIEW_FLAGS_RIGHT_VIEW_FIRST);
break;
case GST_VIDEO_MULTIVIEW_MODE_ROW_INTERLEAVED:
qtpad->trak->mdia.minf.stbl.svmi =
atom_svmi_new (1,
flags & GST_VIDEO_MULTIVIEW_FLAGS_RIGHT_VIEW_FIRST);
break;
case GST_VIDEO_MULTIVIEW_MODE_FRAME_BY_FRAME:
qtpad->trak->mdia.minf.stbl.svmi =
atom_svmi_new (2,
flags & GST_VIDEO_MULTIVIEW_FLAGS_RIGHT_VIEW_FIRST);
break;
default:
GST_DEBUG_OBJECT (qtmux, "Unsupported multiview-mode %s",
multiview_mode);
break;
}
}
/* set common properties */
entry.width = width;
entry.height = height;