summaryrefslogtreecommitdiffstats
path: root/libass/ass_render.c
diff options
context:
space:
mode:
authorwm4 <wm4@nowhere>2013-09-25 19:23:52 +0200
committerwm4 <wm4@nowhere>2013-09-26 00:39:13 +0200
commit4f542f2b9d003125c3b04416074078c3d81c0d6c (patch)
tree0cb8817499bd558a08e1d21a514fa9e2c1afa7fb /libass/ass_render.c
parent9b48357234806a4fe29ec97eba6c998a26033b5d (diff)
downloadlibass-4f542f2b9d003125c3b04416074078c3d81c0d6c.tar.bz2
libass-4f542f2b9d003125c3b04416074078c3d81c0d6c.tar.xz
Fix Hinting again
Commit 05eb520 missed some duplicated bits in ass_shaper.c. <wm4> oh crap <zgreg> oh crap indeed Instead of duplicating the logic in ass_shaper.c, just change the glyphs before they even get into processing. This way, all code reading the font size etc. is affected. This essentially reverts commit c207000c, because it's not needed anymore.
Diffstat (limited to 'libass/ass_render.c')
-rw-r--r--libass/ass_render.c64
1 files changed, 43 insertions, 21 deletions
diff --git a/libass/ass_render.c b/libass/ass_render.c
index 0cf1f16..734dc6c 100644
--- a/libass/ass_render.c
+++ b/libass/ass_render.c
@@ -937,8 +937,8 @@ static void draw_opaque_box(ASS_Renderer *render_priv, GlyphInfo *info,
{
int i;
int adv = advance.x;
- double scale_y = info->scale_y;
- double scale_x = info->scale_x;
+ double scale_y = info->orig_scale_y;
+ double scale_x = info->orig_scale_x;
// to avoid gaps
sx = FFMAX(64, sx);
@@ -1099,21 +1099,10 @@ get_outline_glyph(ASS_Renderer *priv, GlyphInfo *info)
v.desc = drawing->desc;
key.u.drawing.text = strdup(drawing->text);
} else {
- double ft_size;
- if (priv->settings.hinting == ASS_HINTING_NONE) {
- // arbitrary, not too small to prevent grid fitting rounding effects
- // XXX: this is a rather crude hack
- ft_size = 256.0;
- } else {
- // If hinting is enabled, we want to pass the real font size
- // to freetype. Normalize scale_y to 1.0.
- ft_size = info->scale_y * info->font_size;
- }
- ass_face_set_size(info->font->faces[info->face_index], ft_size);
- ass_font_set_transform(info->font,
- info->scale_x * info->font_size / ft_size,
- info->scale_y * info->font_size / ft_size,
- NULL);
+ ass_face_set_size(info->font->faces[info->face_index],
+ info->font_size);
+ ass_font_set_transform(info->font, info->scale_x,
+ info->scale_y, NULL);
FT_Glyph glyph =
ass_font_get_glyph(priv->fontconfig_priv, info->font,
info->symbol, info->face_index, info->glyph_index,
@@ -1128,8 +1117,8 @@ get_outline_glyph(ASS_Renderer *priv, GlyphInfo *info)
FT_Done_Glyph(glyph);
ass_font_get_asc_desc(info->font, info->symbol,
&v.asc, &v.desc);
- v.asc *= info->scale_y * info->font_size / ft_size;
- v.desc *= info->scale_y * info->font_size / ft_size;
+ v.asc *= info->scale_y;
+ v.desc *= info->scale_y;
}
}
@@ -1682,6 +1671,33 @@ fill_bitmap_hash(ASS_Renderer *priv, GlyphInfo *info,
}
/**
+ * \brief Adjust the glyph's font size and scale factors to ensure smooth
+ * scaling and handle pathological font sizes. The main problem here is
+ * freetype's grid fitting, which destroys animations by font size, or will
+ * result in incorrect final text size if font sizes are very small and
+ * scale factors very large. See Google Code issue #46.
+ * \param priv guess what
+ * \param glyph the glyph to be modified
+ */
+static void
+fix_glyph_scaling(ASS_Renderer *priv, GlyphInfo *glyph)
+{
+ double ft_size;
+ if (priv->settings.hinting == ASS_HINTING_NONE) {
+ // arbitrary, not too small to prevent grid fitting rounding effects
+ // XXX: this is a rather crude hack
+ ft_size = 256.0;
+ } else {
+ // If hinting is enabled, we want to pass the real font size
+ // to freetype. Normalize scale_y to 1.0.
+ ft_size = glyph->scale_y * glyph->font_size;
+ }
+ glyph->scale_x = glyph->scale_x * glyph->font_size / ft_size;
+ glyph->scale_y = glyph->scale_y * glyph->font_size / ft_size;
+ glyph->font_size = ft_size;
+}
+
+/**
* \brief Main ass rendering function, glues everything together
* \param event event to render
* \param event_images struct containing resulting images, will also be initialized
@@ -1808,8 +1824,12 @@ ass_render_event(ASS_Renderer *render_priv, ASS_Event *event,
glyphs[text_info->length].blur = render_priv->state.blur;
glyphs[text_info->length].shadow_x = render_priv->state.shadow_x;
glyphs[text_info->length].shadow_y = render_priv->state.shadow_y;
- glyphs[text_info->length].scale_x= render_priv->state.scale_x;
- glyphs[text_info->length].scale_y = render_priv->state.scale_y;
+ glyphs[text_info->length].orig_scale_x
+ = glyphs[text_info->length].scale_x
+ = render_priv->state.scale_x;
+ glyphs[text_info->length].orig_scale_y
+ = glyphs[text_info->length].scale_y
+ = render_priv->state.scale_y;
glyphs[text_info->length].border_style = render_priv->state.border_style;
glyphs[text_info->length].border_x= render_priv->state.border_x;
glyphs[text_info->length].border_y = render_priv->state.border_y;
@@ -1827,6 +1847,8 @@ ass_render_event(ASS_Renderer *render_priv, ASS_Event *event,
if (glyphs[text_info->length].drawing) {
drawing = render_priv->state.drawing =
ass_drawing_new(render_priv->library, render_priv->ftlibrary);
+ } else {
+ fix_glyph_scaling(render_priv, &glyphs[text_info->length]);
}
text_info->length++;