From 66efd2568e1002f11f19d2c672aaf090f7073192 Mon Sep 17 00:00:00 2001 From: Dan Dennedy Date: Thu, 7 Oct 2010 22:07:55 -0700 Subject: [PATCH] Move logic for when to auto-insert consumer producer. Move it into the loader producer so apps other than melt can use it too. To use it, an app must set the profile to explicit. --- src/melt/melt.c | 39 +++++----------------------- src/modules/core/producer_consumer.c | 2 ++ src/modules/core/producer_loader.c | 27 +++++++++++++++++++ src/modules/melt/producer_melt.c | 14 +--------- src/modules/xml/producer_xml.c | 2 ++ 5 files changed, 39 insertions(+), 45 deletions(-) diff --git a/src/melt/melt.c b/src/melt/melt.c index d518b88f..7541ae49 100644 --- a/src/melt/melt.c +++ b/src/melt/melt.c @@ -353,6 +353,7 @@ static void guess_profile( mlt_producer melt, mlt_profile profile ) mlt_frame_close( fr ); mlt_service_get_frame( MLT_PRODUCER_SERVICE(melt), &fr, 0 ); p = MLT_FRAME_PROPERTIES( fr ); +// mlt_properties_dump(p, stderr); if ( mlt_properties_get_int( p, "meta.media.frame_rate_den" ) && mlt_properties_get_int( p, "meta.media.sample_aspect_den" ) ) { profile->width = mlt_properties_get_int( p, "meta.media.width" ); @@ -364,6 +365,9 @@ static void guess_profile( mlt_producer melt, mlt_profile profile ) profile->sample_aspect_den = mlt_properties_get_int( p, "meta.media.sample_aspect_den" ); profile->display_aspect_num = (int) ( (double) profile->sample_aspect_num * profile->width / profile->sample_aspect_den + 0.5 ); profile->display_aspect_den = profile->height; + free( profile->description ); + profile->description = strdup( "automatic" ); + profile->is_explicit = 0; } } } @@ -429,10 +433,8 @@ int main( int argc, char **argv ) FILE *store = NULL; char *name = NULL; mlt_profile profile = NULL; - mlt_profile backup_profile = NULL; int is_progress = 0; int is_silent = 0; - int is_profile_explicit = 0; // Construct the factory mlt_repository repo = mlt_factory_init( NULL ); @@ -530,46 +532,20 @@ query_all: if ( profile == NULL ) profile = mlt_profile_init( NULL ); else - is_profile_explicit = 1; + profile->is_explicit = 1; // Look for the consumer option to load profile settings from consumer properties load_consumer( &consumer, profile, argc, argv ); - // Make backup of profile for determining if we need to use 'consumer' producer. - backup_profile = mlt_profile_init( NULL ); - memcpy( backup_profile, profile, sizeof( struct mlt_profile_s ) ); - backup_profile->description = strdup( "" ); - // Get melt producer if ( argc > 1 ) melt = mlt_factory_producer( profile, "melt", &argv[ 1 ] ); if ( melt ) { - // If the producer changed the profile then do not try to guess it. - if ( profile->width != backup_profile->width || - profile->height != backup_profile->height || - profile->sample_aspect_num != backup_profile->sample_aspect_num || - profile->sample_aspect_den != backup_profile->sample_aspect_den ) - { - if ( is_profile_explicit ) - { - // We need to use the 'consumer' producer. - mlt_producer_close( melt ); - mlt_profile_close( profile ); - profile = backup_profile; - backup_profile = NULL; - if ( profile->description ) - free( profile->description ); - // This is a hack to signal create_producer() in producer_melt.c. - profile->description = strdup( "consumer:" ); - melt = mlt_factory_producer( profile, "melt", &argv[ 1 ] ); - } - } - else if ( ! is_profile_explicit ) - { + // Generate an automatic profile if needed. + if ( ! profile->is_explicit ) guess_profile( melt, profile ); - } // Reload the consumer with the fully qualified profile load_consumer( &consumer, profile, argc, argv ); @@ -663,7 +639,6 @@ query_all: // Close the factory mlt_profile_close( profile ); - mlt_profile_close( backup_profile ); exit_factory: diff --git a/src/modules/core/producer_consumer.c b/src/modules/core/producer_consumer.c index 4803e96f..7cfd7e4a 100644 --- a/src/modules/core/producer_consumer.c +++ b/src/modules/core/producer_consumer.c @@ -104,11 +104,13 @@ static int get_frame( mlt_producer this, mlt_frame_ptr frame, int index ) { cx->profile = mlt_profile_init( profile_name ); cx->is_close_profile = 1; + cx->profile->is_explicit = 1; } else { cx->profile = profile; cx->is_close_profile = 0; + cx->profile->is_explicit = 0; } // For now, we must conform the nested network's frame rate to the parent network's diff --git a/src/modules/core/producer_loader.c b/src/modules/core/producer_loader.c index 4092bd1e..f97d2fd6 100644 --- a/src/modules/core/producer_loader.c +++ b/src/modules/core/producer_loader.c @@ -70,6 +70,9 @@ static mlt_producer create_producer( mlt_profile profile, char *file ) char *lookup = strdup( file ); char *p = lookup; + // Make backup of profile for determining if we need to use 'consumer' producer. + mlt_profile backup_profile = mlt_profile_clone( profile ); + // We only need to load the dictionary once if ( dictionary == NULL ) { @@ -92,8 +95,32 @@ static mlt_producer create_producer( mlt_profile profile, char *file ) char *name = mlt_properties_get_name( dictionary, i ); if ( fnmatch( name, lookup, 0 ) == 0 ) result = create_from( profile, file, mlt_properties_get_value( dictionary, i ) ); + } + + // Check if the producer changed the profile - xml does this. + if ( result && backup_profile->is_explicit && ( + profile->width != backup_profile->width || + profile->height != backup_profile->height || + profile->sample_aspect_num != backup_profile->sample_aspect_num || + profile->sample_aspect_den != backup_profile->sample_aspect_den ) ) + { + // Restore the original profile attributes. + profile->display_aspect_den = backup_profile->display_aspect_den; + profile->display_aspect_num = backup_profile->display_aspect_num; + profile->frame_rate_den = backup_profile->frame_rate_den; + profile->frame_rate_num = backup_profile->frame_rate_num; + profile->height = backup_profile->height; + profile->progressive = backup_profile->progressive; + profile->sample_aspect_den = backup_profile->sample_aspect_den; + profile->sample_aspect_num = backup_profile->sample_aspect_num; + profile->width = backup_profile->width; + + // Use the 'consumer' producer. + mlt_producer_close( result ); + result = mlt_factory_producer( profile, "consumer", file ); } + mlt_profile_close( backup_profile ); free( lookup ); } diff --git a/src/modules/melt/producer_melt.c b/src/modules/melt/producer_melt.c index ac425a62..05b571fa 100644 --- a/src/modules/melt/producer_melt.c +++ b/src/modules/melt/producer_melt.c @@ -69,19 +69,7 @@ static void track_service( mlt_field field, void *service, mlt_destructor destru static mlt_producer create_producer( mlt_profile profile, mlt_field field, char *file ) { - char *filedup; - if ( profile->description && strncmp( file, "consumer:", 9 ) && !strcmp( profile->description, "consumer:" ) ) - { - filedup = calloc( 1, strlen( file ) + strlen( profile->description ) + 1 ); - strcat( filedup, profile->description ); - strcat( filedup, file ); - } - else - { - filedup = strdup( file ); - } - mlt_producer result = mlt_factory_producer( profile, NULL, filedup ); - free( filedup ); + mlt_producer result = mlt_factory_producer( profile, NULL, file ); if ( result != NULL ) track_service( field, result, ( mlt_destructor )mlt_producer_close ); diff --git a/src/modules/xml/producer_xml.c b/src/modules/xml/producer_xml.c index b7c1fd6c..e5e15ad1 100644 --- a/src/modules/xml/producer_xml.c +++ b/src/modules/xml/producer_xml.c @@ -309,6 +309,7 @@ static void on_start_profile( deserialise_context context, const xmlChar *name, p->progressive = my_profile->progressive; p->sample_aspect_den = my_profile->sample_aspect_den; p->sample_aspect_num = my_profile->sample_aspect_num; + p->is_explicit = 1; mlt_profile_close( my_profile ); } } @@ -317,6 +318,7 @@ static void on_start_profile( deserialise_context context, const xmlChar *name, if ( p->description ) free( p->description ); p->description = strdup( _s(atts[ 1 ]) ); + p->is_explicit = 1; } else if ( xmlStrcmp( atts[ 0 ], _x("display_aspect_den") ) == 0 ) p->display_aspect_den = strtol( _s(atts[ 1 ]), NULL, 0 ); -- 2.39.2