Commit 2863a55a authored by Chris Bass's avatar Chris Bass Committed by Sebastian Dröge

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
parent 29d112df
...@@ -2031,8 +2031,14 @@ gst_ttml_render_render_block_elements (GstTtmlRender * render, ...@@ -2031,8 +2031,14 @@ gst_ttml_render_render_block_elements (GstTtmlRender * render,
block_metrics.line_height, block_metrics.baseline_offset); block_metrics.line_height, block_metrics.baseline_offset);
g_free (markup); g_free (markup);
bg_offset = 0; if (!block->style_set->fill_line_gap) {
bg_height = block_metrics.line_height; 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; bg_width = text_image->width;
if (line_padding > 0) { if (line_padding > 0) {
...@@ -2656,7 +2662,9 @@ gst_ttml_render_render_text_region (GstTtmlRender * render, ...@@ -2656,7 +2662,9 @@ gst_ttml_render_render_text_region (GstTtmlRender * render,
/* Render each block and append to list. */ /* Render each block and append to list. */
for (i = 0; i < gst_subtitle_region_get_block_count (region); ++i) { for (i = 0; i < gst_subtitle_region_get_block_count (region); ++i) {
const GstSubtitleBlock *block; 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); block = gst_subtitle_region_get_block (region, i);
rendered_block = gst_ttml_render_render_text_block (render, block, text_buf, rendered_block = gst_ttml_render_render_text_block (render, block, text_buf,
...@@ -2684,22 +2692,17 @@ gst_ttml_render_render_text_region (GstTtmlRender * render, ...@@ -2684,22 +2692,17 @@ gst_ttml_render_render_text_region (GstTtmlRender * render,
break; break;
} }
if (!gst_ttml_render_color_is_transparent (&block->style_set-> tmp = rendered_block;
background_color)) {
/* Draw block background rectangle and render block image over it */ block_height = rendered_block->height + (2 * rendered_block->y);
GstTtmlRenderRenderedImage *tmp = rendered_block; block_bg_buf = gst_ttml_render_draw_rectangle (window_width,
GstBuffer *block_bg_buf; block_height, block->style_set->background_color);
GstTtmlRenderRenderedImage *block_bg_image; block_bg_image = gst_ttml_render_rendered_image_new (block_bg_buf, 0, 0,
window_width, block_height);
block_bg_buf = gst_ttml_render_draw_rectangle (window_width, rendered_block = gst_ttml_render_rendered_image_combine (block_bg_image,
rendered_block->height, block->style_set->background_color); rendered_block);
block_bg_image = gst_ttml_render_rendered_image_new (block_bg_buf, 0, gst_ttml_render_rendered_image_free (tmp);
rendered_block->y, window_width, rendered_block->height); gst_ttml_render_rendered_image_free (block_bg_image);
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; rendered_block->y = 0;
g_ptr_array_add (rendered_blocks, rendered_block); g_ptr_array_add (rendered_blocks, rendered_block);
......
...@@ -77,6 +77,7 @@ gst_subtitle_style_set_new (void) ...@@ -77,6 +77,7 @@ gst_subtitle_style_set_new (void)
ret->extent_w = ret->extent_h = 0.0; ret->extent_w = ret->extent_h = 0.0;
ret->padding_start = ret->padding_end ret->padding_start = ret->padding_end
= ret->padding_before = ret->padding_after = 0.0; = ret->padding_before = ret->padding_after = 0.0;
ret->fill_line_gap = FALSE;
return ret; return ret;
} }
......
...@@ -353,6 +353,12 @@ typedef enum { ...@@ -353,6 +353,12 @@ typedef enum {
* @overflow: Defines what should happen if text and background rectangles * @overflow: Defines what should happen if text and background rectangles
* generated by rendering text blocks overflow the size of their containing * generated by rendering text blocks overflow the size of their containing
* region. Applies only to #GstSubtitleRegions. * 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 * Holds a set of attributes that describes the styling and layout that apply
* to #GstSubtitleRegion, #GstSubtitleBlock and/or #GstSubtitleElement objects. * to #GstSubtitleRegion, #GstSubtitleBlock and/or #GstSubtitleElement objects.
...@@ -391,6 +397,7 @@ struct _GstSubtitleStyleSet ...@@ -391,6 +397,7 @@ struct _GstSubtitleStyleSet
GstSubtitleWritingMode writing_mode; GstSubtitleWritingMode writing_mode;
GstSubtitleBackgroundMode show_background; GstSubtitleBackgroundMode show_background;
GstSubtitleOverflowMode overflow; GstSubtitleOverflowMode overflow;
gboolean fill_line_gap;
/*< private >*/ /*< private >*/
gpointer _gst_reserved[GST_PADDING]; gpointer _gst_reserved[GST_PADDING];
......
...@@ -234,6 +234,7 @@ ttml_parse_style_set (const xmlNode * node) ...@@ -234,6 +234,7 @@ ttml_parse_style_set (const xmlNode * node)
for (attr = node->properties; attr != NULL; attr = attr->next) { for (attr = node->properties; attr != NULL; attr = attr->next) {
if (attr->ns && ((g_strcmp0 ((const gchar *) attr->ns->prefix, "tts") == 0) 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))) { || (g_strcmp0 ((const gchar *) attr->ns->prefix, "ebutts") == 0))) {
ttml_style_set_add_attr (s, (const gchar *) attr->name, ttml_style_set_add_attr (s, (const gchar *) attr->name,
(const gchar *) attr->children->content); (const gchar *) attr->children->content);
...@@ -658,6 +659,11 @@ ttml_update_style_set (GstSubtitleStyleSet * style_set, TtmlStyleSet * tss, ...@@ -658,6 +659,11 @@ ttml_update_style_set (GstSubtitleStyleSet * style_set, TtmlStyleSet * tss,
else else
style_set->overflow = GST_SUBTITLE_OVERFLOW_MODE_HIDDEN; 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;
}
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment