2 * filter_dust.c -- dust filter
3 * Copyright (c) 2007 Marco Gittler <g.marco@freenet.de>
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 //#include <framework/mlt_filter.h>
21 //#include <framework/mlt_frame.h>
22 #include <framework/mlt.h>
30 static void overlay_image(uint8_t *src
, int src_width
, int src_height
, uint8_t * overlay
, int overlay_width
, int overlay_height
, uint8_t * alpha
, int xpos
, int ypos
, int upsidedown
, int mirror
){
33 for (y
=ypos
;y
<src_height
; y
++){
34 if ( y
>=0 && (y
-ypos
)<overlay_height
){
35 uint8_t *scanline_image
=src
+src_width
*y
*2;
36 int overlay_y
= upsidedown ?
( overlay_height
- ( y
- ypos
) - 1 ) : ( y
- ypos
);
37 uint8_t *scanline_overlay
=overlay
+ overlay_width
* 2 * overlay_y
;
39 for ( x
= xpos
; x
< src_width
&& x
-xpos
< overlay_width
;x
++){
41 int overlay_x
= mirror ? overlay_width
- ( x
- xpos
) -1 : ( x
- xpos
);
42 double alp
=(double)*(alpha
+ overlay_width
* overlay_y
+ overlay_x
)/255.0;
43 uint8_t* image_pixel
= scanline_image
+ x
* 2;
44 uint8_t* overlay_pixel
= scanline_overlay
+ overlay_x
* 2;
46 *image_pixel
=(double)(*overlay_pixel
)*alp
+ (double)*image_pixel
*(1.0-alp
) ;
52 mirror? overlay_pixel
-- : overlay_pixel
++;
54 *image_pixel
=(double)(*(overlay_pixel
))*alp
+ (double)(*image_pixel
)*(1.0-alp
) ;
62 static int filter_get_image( mlt_frame
this, uint8_t **image
, mlt_image_format
*format
, int *width
, int *height
, int writable
)
64 mlt_filter filter
= mlt_frame_pop_service( this );
66 int maxdia
= mlt_properties_get_int( MLT_FILTER_PROPERTIES( filter
), "maxdiameter" );
67 int maxcount
= mlt_properties_get_int( MLT_FILTER_PROPERTIES( filter
), "maxcount" );
69 mlt_position in
= mlt_filter_get_in( filter
);
70 mlt_position out
= mlt_filter_get_out( filter
);
71 mlt_position time
= mlt_frame_get_position( this );
72 double position
= ( double )( time
- in
) / ( double )( out
- in
+ 1 );
74 int error
= mlt_frame_get_image( this, image
, format
, width
, height
, 1 );
76 mlt_properties properties
= MLT_FILTER_PROPERTIES( filter
);
77 char *factory
= mlt_properties_get( properties
, "factory" );
79 sprintf( temp
, "%s/oldfilm/", mlt_environment( "MLT_DATA" ) );
81 mlt_properties direntries
=mlt_properties_new();
82 mlt_properties_dir_list(direntries
,temp
,"dust*.svg",1);
86 srand(position
*10000);
88 int im
=rand()%maxcount
;
89 int piccount
=mlt_properties_count(direntries
);
90 while (im
-- && piccount
){
92 int picnum
=rand()%piccount
;
94 int y1
=rand()%*height
;
96 char resource
[1024]="";
97 char savename
[1024]="",savename1
[1024]="", cachedy
[100];
98 int dx
=(*width
*maxdia
/100);
99 int luma_width
,luma_height
;
100 uint8_t *luma_image
= NULL
;
101 uint8_t *alpha
=NULL
;
102 int updown
= rand()%2;
105 sprintf(resource
,"%s",mlt_properties_get_value(direntries
,picnum
));
106 sprintf(savename
,"cache-%d-%d",picnum
,dx
);
107 sprintf(savename1
,"cache-alpha-%d-%d",picnum
,dx
);
108 sprintf(cachedy
,"cache-dy-%d-%d",picnum
,dx
);
110 luma_image
= mlt_properties_get_data( properties
, savename
, NULL
);
111 alpha
= mlt_properties_get_data( properties
, savename1
, NULL
);
113 if (luma_image
== NULL
|| alpha
== NULL
){
114 mlt_profile profile
= mlt_service_profile( MLT_FILTER_SERVICE( filter
) );
115 mlt_producer producer
= mlt_factory_producer( profile
, factory
, resource
);
117 if ( producer
!= NULL
)
119 mlt_properties producer_properties
= MLT_PRODUCER_PROPERTIES( producer
);
121 mlt_properties_set( producer_properties
, "eof", "loop" );
122 mlt_frame luma_frame
= NULL
;
124 if ( mlt_service_get_frame( MLT_PRODUCER_SERVICE( producer
), &luma_frame
, 0 ) == 0 ){
126 mlt_properties_set_double ( MLT_FRAME_PROPERTIES ( luma_frame
) , "consumer_aspect_ratio" , 1.0 );
127 mlt_image_format luma_format
= mlt_image_yuv422
;
129 luma_height
= luma_width
* mlt_properties_get_int( MLT_FRAME_PROPERTIES ( luma_frame
) , "height" ) / mlt_properties_get_int( MLT_FRAME_PROPERTIES ( luma_frame
) , "width" );
131 mlt_properties_set( MLT_FRAME_PROPERTIES( luma_frame
), "rescale.interp", "best" );// none/nearest/tiles/hyper
133 mlt_frame_get_image( luma_frame
, &luma_image
, &luma_format
, &luma_width
, &luma_height
, 0 );
134 alpha
=mlt_frame_get_alpha_mask(luma_frame
);
136 uint8_t* savealpha
=mlt_pool_alloc ( luma_width
* luma_height
);
137 uint8_t* savepic
=mlt_pool_alloc ( luma_width
* luma_height
* 2);
139 if (savealpha
&& savepic
){
140 memcpy (savealpha
, alpha
, luma_width
* luma_height
);
141 memcpy (savepic
, luma_image
, luma_width
* luma_height
* 2);
143 mlt_properties_set_data ( properties
, savename
, savepic
, sizeof(uint8_t*) , mlt_pool_release
, NULL
);
144 mlt_properties_set_data ( properties
, savename1
, savealpha
, sizeof(uint8_t*) , mlt_pool_release
, NULL
);
145 mlt_properties_set_int ( properties
, cachedy
, luma_height
);
147 overlay_image(*image
,*width
,*height
,luma_image
,luma_width
,luma_height
, alpha
, x1
, y1
, updown
, mirror
);
149 mlt_frame_close( luma_frame
);
151 mlt_producer_close( producer
);
154 overlay_image ( *image
, *width
, *height
, luma_image
, dx
, mlt_properties_get_int ( properties
, cachedy
) , alpha
, x1
, y1
, updown
, mirror
);
159 if ( error
== 0 && *image
&& *format
== mlt_image_yuv422
)
167 int im
=rand()%maxcount
;
173 int dx
=rand()%maxdia
;
174 int dy
=rand()%maxdia
;
177 for ( x
= -dx
; x
< dx
; x
++ )
178 for ( y
= -dy
; y
< dy
; y
++ ) {
179 if ( x1
+x
< w
&& x1
+x
> 0 && y1
+y
< h
&& y1
+y
> 0 ){
180 uint8_t *pix
=*image
+(y
+y1
)*w
*2+(x
+x1
)*2;
181 //v=(1.0-fabs(x)/dx)*(1.0-fabs(y)/dy);
182 v
=pow((double)x
/(double)dx
*5.0,2.0)+pow((double)y
/(double)dy
*5.0,2.0);
203 static mlt_frame
filter_process( mlt_filter
this, mlt_frame frame
)
206 mlt_frame_push_service( frame
, this );
207 mlt_frame_push_get_image( frame
, filter_get_image
);
212 mlt_filter
filter_dust_init( mlt_profile profile
, mlt_service_type type
, const char *id
, char *arg
)
214 mlt_filter
this = mlt_filter_new( );
217 this->process
= filter_process
;
218 mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "maxdiameter", "2" );
219 mlt_properties_set( MLT_FILTER_PROPERTIES( this ), "maxcount", "10" );