Commit cbe9f051 authored by Antoine Cellerier's avatar Antoine Cellerier

Make code less readable and (hopefully) faster for gradient and edge modes.

parent 5fcb0513
...@@ -107,6 +107,10 @@ struct filter_sys_t ...@@ -107,6 +107,10 @@ struct filter_sys_t
int i_gradient_type; int i_gradient_type;
vlc_bool_t b_cartoon; vlc_bool_t b_cartoon;
uint32_t *p_buf32;
uint32_t *p_buf32_bis;
uint8_t *p_buf8;
/* For hough mode */ /* For hough mode */
int *p_pre_hough; int *p_pre_hough;
}; };
...@@ -176,6 +180,10 @@ static int Create( vlc_object_t *p_this ) ...@@ -176,6 +180,10 @@ static int Create( vlc_object_t *p_this )
p_filter->p_sys->b_cartoon = p_filter->p_sys->b_cartoon =
var_GetInteger( p_filter, FILTER_PREFIX "cartoon" ); var_GetInteger( p_filter, FILTER_PREFIX "cartoon" );
p_filter->p_sys->p_buf32 = NULL;
p_filter->p_sys->p_buf32_bis = NULL;
p_filter->p_sys->p_buf8 = NULL;
return VLC_SUCCESS; return VLC_SUCCESS;
} }
...@@ -188,8 +196,10 @@ static void Destroy( vlc_object_t *p_this ) ...@@ -188,8 +196,10 @@ static void Destroy( vlc_object_t *p_this )
{ {
filter_t *p_filter = (filter_t *)p_this; filter_t *p_filter = (filter_t *)p_this;
if(p_filter->p_sys->p_pre_hough) free( p_filter->p_sys->p_buf32 );
free(p_filter->p_sys->p_pre_hough); free( p_filter->p_sys->p_buf32_bis );
free( p_filter->p_sys->p_buf8 );
free( p_filter->p_sys->p_pre_hough );
free( p_filter->p_sys ); free( p_filter->p_sys );
} }
...@@ -272,36 +282,36 @@ static void GaussianConvolution( picture_t *p_inpic, uint32_t *p_smooth ) ...@@ -272,36 +282,36 @@ static void GaussianConvolution( picture_t *p_inpic, uint32_t *p_smooth )
{ {
p_smooth[y*i_src_visible+x] = (uint32_t)( p_smooth[y*i_src_visible+x] = (uint32_t)(
/* 2 rows up */ /* 2 rows up */
( p_inpix[(y-2)*i_src_pitch+x-2]<<1 ) ( p_inpix[(y-2)*i_src_pitch+x-2] )
+ ( p_inpix[(y-2)*i_src_pitch+x-1]<<2 ) + ((p_inpix[(y-2)*i_src_pitch+x-1]
+ ( p_inpix[(y-2)*i_src_pitch+x]<<2 ) + p_inpix[(y-2)*i_src_pitch+x]
+ ( p_inpix[(y-2)*i_src_pitch+x+1]<<2 ) + p_inpix[(y-2)*i_src_pitch+x+1])<<1 )
+ ( p_inpix[(y-2)*i_src_pitch+x+2]<<1 ) + ( p_inpix[(y-2)*i_src_pitch+x+2] )
/* 1 row up */ /* 1 row up */
+ ( p_inpix[(y-1)*i_src_pitch+x-2]<<2 ) + ((p_inpix[(y-1)*i_src_pitch+x-2]
+ ( p_inpix[(y-1)*i_src_pitch+x-1]<<3 ) + ( p_inpix[(y-1)*i_src_pitch+x-1]<<1 )
+ ( p_inpix[(y-1)*i_src_pitch+x]*12 ) + ( p_inpix[(y-1)*i_src_pitch+x]*3 )
+ ( p_inpix[(y-1)*i_src_pitch+x+1]<<3 ) + ( p_inpix[(y-1)*i_src_pitch+x+1]<<1 )
+ ( p_inpix[(y-1)*i_src_pitch+x+2]<<2 ) + p_inpix[(y-1)*i_src_pitch+x+2]
/* */ /* */
+ ( p_inpix[y*i_src_pitch+x-2]<<2 ) + p_inpix[y*i_src_pitch+x-2]
+ ( p_inpix[y*i_src_pitch+x-1]*12 ) + ( p_inpix[y*i_src_pitch+x-1]*3 )
+ ( p_inpix[y*i_src_pitch+x]<<4 ) + ( p_inpix[y*i_src_pitch+x]<<2 )
+ ( p_inpix[y*i_src_pitch+x+1]*12 ) + ( p_inpix[y*i_src_pitch+x+1]*3 )
+ ( p_inpix[y*i_src_pitch+x+2]<<2 ) + p_inpix[y*i_src_pitch+x+2]
/* 1 row down */ /* 1 row down */
+ ( p_inpix[(y+1)*i_src_pitch+x-2]<<2 ) + p_inpix[(y+1)*i_src_pitch+x-2]
+ ( p_inpix[(y+1)*i_src_pitch+x-1]<<3 ) + ( p_inpix[(y+1)*i_src_pitch+x-1]<<1 )
+ ( p_inpix[(y+1)*i_src_pitch+x]*12 ) + ( p_inpix[(y+1)*i_src_pitch+x]*3 )
+ ( p_inpix[(y+1)*i_src_pitch+x+1]<<3 ) + ( p_inpix[(y+1)*i_src_pitch+x+1]<<1 )
+ ( p_inpix[(y+1)*i_src_pitch+x+2]<<2 ) + p_inpix[(y+1)*i_src_pitch+x+2] )<<1 )
/* 2 rows down */ /* 2 rows down */
+ ( p_inpix[(y+2)*i_src_pitch+x-2]<<1 ) + ( p_inpix[(y+2)*i_src_pitch+x-2] )
+ ( p_inpix[(y+2)*i_src_pitch+x-1]<<2 ) + ((p_inpix[(y+2)*i_src_pitch+x-1]
+ ( p_inpix[(y+2)*i_src_pitch+x]<<2 ) + p_inpix[(y+2)*i_src_pitch+x]
+ ( p_inpix[(y+2)*i_src_pitch+x+1]<<2 ) + p_inpix[(y+2)*i_src_pitch+x+1])<<1 )
+ ( p_inpix[(y+2)*i_src_pitch+x+2]<<1 ) + ( p_inpix[(y+2)*i_src_pitch+x+2] )
) >> 7 /* 115 */; ) >> 6 /* 115 */;
} }
} }
} }
...@@ -321,7 +331,11 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic, ...@@ -321,7 +331,11 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic,
uint8_t *p_inpix = p_inpic->p[Y_PLANE].p_pixels; uint8_t *p_inpix = p_inpic->p[Y_PLANE].p_pixels;
uint8_t *p_outpix = p_outpic->p[Y_PLANE].p_pixels; uint8_t *p_outpix = p_outpic->p[Y_PLANE].p_pixels;
uint32_t *p_smooth = (uint32_t *)malloc( i_num_lines * i_src_visible * sizeof(uint32_t)); uint32_t *p_smooth;
if( !p_filter->p_sys->p_buf32 )
p_filter->p_sys->p_buf32 =
(uint32_t *)malloc( i_num_lines * i_src_visible * sizeof(uint32_t));
p_smooth = p_filter->p_sys->p_buf32;
if( !p_smooth ) return; if( !p_smooth ) return;
...@@ -350,34 +364,36 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic, ...@@ -350,34 +364,36 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic,
| -2 0 2 | and | 0 0 0 | | -2 0 2 | and | 0 0 0 |
| -1 0 1 | | -1 -2 -1 | */ | -1 0 1 | | -1 -2 -1 | */
for( y = 1; y < i_num_lines - 1; y++ ) #define FOR \
{ for( y = 1; y < i_num_lines - 1; y++ ) \
for( x = 1; x < i_src_visible - 1; x++ ) { \
{ for( x = 1; x < i_src_visible - 1; x++ ) \
uint32_t a = { \
( uint32_t a = \
abs( ( \
( ( p_smooth[(y-1)*i_src_visible+x] abs( \
- p_smooth[(y+1)*i_src_visible+x] ) <<1 ) ( p_smooth[(y-1)*i_src_visible+x-1] \
+ ( p_smooth[(y-1)*i_src_visible+x-1] - p_smooth[(y+1)*i_src_visible+x-1] ) \
- p_smooth[(y+1)*i_src_visible+x-1] ) + ( ( p_smooth[(y-1)*i_src_visible+x] \
+ ( p_smooth[(y-1)*i_src_visible+x+1] - p_smooth[(y+1)*i_src_visible+x] ) <<1 ) \
- p_smooth[(y+1)*i_src_visible+x+1] ) + ( p_smooth[(y-1)*i_src_visible+x+1] \
) - p_smooth[(y+1)*i_src_visible+x+1] ) \
+ ) \
abs( + \
( ( p_smooth[y*i_src_visible+x-1] abs( \
- p_smooth[y*i_src_visible+x+1] ) <<1 ) ( p_smooth[(y-1)*i_src_visible+x-1] \
+ ( p_smooth[(y-1)*i_src_visible+x-1] - p_smooth[(y-1)*i_src_visible+x+1] ) \
- p_smooth[(y-1)*i_src_visible+x+1] ) + ( ( p_smooth[y*i_src_visible+x-1] \
+ ( p_smooth[(y+1)*i_src_visible+x-1] - p_smooth[y*i_src_visible+x+1] ) <<1 ) \
- p_smooth[(y+1)*i_src_visible+x+1] ) + ( p_smooth[(y+1)*i_src_visible+x-1] \
) - p_smooth[(y+1)*i_src_visible+x+1] ) \
) \
); );
if( p_filter->p_sys->i_gradient_type ) if( p_filter->p_sys->i_gradient_type )
{ {
if( p_filter->p_sys->b_cartoon ) if( p_filter->p_sys->b_cartoon )
{ {
FOR
if( a > 60 ) if( a > 60 )
{ {
p_outpix[y*i_dst_pitch+x] = 0x00; p_outpix[y*i_dst_pitch+x] = 0x00;
...@@ -397,26 +413,28 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic, ...@@ -397,26 +413,28 @@ static void FilterGradient( filter_t *p_filter, picture_t *p_inpic,
p_outpix[y*i_dst_pitch+x] = p_outpix[y*i_dst_pitch+x] =
0x28 - ((0x28 - p_inpix[y*i_src_pitch+x] )>>2); 0x28 - ((0x28 - p_inpix[y*i_src_pitch+x] )>>2);
} }
}}
} }
else else
{ {
FOR
if( a>>8 ) if( a>>8 )
p_outpix[y*i_dst_pitch+x] = 255; p_outpix[y*i_dst_pitch+x] = 255;
else else
p_outpix[y*i_dst_pitch+x] = (uint8_t)a; p_outpix[y*i_dst_pitch+x] = (uint8_t)a;
}}
} }
} }
else else
{ {
FOR
if( a>>8 ) if( a>>8 )
p_outpix[y*i_dst_pitch+x] = 0; p_outpix[y*i_dst_pitch+x] = 0;
else else
p_outpix[y*i_dst_pitch+x] = (uint8_t)(255 - a); p_outpix[y*i_dst_pitch+x] = 0xff-(uint8_t)a;
}}
} }
} #undef FOR
}
if( p_smooth ) free( p_smooth );
} }
/***************************************************************************** /*****************************************************************************
...@@ -447,9 +465,24 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic, ...@@ -447,9 +465,24 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic,
uint8_t *p_inpix = p_inpic->p[Y_PLANE].p_pixels; uint8_t *p_inpix = p_inpic->p[Y_PLANE].p_pixels;
uint8_t *p_outpix = p_outpic->p[Y_PLANE].p_pixels; uint8_t *p_outpix = p_outpic->p[Y_PLANE].p_pixels;
uint32_t *p_smooth = malloc( i_num_lines*i_src_visible * sizeof(uint32_t) ); uint32_t *p_smooth;
uint32_t *p_grad = malloc( i_num_lines*i_src_visible *sizeof(uint32_t) ); uint32_t *p_grad;
uint8_t *p_theta = malloc( i_num_lines*i_src_visible *sizeof(uint8_t) ); uint8_t *p_theta;
if( !p_filter->p_sys->p_buf32 )
p_filter->p_sys->p_buf32 =
(uint32_t *)malloc( i_num_lines * i_src_visible * sizeof(uint32_t));
p_smooth = p_filter->p_sys->p_buf32;
if( !p_filter->p_sys->p_buf32_bis )
p_filter->p_sys->p_buf32_bis =
(uint32_t *)malloc( i_num_lines * i_src_visible * sizeof(uint32_t));
p_grad = p_filter->p_sys->p_buf32_bis;
if( !p_filter->p_sys->p_buf8 )
p_filter->p_sys->p_buf8 =
(uint8_t *)malloc( i_num_lines * i_src_visible * sizeof(uint8_t));
p_theta = p_filter->p_sys->p_buf8;
if( !p_smooth || !p_grad || !p_theta ) return; if( !p_smooth || !p_grad || !p_theta ) return;
...@@ -486,17 +519,17 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic, ...@@ -486,17 +519,17 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic,
{ {
int gradx = int gradx =
( ( p_smooth[(y-1)*i_src_visible+x] ( p_smooth[(y-1)*i_src_visible+x-1]
- p_smooth[(y+1)*i_src_visible+x] ) <<1 )
+ ( p_smooth[(y-1)*i_src_visible+x-1]
- p_smooth[(y+1)*i_src_visible+x-1] ) - p_smooth[(y+1)*i_src_visible+x-1] )
+ ( ( p_smooth[(y-1)*i_src_visible+x]
- p_smooth[(y+1)*i_src_visible+x] ) <<1 )
+ ( p_smooth[(y-1)*i_src_visible+x+1] + ( p_smooth[(y-1)*i_src_visible+x+1]
- p_smooth[(y+1)*i_src_visible+x+1] ); - p_smooth[(y+1)*i_src_visible+x+1] );
int grady = int grady =
( ( p_smooth[y*i_src_visible+x-1] ( p_smooth[(y-1)*i_src_visible+x-1]
- p_smooth[y*i_src_visible+x+1] ) <<1 )
+ ( p_smooth[(y-1)*i_src_visible+x-1]
- p_smooth[(y-1)*i_src_visible+x+1] ) - p_smooth[(y-1)*i_src_visible+x+1] )
+ ( ( p_smooth[y*i_src_visible+x-1]
- p_smooth[y*i_src_visible+x+1] ) <<1 )
+ ( p_smooth[(y+1)*i_src_visible+x-1] + ( p_smooth[(y+1)*i_src_visible+x-1]
- p_smooth[(y+1)*i_src_visible+x+1] ); - p_smooth[(y+1)*i_src_visible+x+1] );
...@@ -531,29 +564,29 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic, ...@@ -531,29 +564,29 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic,
&& p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x] ) && p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x] )
{ {
p_outpix[y*i_dst_pitch+x] = 0; p_outpix[y*i_dst_pitch+x] = 0;
} else goto colorize;
break; break;
} else goto colorize;
case THETA_P: case THETA_P:
if( p_grad[y*i_src_visible+x] > p_grad[(y-1)*i_src_visible+x-1] if( p_grad[y*i_src_visible+x] > p_grad[(y-1)*i_src_visible+x-1]
&& p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x+1] ) && p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x+1] )
{ {
p_outpix[y*i_dst_pitch+x] = 0; p_outpix[y*i_dst_pitch+x] = 0;
} else goto colorize;
break; break;
} else goto colorize;
case THETA_M: case THETA_M:
if( p_grad[y*i_src_visible+x] > p_grad[(y-1)*i_src_visible+x+1] if( p_grad[y*i_src_visible+x] > p_grad[(y-1)*i_src_visible+x+1]
&& p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x-1] ) && p_grad[y*i_src_visible+x] > p_grad[(y+1)*i_src_visible+x-1] )
{ {
p_outpix[y*i_dst_pitch+x] = 0; p_outpix[y*i_dst_pitch+x] = 0;
} else goto colorize;
break; break;
} else goto colorize;
case THETA_X: case THETA_X:
if( p_grad[y*i_src_visible+x] > p_grad[y*i_src_visible+x-1] if( p_grad[y*i_src_visible+x] > p_grad[y*i_src_visible+x-1]
&& p_grad[y*i_src_visible+x] > p_grad[y*i_src_visible+x+1] ) && p_grad[y*i_src_visible+x] > p_grad[y*i_src_visible+x+1] )
{ {
p_outpix[y*i_dst_pitch+x] = 0; p_outpix[y*i_dst_pitch+x] = 0;
} else goto colorize;
break; break;
} else goto colorize;
} }
} }
else else
...@@ -577,9 +610,6 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic, ...@@ -577,9 +610,6 @@ static void FilterEdge( filter_t *p_filter, picture_t *p_inpic,
} }
} }
} }
if( p_smooth ) free( p_smooth );
if( p_grad ) free( p_grad );
if( p_theta) free( p_theta );
} }
/***************************************************************************** /*****************************************************************************
......
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