ttml: Add support for IMSC 1.0.1 fillLineGap attribute

Strictly speaking, the TTML spec requires that text backgrounds extend
only to the font height of the related text, rather than to the vertical
distance between lines. The result of this is that there will typically
be vertical gaps between line backgrounds through which moving video can
be seen. Since this was unnacceptable to some content providers, v1.0.1
of the IMSC spec (which profiles TTML) adds a new attribute,
itts:fillLineGap[1], that allows content authors to specify that clients
should extend text backgrounds such that there are no gaps between
lines. This attribute is also going to be included in the next release
of EBU-TT-D.

This patch adds support for fillLineGap to ttmlparse and ttmlrender.

[1] https://www.w3.org/TR/ttml-imsc1.0.1/#itts-fillLineGap

https://bugzilla.gnome.org/show_bug.cgi?id=787071
This commit is contained in:
Chris Bass 2018-02-27 10:07:18 +00:00 committed by Sebastian Dröge
parent 29d112dfd1
commit 2863a55a89
4 changed files with 35 additions and 18 deletions

View file

@ -2031,8 +2031,14 @@ gst_ttml_render_render_block_elements (GstTtmlRender * render,
block_metrics.line_height, block_metrics.baseline_offset);
g_free (markup);
bg_offset = 0;
bg_height = block_metrics.line_height;
if (!block->style_set->fill_line_gap) {
bg_offset =
block_metrics.baseline_offset - ue->pango_font_metrics.baseline;
bg_height = ue->pango_font_metrics.height;
} else {
bg_offset = 0;
bg_height = block_metrics.line_height;
}
bg_width = text_image->width;
if (line_padding > 0) {
@ -2656,7 +2662,9 @@ gst_ttml_render_render_text_region (GstTtmlRender * render,
/* Render each block and append to list. */
for (i = 0; i < gst_subtitle_region_get_block_count (region); ++i) {
const GstSubtitleBlock *block;
GstTtmlRenderRenderedImage *rendered_block;
GstTtmlRenderRenderedImage *rendered_block, *block_bg_image, *tmp;
GstBuffer *block_bg_buf;
gint block_height;
block = gst_subtitle_region_get_block (region, i);
rendered_block = gst_ttml_render_render_text_block (render, block, text_buf,
@ -2684,22 +2692,17 @@ gst_ttml_render_render_text_region (GstTtmlRender * render,
break;
}
if (!gst_ttml_render_color_is_transparent (&block->style_set->
background_color)) {
/* Draw block background rectangle and render block image over it */
GstTtmlRenderRenderedImage *tmp = rendered_block;
GstBuffer *block_bg_buf;
GstTtmlRenderRenderedImage *block_bg_image;
tmp = rendered_block;
block_bg_buf = gst_ttml_render_draw_rectangle (window_width,
rendered_block->height, block->style_set->background_color);
block_bg_image = gst_ttml_render_rendered_image_new (block_bg_buf, 0,
rendered_block->y, window_width, rendered_block->height);
rendered_block = gst_ttml_render_rendered_image_combine (block_bg_image,
rendered_block);
gst_ttml_render_rendered_image_free (tmp);
gst_ttml_render_rendered_image_free (block_bg_image);
}
block_height = rendered_block->height + (2 * rendered_block->y);
block_bg_buf = gst_ttml_render_draw_rectangle (window_width,
block_height, block->style_set->background_color);
block_bg_image = gst_ttml_render_rendered_image_new (block_bg_buf, 0, 0,
window_width, block_height);
rendered_block = gst_ttml_render_rendered_image_combine (block_bg_image,
rendered_block);
gst_ttml_render_rendered_image_free (tmp);
gst_ttml_render_rendered_image_free (block_bg_image);
rendered_block->y = 0;
g_ptr_array_add (rendered_blocks, rendered_block);

View file

@ -77,6 +77,7 @@ gst_subtitle_style_set_new (void)
ret->extent_w = ret->extent_h = 0.0;
ret->padding_start = ret->padding_end
= ret->padding_before = ret->padding_after = 0.0;
ret->fill_line_gap = FALSE;
return ret;
}

View file

@ -353,6 +353,12 @@ typedef enum {
* @overflow: Defines what should happen if text and background rectangles
* generated by rendering text blocks overflow the size of their containing
* region. Applies only to #GstSubtitleRegions.
* @fill_line_gap: Controls whether the rendered backgrounds of text elements
* in a line fill the whole space between that line and adjacent lines or
* extends only to the font height of the text in the individual elements (thus
* this field controls whether or not there are gaps between backgrounds
* through which the underlying video can be seen). Applies only to
* #GstSubtitleBlocks.
*
* Holds a set of attributes that describes the styling and layout that apply
* to #GstSubtitleRegion, #GstSubtitleBlock and/or #GstSubtitleElement objects.
@ -391,6 +397,7 @@ struct _GstSubtitleStyleSet
GstSubtitleWritingMode writing_mode;
GstSubtitleBackgroundMode show_background;
GstSubtitleOverflowMode overflow;
gboolean fill_line_gap;
/*< private >*/
gpointer _gst_reserved[GST_PADDING];

View file

@ -234,6 +234,7 @@ ttml_parse_style_set (const xmlNode * node)
for (attr = node->properties; attr != NULL; attr = attr->next) {
if (attr->ns && ((g_strcmp0 ((const gchar *) attr->ns->prefix, "tts") == 0)
|| (g_strcmp0 ((const gchar *) attr->ns->prefix, "itts") == 0)
|| (g_strcmp0 ((const gchar *) attr->ns->prefix, "ebutts") == 0))) {
ttml_style_set_add_attr (s, (const gchar *) attr->name,
(const gchar *) attr->children->content);
@ -658,6 +659,11 @@ ttml_update_style_set (GstSubtitleStyleSet * style_set, TtmlStyleSet * tss,
else
style_set->overflow = GST_SUBTITLE_OVERFLOW_MODE_HIDDEN;
}
if ((attr = ttml_style_set_get_attr (tss, "fillLineGap"))) {
if (g_strcmp0 (attr, "true") == 0)
style_set->fill_line_gap = TRUE;
}
}