#include <math.h>
-static void PreCompute(uint8_t *yuv, int32_t *rgb, int width, int height)
+static void PreCompute(uint8_t *image, int32_t *rgb, int width, int height)
{
register int x, y, z;
- register int uneven = width % 2;
- int w = (width - uneven ) / 2;
- int yy, uu, vv;
- int r, g, b;
int32_t pts[3];
- for (y=0; y<height; y++)
+
+ for (y = 0; y < height; y++)
{
- for (x=0; x<w; x++)
+ for (x = 0; x < width; x++)
{
- uu = yuv[1];
- vv = yuv[3];
- yy = yuv[0];
- YUV2RGB(yy, uu, vv, r, g, b);
- pts[0] = r;
- pts[1] = g;
- pts[2] = b;
+ pts[0] = image[0];
+ pts[1] = image[1];
+ pts[2] = image[2];
for (z = 0; z < 3; z++)
{
- if (x>0) pts[z]+=rgb[-3];
- if (y>0) pts[z]+=rgb[-(width*3)];
- if (x>0 && y>0) pts[z]-=rgb[-((width+1)*3)];
- *rgb++=pts[z];
- }
-
- yy = yuv[2];
- YUV2RGB(yy, uu, vv, r, g, b);
- pts[0] = r;
- pts[1] = g;
- pts[2] = b;
- for (z = 0; z < 3; z++)
- {
- pts[z]+=rgb[-3];
- if (y>0)
- {
- pts[z]+=rgb[-(width*3)];
- pts[z]-=rgb[-((width+1)*3)];
- }
- *rgb++=pts[z];
- }
- yuv += 4;
- }
- if (uneven)
- {
- uu = yuv[1];
- vv = yuv[3];
- yy = yuv[0];
- YUV2RGB(yy, uu, vv, r, g, b);
- pts[0] = r;
- pts[1] = g;
- pts[2] = b;
- for (z = 0; z < 3; z++)
- {
- pts[z]+=rgb[-3];
- if (y>0)
- {
- pts[z]+=rgb[-(width*3)];
- pts[z]-=rgb[-((width+1)*3)];
- }
- *rgb++=pts[z];
- }
- yuv += 2;
+ if (x > 0) pts[z] += rgb[-3];
+ if (y > 0) pts[z] += rgb[width * -3];
+ if (x>0 && y>0) pts[z] -= rgb[(width + 1) * -3];
+ *rgb++ = pts[z];
+ }
+ image += 3;
}
}
}
static int32_t GetRGB(int32_t *rgb, unsigned int w, unsigned int h, unsigned int x, int offsetx, unsigned int y, int offsety, unsigned int z)
{
- int xtheo = x * 2 + offsetx;
- int ytheo = y + offsety;
- if (xtheo < 0) xtheo = 0; else if (xtheo >= w) xtheo = w - 1;
- if (ytheo < 0) ytheo = 0; else if (ytheo >= h) ytheo = h - 1;
- return rgb[3*(xtheo+ytheo*w)+z];
-}
-
-static int32_t GetRGB2(int32_t *rgb, unsigned int w, unsigned int h, unsigned int x, int offsetx, unsigned int y, int offsety, unsigned int z)
-{
- int xtheo = x * 2 + 1 + offsetx;
+ int xtheo = x * 1 + offsetx;
int ytheo = y + offsety;
if (xtheo < 0) xtheo = 0; else if (xtheo >= w) xtheo = w - 1;
if (ytheo < 0) ytheo = 0; else if (ytheo >= h) ytheo = h - 1;
return rgb[3*(xtheo+ytheo*w)+z];
}
-static void DoBoxBlur(uint8_t *yuv, int32_t *rgb, unsigned int width, unsigned int height, unsigned int boxw, unsigned int boxh)
+static void DoBoxBlur(uint8_t *image, int32_t *rgb, unsigned int width, unsigned int height, unsigned int boxw, unsigned int boxh)
{
register int x, y;
- int32_t r, g, b;
- register int uneven = width % 2;
- register int y0, y1, u0, u1, v0, v1;
- int w = (width - uneven ) / 2;
float mul = 1.f / ((boxw*2) * (boxh*2));
for (y = 0; y < height; y++)
{
- for (x = 0; x < w; x++)
+ for (x = 0; x < width; x++)
{
- r = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 0) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 0) - GetRGB(rgb, width, height, x, -boxw, y, + boxh, 0) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 0);
- g = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 1) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 1) - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 1) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 1);
- b = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 2) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 2) - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 2) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 2);
- r = (int32_t) (r * mul);
- g = (int32_t) (g * mul);
- b = (int32_t) (b * mul);
- RGB2YUV (r, g, b, y0, u0, v0);
-
- r = GetRGB2(rgb, width, height, x, +boxw, y, +boxh, 0) + GetRGB2(rgb, width, height, x, -boxw, y, -boxh, 0) - GetRGB2(rgb, width, height, x, -boxw, y, +boxh, 0) - GetRGB2(rgb, width, height, x, +boxw, y, -boxh, 0);
- g = GetRGB2(rgb, width, height, x, +boxw, y, +boxh, 1) + GetRGB2(rgb, width, height, x, -boxw, y, -boxh, 1) - GetRGB2(rgb, width, height, x, -boxw, y, +boxh, 1) - GetRGB2(rgb, width, height, x, +boxw, y, -boxh, 1);
- b = GetRGB2(rgb, width, height, x, +boxw, y, +boxh, 2) + GetRGB2(rgb, width, height, x, -boxw, y, -boxh, 2) - GetRGB2(rgb, width, height, x, -boxw, y, +boxh, 2) - GetRGB2(rgb, width, height, x, +boxw, y, -boxh, 2);
- r = (int32_t) (r * mul);
- g = (int32_t) (g * mul);
- b = (int32_t) (b * mul);
- RGB2YUV (r, g, b, y1, u1, v1);
- *yuv++ = y0;
- *yuv++ = (u0+u1) >> 1;
- *yuv++ = y1;
- *yuv++ = (v0+v1) >> 1;
- }
- if (uneven)
- {
- r = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 0) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 0) - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 0) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 0);
- g = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 1) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 1) - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 1) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 1);
- b = GetRGB(rgb, width, height, x, +boxw, y, +boxh, 2) + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 2) - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 2) - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 2);
- r = (int32_t) (r * mul);
- g = (int32_t) (g * mul);
- b = (int32_t) (b * mul);
- RGB2YUV (r, g, b, y0, u0, v0);
- *yuv++ = mul * y0;
- *yuv++ = mul * u0;
+ *image++ = (GetRGB(rgb, width, height, x, +boxw, y, +boxh, 0)
+ + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 0)
+ - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 0)
+ - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 0)) * mul;
+ *image++ = (GetRGB(rgb, width, height, x, +boxw, y, +boxh, 1)
+ + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 1)
+ - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 1)
+ - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 1)) * mul;
+ *image++ = (GetRGB(rgb, width, height, x, +boxw, y, +boxh, 2)
+ + GetRGB(rgb, width, height, x, -boxw, y, -boxh, 2)
+ - GetRGB(rgb, width, height, x, -boxw, y, +boxh, 2)
+ - GetRGB(rgb, width, height, x, +boxw, y, -boxh, 2)) * mul;
}
}
}
static int filter_get_image( mlt_frame this, uint8_t **image, mlt_image_format *format, int *width, int *height, int writable )
{
// Get the image
+ *format = mlt_image_rgb24;
int error = mlt_frame_get_image( this, image, format, width, height, 1 );
- short hori = mlt_properties_get_int(MLT_FRAME_PROPERTIES( this ), "hori" );
- short vert = mlt_properties_get_int(MLT_FRAME_PROPERTIES( this ), "vert" );
+ short hori = mlt_properties_get_int( MLT_FRAME_PROPERTIES( this ), "hori" );
+ short vert = mlt_properties_get_int( MLT_FRAME_PROPERTIES( this ), "vert" );
// Only process if we have no error and a valid colour space
- if ( error == 0 && *format == mlt_image_yuv422 )
+ if ( error == 0 )
{
double factor = mlt_properties_get_double( MLT_FRAME_PROPERTIES( this ), "boxblur" );
- if (factor != 0) {
+ if ( factor != 0)
+ {
int h = *height + 1;
- int32_t *rgb = mlt_pool_alloc (3 * *width * h * sizeof(int32_t));
- PreCompute (*image, rgb, *width, h);
- DoBoxBlur (*image, rgb, *width, h, (int) factor*hori, (int) factor*vert);
- mlt_pool_release (rgb);
+ int32_t *rgb = mlt_pool_alloc( 3 * *width * h * sizeof(int32_t) );
+ PreCompute( *image, rgb, *width, h );
+ DoBoxBlur( *image, rgb, *width, h, (int) factor * hori, (int) factor * vert );
+ mlt_pool_release( rgb );
}
- }
+ }
return error;
}
if ( mlt_properties_get( MLT_FILTER_PROPERTIES( this ), "end" ) != NULL )
{
// Determine the time position of this frame in the transition duration
- mlt_position in = mlt_filter_get_in( this );
- mlt_position out = mlt_filter_get_out( this );
- mlt_position time = mlt_frame_get_position( frame );
- double position = (double) ( time - in ) / ( out - in + 1.0 );
double end = (double) mlt_properties_get_int( MLT_FILTER_PROPERTIES( this ), "end" );
- blur += ( end - blur ) * position;
+ blur += ( end - blur ) * mlt_filter_get_progress( this, frame );
}
// Push the frame filter
if ( this != NULL )
{
this->process = filter_process;
- mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "start", arg == NULL ? "10" : arg);
+ mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "start", arg == NULL ? "2" : arg);
mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "hori", arg == NULL ? "1" : arg);
mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "vert", arg == NULL ? "1" : arg);
}