changeset 28799:65b83aee82fb

Use blur with kernel [[1,2,1], [2,4,2], [1,2,1]] for \be. This is faster than gaussian blur and similar to vsfilter.
author greg
date Fri, 06 Mar 2009 01:17:05 +0000
parents 60b7ea3da519
children 83f8140eb736
files libass/ass_bitmap.c libass/ass_bitmap.h libass/ass_render.c
diffstat 3 files changed, 34 insertions(+), 14 deletions(-) [+]
line wrap: on
line diff
--- a/libass/ass_bitmap.c	Fri Mar 06 00:47:03 2009 +0000
+++ b/libass/ass_bitmap.c	Fri Mar 06 01:17:05 2009 +0000
@@ -255,11 +255,38 @@
 	return bm_s;
 }
 
-int glyph_to_bitmap(ass_synth_priv_t* priv, ass_synth_priv_t* priv_blur,
+/**
+ * \brief Blur with [[1,2,1]. [2,4,2], [1,2,1]] kernel
+ * This blur is the same as the one employed by vsfilter.
+ */
+static void be_blur(unsigned char *buf, int w, int h) {
+	unsigned int x, y;
+	unsigned int old_sum, new_sum;
+
+	for (y=0; y<h; y++) {
+		old_sum = 2 * buf[0];
+		for (x=0; x<w-1; x++) {
+			new_sum = buf[y*w+x] + buf[y*w+x+1];
+			buf[y*w+x] = (old_sum + new_sum) >> 2;
+			old_sum = new_sum;
+		}
+	}
+
+	for (x=0; x<w; x++) {
+		old_sum = 2 * buf[0];
+		for (y=0; y<h-1; y++) {
+			new_sum = buf[y*w+x] + buf[(y+1)*w+x];
+			buf[y*w+x] = (old_sum + new_sum) >> 2;
+			old_sum = new_sum;
+		}
+	}
+}
+
+int glyph_to_bitmap(ass_synth_priv_t* priv_blur,
 		FT_Glyph glyph, FT_Glyph outline_glyph, bitmap_t** bm_g,
 		bitmap_t** bm_o, bitmap_t** bm_s, int be, double blur_radius)
 {
-	int bord = be ? (be+1) : 0;
+	int bord = be ? (be/4+1) : 0;
 	blur_radius *= 2;
 	bord = (blur_radius > 0.0) ? blur_radius : bord;
 
@@ -279,19 +306,16 @@
 			return 1;
 		}
 	}
-	if (*bm_o) {
-		resize_tmp(priv, (*bm_o)->w, (*bm_o)->h);
+	if (*bm_o)
 		resize_tmp(priv_blur, (*bm_o)->w, (*bm_o)->h);
-	}
-	resize_tmp(priv, (*bm_g)->w, (*bm_g)->h);
 	resize_tmp(priv_blur, (*bm_g)->w, (*bm_g)->h);
 	
 	if (be) {
 		while (be--) {
 			if (*bm_o)
-				blur((*bm_o)->buffer, priv->tmp, (*bm_o)->w, (*bm_o)->h, (*bm_o)->w, (int*)priv->gt2, priv->g_r, priv->g_w);
+				be_blur((*bm_o)->buffer, (*bm_o)->w, (*bm_o)->h);
 			else
-				blur((*bm_g)->buffer, priv->tmp, (*bm_g)->w, (*bm_g)->h, (*bm_g)->w, (int*)priv->gt2, priv->g_r, priv->g_w);
+				be_blur((*bm_g)->buffer, (*bm_g)->w, (*bm_g)->h);
 		}
 	} else {
 		if (blur_radius > 0.0) {
--- a/libass/ass_bitmap.h	Fri Mar 06 00:47:03 2009 +0000
+++ b/libass/ass_bitmap.h	Fri Mar 06 01:17:05 2009 +0000
@@ -46,7 +46,7 @@
  * \param bm_g out: pointer to the bitmap of glyph shadow is returned here
  * \param be 1 = produces blurred bitmaps, 0 = normal bitmaps
  */
-int glyph_to_bitmap(ass_synth_priv_t* priv, ass_synth_priv_t* priv_blur, FT_Glyph glyph, FT_Glyph outline_glyph, bitmap_t** bm_g, bitmap_t** bm_o, bitmap_t** bm_s, int be, double blur_radius);
+int glyph_to_bitmap(ass_synth_priv_t* priv_blur, FT_Glyph glyph, FT_Glyph outline_glyph, bitmap_t** bm_g, bitmap_t** bm_o, bitmap_t** bm_s, int be, double blur_radius);
 
 void ass_free_bitmap(bitmap_t* bm);
 
--- a/libass/ass_render.c	Fri Mar 06 00:47:03 2009 +0000
+++ b/libass/ass_render.c	Fri Mar 06 01:17:05 2009 +0000
@@ -43,7 +43,6 @@
 
 #define MAX_GLYPHS 3000
 #define MAX_LINES 300
-#define BE_RADIUS 1.5
 #define BLUR_MAX_RADIUS 50.0
 #define ROUND(x) ((int) ((x) + .5))
 
@@ -83,7 +82,6 @@
 	ass_settings_t settings;
 	int render_id;
 	ass_synth_priv_t* synth_priv;
-	ass_synth_priv_t* synth_priv_blur;
 
 	ass_image_t* images_root; // rendering result is stored here
 	ass_image_t* prev_images_root;
@@ -270,8 +268,7 @@
 		goto ass_init_exit;
 	}
 
-	priv->synth_priv = ass_synth_init(BE_RADIUS);
-	priv->synth_priv_blur = ass_synth_init(BLUR_MAX_RADIUS);
+	priv->synth_priv = ass_synth_init(BLUR_MAX_RADIUS);
 
 	priv->library = library;
 	priv->ftlibrary = ft;
@@ -1503,7 +1500,6 @@
 
 			// render glyph
 			error = glyph_to_bitmap(ass_renderer->synth_priv,
-					ass_renderer->synth_priv_blur,
 					info->glyph, info->outline_glyph,
 					&info->bm, &info->bm_o,
 					&info->bm_s, info->be, info->blur * frame_context.border_scale);