15.02.12 20:49, Dan Dennedy написав(ла): [...]
use mlt_frame_get_image for converting image did not work - call to that function return blank frame...In the pixbuf patch, you should not call the convert_image virtual function directly; use mlt_frame_get_image().
i updated patch and added the same functionality to pango producer, but calling convert_image virtual function directly left till i find another way to convert it...
-- ________________________________________ Maksym Veremeyenko
>From 061535dd2d7675cbb7596f3be0ff4a7c1fc272ac Mon Sep 17 00:00:00 2001 From: Maksym Veremeyenko <ve...@m1stereo.tv> Date: Fri, 17 Feb 2012 16:17:32 +0200 Subject: [PATCH 1/2] save converted frame of pixbuf producer --- src/modules/gtk2/producer_pixbuf.c | 74 +++++++++++++++++++++++++++++++----- 1 files changed, 64 insertions(+), 10 deletions(-) diff --git a/src/modules/gtk2/producer_pixbuf.c b/src/modules/gtk2/producer_pixbuf.c index b7da50b..3adce16 100644 --- a/src/modules/gtk2/producer_pixbuf.c +++ b/src/modules/gtk2/producer_pixbuf.c @@ -59,8 +59,24 @@ struct producer_pixbuf_s uint8_t *image; mlt_cache_item image_cache; pthread_mutex_t mutex; + struct + { + uint8_t *image, *alpha; + int image_size, alpha_size; + mlt_image_format format; + } clone; }; +static void clean_clone( producer_pixbuf self ) +{ + if ( self->clone.image ) + mlt_pool_release( self->clone.image ); + self->clone.image = NULL; + if ( self->clone.alpha ) + mlt_pool_release( self->clone.alpha ); + self->clone.alpha = NULL; +} + static void load_filenames( producer_pixbuf self, mlt_properties producer_properties ); static void refresh_image( producer_pixbuf self, mlt_frame frame, int width, int height ); static int producer_get_frame( mlt_producer parent, mlt_frame_ptr frame, int index ); @@ -391,6 +407,7 @@ static void refresh_image( producer_pixbuf self, mlt_frame frame, int width, int int dst_stride = self->width * ( self->alpha ? 4 : 3 ); int image_size = dst_stride * ( height + 1 ); self->image = mlt_pool_alloc( image_size ); + clean_clone( self ); if ( src_stride != dst_stride ) { @@ -454,7 +471,8 @@ static void refresh_image( producer_pixbuf self, mlt_frame frame, int width, int static int producer_get_image( mlt_frame frame, uint8_t **buffer, mlt_image_format *format, int *width, int *height, int writable ) { int error = 0; - + mlt_image_format format_origin; + // Obtain properties of frame mlt_properties properties = MLT_FRAME_PROPERTIES( frame ); @@ -472,20 +490,55 @@ static int producer_get_image( mlt_frame frame, uint8_t **buffer, mlt_image_form // Get width and height (may have changed during the refresh) *width = self->width; *height = self->height; - *format = self->alpha ? mlt_image_rgb24a : mlt_image_rgb24; + format_origin = self->alpha ? mlt_image_rgb24a : mlt_image_rgb24; + if ( mlt_image_none == *format) + *format = format_origin; // NB: Cloning is necessary with this producer (due to processing of images ahead of use) // The fault is not in the design of mlt, but in the implementation of the pixbuf producer... if ( self->image ) { - // Clone the image - int image_size = self->width * self->height * ( self->alpha ? 4 :3 ); - uint8_t *image_copy = mlt_pool_alloc( image_size ); - memcpy( image_copy, self->image, image_size ); - // Now update properties so we free the copy after - mlt_frame_set_image( frame, image_copy, image_size, mlt_pool_release ); - // We're going to pass the copy on - *buffer = image_copy; + int size; + uint8_t* image; + + if ( self->clone.image && self->clone.format == *format) + { + image = mlt_pool_alloc( self->clone.image_size ); + memcpy( image, self->clone.image, self->clone.image_size ); + mlt_frame_set_image( frame, image, self->clone.image_size, mlt_pool_release ); + *buffer = image; + if ( self->clone.alpha ) + { + image = mlt_pool_alloc( self->clone.alpha_size ); + memcpy( image, self->clone.alpha, self->clone.alpha_size ); + mlt_frame_set_alpha( frame, image, self->clone.alpha_size, mlt_pool_release ); + }; + } + else + { + clean_clone( self ); + size = self->width * self->height * ( self->alpha ? 4 :3 ); + image = mlt_pool_alloc( size ); + memcpy( image, self->image, size ); + if(frame->convert_image && format_origin != *format) + { + frame->convert_image( frame, &image, &format_origin, *format ); + *format = format_origin; + } + mlt_frame_set_image( frame, image, size, mlt_pool_release ); + *buffer = image; + self->clone.format = *format; + self->clone.image_size = mlt_image_format_size( *format, *width, *height, NULL ); + self->clone.image = mlt_pool_alloc( self->clone.image_size ); + memcpy(self->clone.image, image, self->clone.image_size); + image = mlt_frame_get_alpha_mask(frame); + if ( image ) + { + self->clone.alpha_size = (*width) * (*height); + self->clone.alpha = mlt_pool_alloc( self->clone.alpha_size ); + memcpy(self->clone.alpha, image, self->clone.alpha_size); + }; + } mlt_log_debug( MLT_PRODUCER_SERVICE( &self->parent ), "%dx%d (%s)\n", self->width, self->height, mlt_image_format_name( *format ) ); } @@ -555,6 +608,7 @@ static int producer_get_frame( mlt_producer producer, mlt_frame_ptr frame, int i static void producer_close( mlt_producer parent ) { producer_pixbuf self = parent->child; + clean_clone( self ); pthread_mutex_destroy( &self->mutex ); parent->close = NULL; mlt_service_cache_purge( MLT_PRODUCER_SERVICE(parent) ); -- 1.7.7.6
>From 47dc4d7d2e085bdf153cbccc9adad1c4e7578293 Mon Sep 17 00:00:00 2001 From: Maksym Veremeyenko <ve...@m1stereo.tv> Date: Fri, 17 Feb 2012 16:17:42 +0200 Subject: [PATCH 2/2] save converted frame of pango producer --- src/modules/gtk2/producer_pango.c | 69 +++++++++++++++++++++++++++++++++---- 1 files changed, 62 insertions(+), 7 deletions(-) diff --git a/src/modules/gtk2/producer_pango.c b/src/modules/gtk2/producer_pango.c index ef4985c..12ee4cb 100644 --- a/src/modules/gtk2/producer_pango.c +++ b/src/modules/gtk2/producer_pango.c @@ -60,8 +60,24 @@ struct producer_pango_s int size; int style; int weight; + struct + { + uint8_t *image, *alpha; + int image_size, alpha_size; + mlt_image_format format; + } clone; }; +static void clean_clone( producer_pango self ) +{ + if ( self->clone.image ) + mlt_pool_release( self->clone.image ); + self->clone.image = NULL; + if ( self->clone.alpha ) + mlt_pool_release( self->clone.alpha ); + self->clone.alpha = NULL; +} + // special color type used by internal pango routines typedef struct { @@ -475,6 +491,7 @@ static void refresh_image( mlt_frame frame, int width, int height ) // Note - the original pixbuf is already safe and ready for destruction this->pixbuf = gdk_pixbuf_scale_simple( pixbuf, width, height, interp ); + clean_clone( this ); // Store width and height this->width = width; @@ -492,6 +509,7 @@ static int producer_get_image( mlt_frame frame, uint8_t **buffer, mlt_image_form { int error = 0; producer_pango this = ( producer_pango ) mlt_frame_pop_service( frame ); + mlt_image_format format_origin; // Obtain properties of frame mlt_properties properties = MLT_FRAME_PROPERTIES( frame ); @@ -508,18 +526,54 @@ static int producer_get_image( mlt_frame frame, uint8_t **buffer, mlt_image_form // Get width and height *width = this->width; *height = this->height; - *format = mlt_image_rgb24a; + format_origin = mlt_image_rgb24a; + if ( mlt_image_none == *format) + *format = format_origin; // Always clone here to allow 'animated' text if ( this->pixbuf ) { - // Clone the image - int image_size = this->width * this->height * 4; - *buffer = mlt_pool_alloc( image_size ); - memcpy( *buffer, gdk_pixbuf_get_pixels( this->pixbuf ), image_size ); + int size; + uint8_t* image; - // Now update properties so we free the copy after - mlt_frame_set_image( frame, *buffer, image_size, mlt_pool_release ); + if ( this->clone.image && this->clone.format == *format) + { + image = mlt_pool_alloc( this->clone.image_size ); + memcpy( image, this->clone.image, this->clone.image_size ); + mlt_frame_set_image( frame, image, this->clone.image_size, mlt_pool_release ); + *buffer = image; + if ( this->clone.alpha ) + { + image = mlt_pool_alloc( this->clone.alpha_size ); + memcpy( image, this->clone.alpha, this->clone.alpha_size ); + mlt_frame_set_alpha( frame, image, this->clone.alpha_size, mlt_pool_release ); + }; + } + else + { + clean_clone( this ); + size = this->width * this->height * 4; + image = mlt_pool_alloc( size ); + memcpy( image, gdk_pixbuf_get_pixels( this->pixbuf ), size ); + if(frame->convert_image && format_origin != *format) + { + frame->convert_image( frame, &image, &format_origin, *format ); + *format = format_origin; + } + mlt_frame_set_image( frame, image, size, mlt_pool_release ); + *buffer = image; + this->clone.format = *format; + this->clone.image_size = mlt_image_format_size( *format, *width, *height, NULL ); + this->clone.image = mlt_pool_alloc( this->clone.image_size ); + memcpy(this->clone.image, image, this->clone.image_size); + image = mlt_frame_get_alpha_mask(frame); + if ( image ) + { + this->clone.alpha_size = (*width) * (*height); + this->clone.alpha = mlt_pool_alloc( this->clone.alpha_size ); + memcpy(this->clone.alpha, image, this->clone.alpha_size); + }; + } } else { @@ -587,6 +641,7 @@ static void producer_close( mlt_producer parent ) free( this->text ); free( this->font ); free( this->family ); + clean_clone( this ); parent->close = NULL; mlt_producer_close( parent ); free( this ); -- 1.7.7.6
------------------------------------------------------------------------------ Virtualization & Cloud Management Using Capacity Planning Cloud computing makes use of virtualization - but cloud computing also focuses on allowing computing to be delivered as a service. http://www.accelacomm.com/jaw/sfnl/114/51521223/
_______________________________________________ Mlt-devel mailing list Mlt-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/mlt-devel