static void plugin_mgr_get_path_plugins (plugin_mgr_t * plugin_mgr) { char * ladspa_path, * dir; ladspa_path = g_strdup (getenv ("LADSPA_PATH")); #ifdef WIN32 if (!ladspa_path) { ladspa_path = malloc (strlen (mlt_environment("MLT_APPDIR")) + strlen ("\\lib\\ladspa") + 1); strcpy (ladspa_path, mlt_environment("MLT_APPDIR")); strcat (ladspa_path, "\\lib\\ladspa"); } #elif defined(__DARWIN__) && defined(RELOCATABLE) { ladspa_path = malloc( strlen (mlt_environment ("MLT_APPDIR")) + strlen ("/lib/ladspa") + 1 ); strcpy (ladspa_path, mlt_environment ("MLT_APPDIR")); strcat (ladspa_path, "/lib/ladspa" ); } #else if (!ladspa_path) ladspa_path = g_strdup ("/usr/local/lib/ladspa:/usr/lib/ladspa:/usr/lib64/ladspa"); #endif for (dir = strtok (ladspa_path, ":"); dir; dir = strtok (NULL, ":")) plugin_mgr_get_dir_plugins (plugin_mgr, dir); g_free (ladspa_path); }
static mlt_filter obtain_filter( mlt_filter filter, char *type ) { // Result to return mlt_filter result = NULL; // Miscelaneous variable int i = 0; int type_len = strlen( type ); // Get the properties of the data show filter mlt_properties filter_properties = MLT_FILTER_PROPERTIES( filter ); // Get the profile properties mlt_properties profile_properties = mlt_properties_get_data( filter_properties, "profile_properties", NULL ); // Obtain the profile_properties if we haven't already if ( profile_properties == NULL ) { char temp[ 512 ]; // Get the profile requested char *profile = mlt_properties_get( filter_properties, "resource" ); // If none is specified, pick up the default for this normalisation if ( profile == NULL ) sprintf( temp, "%s/feeds/%s/data_fx.properties", mlt_environment( "MLT_DATA" ), mlt_environment( "MLT_NORMALISATION" ) ); else if ( strchr( profile, '%' ) ) sprintf( temp, "%s/feeds/%s/%s", mlt_environment( "MLT_DATA" ), mlt_environment( "MLT_NORMALISATION" ), strchr( profile, '%' ) + 1 ); else { strncpy( temp, profile, sizeof( temp ) ); temp[ sizeof( temp ) - 1 ] = '\0'; } // Load the specified profile or use the default profile_properties = mlt_properties_load( temp ); // Store for later retrieval mlt_properties_set_data( filter_properties, "profile_properties", profile_properties, 0, ( mlt_destructor )mlt_properties_close, NULL ); } if ( profile_properties != NULL ) { for ( i = 0; i < mlt_properties_count( profile_properties ); i ++ ) { char *name = mlt_properties_get_name( profile_properties, i ); char *value = mlt_properties_get_value( profile_properties, i ); if ( result == NULL && !strcmp( name, type ) && result == NULL ) result = mlt_factory_filter( mlt_service_profile( MLT_FILTER_SERVICE( filter ) ), value, NULL ); else if ( result != NULL && !strncmp( name, type, type_len ) && name[ type_len ] == '.' ) mlt_properties_set( MLT_FILTER_PROPERTIES( result ), name + type_len + 1, value ); else if ( result != NULL ) break; } } return result; }
void GlslManager::onInit( mlt_properties owner, GlslManager* filter ) { mlt_log_debug( filter->get_service(), "%s\n", __FUNCTION__ ); #ifdef WIN32 std::string path = std::string(mlt_environment("MLT_APPDIR")).append("\\share\\movit"); #elif defined(__DARWIN__) && defined(RELOCATABLE) std::string path = std::string(mlt_environment("MLT_APPDIR")).append("/share/movit"); #else std::string path = std::string(getenv("MLT_MOVIT_PATH") ? getenv("MLT_MOVIT_PATH") : SHADERDIR); #endif ::init_movit( path, mlt_log_get_level() == MLT_LOG_DEBUG? MOVIT_DEBUG_ON : MOVIT_DEBUG_OFF ); filter->set( "glsl_supported", movit_initialized ); }
mlt_transition transition_region_init( mlt_profile profile, mlt_service_type type, const char *id, char *arg ) { // Create a new transition mlt_transition transition = mlt_transition_new( ); // Further initialisation if ( transition != NULL ) { // Get the properties from the transition mlt_properties properties = MLT_TRANSITION_PROPERTIES( transition ); // Assign the transition process method transition->process = transition_process; // Default factory mlt_properties_set( properties, "factory", mlt_environment( "MLT_PRODUCER" ) ); // Resource defines the shape of the region mlt_properties_set( properties, "resource", arg == NULL ? "rectangle" : arg ); // Inform apps and framework that this is a video only transition mlt_properties_set_int( properties, "_transition_type", 1 ); } // Return the transition return transition; }
int mlt_consumer_init( mlt_consumer self, void *child, mlt_profile profile ) { int error = 0; memset( self, 0, sizeof( struct mlt_consumer_s ) ); self->child = child; error = mlt_service_init( &self->parent, self ); if ( error == 0 ) { // Get the properties from the service mlt_properties properties = MLT_SERVICE_PROPERTIES( &self->parent ); // Apply profile to properties if ( profile == NULL ) { // Normally the application creates the profile and controls its lifetime // This is the fallback exception handling profile = mlt_profile_init( NULL ); mlt_properties properties = MLT_CONSUMER_PROPERTIES( self ); mlt_properties_set_data( properties, "_profile", profile, 0, (mlt_destructor)mlt_profile_close, NULL ); } apply_profile_properties( self, profile, properties ); // Default rescaler for all consumers mlt_properties_set( properties, "rescale", "bilinear" ); // Default read ahead buffer size mlt_properties_set_int( properties, "buffer", 25 ); mlt_properties_set_int( properties, "drop_max", 5 ); // Default audio frequency and channels mlt_properties_set_int( properties, "frequency", 48000 ); mlt_properties_set_int( properties, "channels", 2 ); // Default of all consumers is real time mlt_properties_set_int( properties, "real_time", 1 ); // Default to environment test card mlt_properties_set( properties, "test_card", mlt_environment( "MLT_TEST_CARD" ) ); // Hmm - default all consumers to yuv422 :-/ self->format = mlt_image_yuv422; mlt_properties_set( properties, "mlt_image_format", mlt_image_format_name( self->format ) ); mlt_properties_set( properties, "mlt_audio_format", mlt_audio_format_name( mlt_audio_s16 ) ); mlt_events_register( properties, "consumer-frame-show", ( mlt_transmitter )mlt_consumer_frame_show ); mlt_events_register( properties, "consumer-frame-render", ( mlt_transmitter )mlt_consumer_frame_render ); mlt_events_register( properties, "consumer-stopped", NULL ); mlt_events_listen( properties, self, "consumer-frame-show", ( mlt_listener )on_consumer_frame_show ); // Register a property-changed listener to handle the profile property - // subsequent properties can override the profile self->event_listener = mlt_events_listen( properties, self, "property-changed", ( mlt_listener )mlt_consumer_property_changed ); // Create the push mutex and condition pthread_mutex_init( &self->put_mutex, NULL ); pthread_cond_init( &self->put_cond, NULL ); } return error; }
static char* get_frei0r_path() { #ifdef WIN32 char *dirname = malloc( strlen( mlt_environment( "MLT_APPDIR" ) ) + strlen( FREI0R_PLUGIN_PATH ) + 1 ); strcpy( dirname, mlt_environment( "MLT_APPDIR" ) ); strcat( dirname, FREI0R_PLUGIN_PATH ); return dirname; #elif defined(__DARWIN__) && defined(RELOCATABLE) char *dirname = malloc( strlen( mlt_environment( "MLT_APPDIR" ) ) + strlen( FREI0R_PLUGIN_PATH ) + 1 ); strcpy( dirname, mlt_environment( "MLT_APPDIR" ) ); strcat( dirname, FREI0R_PLUGIN_PATH ); return dirname; #else return strdup( GET_FREI0R_PATH ); #endif }
mlt_profile mlt_profile_load_file( const char *file ) { mlt_profile profile = NULL; // Load the profile as properties mlt_properties properties = mlt_properties_load( file ); if ( properties ) { // Simple check if the profile is valid if ( mlt_properties_get_int( properties, "width" ) ) { profile = mlt_profile_load_properties( properties ); // Set MLT_PROFILE to basename char *filename = strdup( file ); mlt_environment_set( "MLT_PROFILE", basename( filename ) ); set_mlt_normalisation( basename( filename ) ); free( filename ); } mlt_properties_close( properties ); } // Set MLT_NORMALISATION to appease legacy modules char *profile_name = mlt_environment( "MLT_PROFILE" ); set_mlt_normalisation( profile_name ); return profile; }
static void attach_normalisers( mlt_profile profile, mlt_producer producer ) { // Loop variable int i; // Tokeniser mlt_tokeniser tokeniser = mlt_tokeniser_init( ); // We only need to load the normalising properties once if ( normalisers == NULL ) { char temp[ 1024 ]; sprintf( temp, "%s/core/loader.ini", mlt_environment( "MLT_DATA" ) ); normalisers = mlt_properties_load( temp ); mlt_factory_register_for_clean_up( normalisers, ( mlt_destructor )mlt_properties_close ); } // Apply normalisers for ( i = 0; i < mlt_properties_count( normalisers ); i ++ ) { int j = 0; int created = 0; char *value = mlt_properties_get_value( normalisers, i ); mlt_tokeniser_parse_new( tokeniser, value, "," ); for ( j = 0; !created && j < mlt_tokeniser_count( tokeniser ); j ++ ) create_filter( profile, producer, mlt_tokeniser_get_string( tokeniser, j ), &created ); } // Close the tokeniser mlt_tokeniser_close( tokeniser ); }
ServiceManager::ServiceManager(mlt_service service) : service(service) , event(0) , effects(0) , imageProducers(0) { mlt_properties_set(MLT_SERVICE_PROPERTIES(service), "factory", mlt_environment("MLT_PRODUCER")); }
mlt_properties mlt_repository_presets( ) { mlt_properties result = mlt_properties_new(); char *path = getenv( "MLT_PRESETS_PATH" ); if ( path ) { path = strdup( path ); } else { path = malloc( strlen( mlt_environment( "MLT_DATA" ) ) + strlen( PRESETS_DIR ) + 1 ); strcpy( path, mlt_environment( "MLT_DATA" ) ); strcat( path, PRESETS_DIR ); } list_presets( result, NULL, path ); free( path ); return result; }
mlt_filter filter_watermark_init( mlt_profile profile, mlt_service_type type, const char *id, char *arg ) { mlt_filter filter = mlt_filter_new( ); if ( filter != NULL ) { mlt_properties properties = MLT_FILTER_PROPERTIES( filter ); filter->process = filter_process; mlt_properties_set( properties, "factory", mlt_environment( "MLT_PRODUCER" ) ); if ( arg != NULL ) mlt_properties_set( properties, "resource", arg ); // Ensure that attached filters are handled privately mlt_properties_set_int( properties, "_filter_private", 1 ); } return filter; }
static void check_thread_safe( mlt_properties properties, const char *name ) { char dirname[PATH_MAX]; snprintf( dirname, PATH_MAX, "%s/frei0r/not_thread_safe.txt", mlt_environment( "MLT_DATA" ) ); mlt_properties not_thread_safe = mlt_properties_load( dirname ); int i; for ( i = 0; i < mlt_properties_count( not_thread_safe ); i++ ) { if ( strcmp( name, mlt_properties_get_name( not_thread_safe, i ) ) == 0 ) { mlt_properties_set_int( properties, "_not_thread_safe", 1 ); break; } } mlt_properties_close( not_thread_safe ); }
mlt_properties mlt_profile_list( ) { char *filename = NULL; const char *prefix = getenv( "MLT_PROFILES_PATH" ); mlt_properties properties = mlt_properties_new(); mlt_properties dir = mlt_properties_new(); int sort = 1; const char *wildcard = NULL; int i; // Load from $datadir/mlt/profiles if no env var if ( prefix == NULL ) { prefix = mlt_environment( "MLT_DATA" ); filename = calloc( 1, strlen( prefix ) + strlen( PROFILES_DIR ) + 1 ); strcpy( filename, prefix ); strcat( filename, PROFILES_DIR ); prefix = filename; } mlt_properties_dir_list( dir, prefix, wildcard, sort ); for ( i = 0; i < mlt_properties_count( dir ); i++ ) { char *filename = mlt_properties_get_value( dir, i ); char *profile_name = basename( filename ); if ( profile_name[0] != '.' && strcmp( profile_name, "Makefile" ) && profile_name[ strlen( profile_name ) - 1 ] != '~' ) { mlt_properties profile = mlt_properties_load( filename ); if ( profile ) { mlt_properties_set_data( properties, profile_name, profile, 0, (mlt_destructor) mlt_properties_close, NULL ); } } } mlt_properties_close( dir ); if ( filename ) free( filename ); return properties; }
static mlt_profile mlt_profile_select( const char *name ) { char *filename = NULL; const char *prefix = getenv( "MLT_PROFILES_PATH" ); mlt_properties properties = mlt_properties_load( name ); mlt_profile profile = NULL; // Try to load from file specification if ( properties && mlt_properties_get_int( properties, "width" ) ) { filename = calloc( 1, strlen( name ) + 1 ); } // Load from $datadir/mlt/profiles else if ( prefix == NULL ) { prefix = mlt_environment( "MLT_DATA" ); filename = calloc( 1, strlen( prefix ) + strlen( PROFILES_DIR ) + strlen( name ) + 1 ); strcpy( filename, prefix ); strcat( filename, PROFILES_DIR ); } // Use environment variable instead else { filename = calloc( 1, strlen( prefix ) + strlen( name ) + 2 ); strcpy( filename, prefix ); if ( filename[ strlen( filename ) - 1 ] != '/' ) filename[ strlen( filename ) ] = '/'; } // Finish loading strcat( filename, name ); profile = mlt_profile_load_file( filename ); // Cleanup mlt_properties_close( properties ); free( filename ); return profile; }
plugin_mgr_t * plugin_mgr_new () { plugin_mgr_t * pm; char dirname[PATH_MAX]; pm = g_malloc (sizeof (plugin_mgr_t)); pm->all_plugins = NULL; pm->plugins = NULL; pm->plugin_count = 0; snprintf (dirname, PATH_MAX, "%s/jackrack/blacklist.txt", mlt_environment ("MLT_DATA")); pm->blacklist = mlt_properties_load (dirname); plugin_mgr_get_path_plugins (pm); if (!pm->all_plugins) mlt_log_warning( NULL, "No LADSPA plugins were found!\n\nCheck your LADSPA_PATH environment variable.\n"); else pm->all_plugins = g_slist_sort (pm->all_plugins, plugin_mgr_sort); return pm; }
mlt_consumer mlt_factory_consumer( mlt_profile profile, const char *service, const void *input ) { mlt_consumer obj = NULL; if ( service == NULL ) service = mlt_environment( "MLT_CONSUMER" ); // Offer the application the chance to 'create' mlt_events_fire( event_object, "consumer-create-request", service, input, &obj, NULL ); if ( obj == NULL ) { obj = mlt_repository_create( repository, profile, consumer_type, service, input ); mlt_events_fire( event_object, "consumer-create-done", service, input, obj, NULL ); } if ( obj != NULL ) { mlt_properties properties = MLT_CONSUMER_PROPERTIES( obj ); set_common_properties( properties, profile, "consumer", service ); } return obj; }
static mlt_properties metadata( mlt_service_type type, const char *id, void *data ) { char file[ PATH_MAX ]; mlt_properties result = NULL; // Load the yaml file snprintf( file, PATH_MAX, "%s/sox/filter_%s.yml", mlt_environment( "MLT_DATA" ), strcmp( id, "sox" ) ? "sox_effect" : "sox" ); result = mlt_properties_parse_yaml( file ); #ifdef SOX14 if ( result && ( type == filter_type ) && strcmp( id, "sox" ) ) { // Annotate the yaml properties with sox effect usage. mlt_properties params = mlt_properties_get_data( result, "parameters", NULL ); const sox_effect_handler_t *e; int i; for ( i = 0; sox_effect_fns[i]; i++ ) { e = sox_effect_fns[i](); if ( e && e->name && !strcmp( e->name, id + 4 ) ) { mlt_properties p = mlt_properties_get_data( params, "0", NULL ); mlt_properties_set( result, "identifier", e->name ); mlt_properties_set( result, "title", e->name ); mlt_properties_set( p, "type", "string" ); mlt_properties_set( p, "title", "Options" ); if ( e->usage ) mlt_properties_set( p, "format", e->usage ); break; } } } #endif return result; }
mlt_producer mlt_factory_producer( mlt_profile profile, const char *service, const void *resource ) { mlt_producer obj = NULL; // Pick up the default normalising producer if necessary if ( service == NULL ) service = mlt_environment( "MLT_PRODUCER" ); // Offer the application the chance to 'create' mlt_events_fire( event_object, "producer-create-request", service, resource, &obj, NULL ); // Try to instantiate via the specified service if ( obj == NULL ) { obj = mlt_repository_create( repository, profile, producer_type, service, resource ); mlt_events_fire( event_object, "producer-create-done", service, resource, obj, NULL ); if ( obj != NULL ) { mlt_properties properties = MLT_PRODUCER_PROPERTIES( obj ); set_common_properties( properties, profile, "producer", service ); } } return obj; }
static mlt_frame get_background_frame( mlt_producer producer ) { mlt_properties producer_properties = MLT_PRODUCER_PROPERTIES( producer ); mlt_frame bg_frame = NULL; mlt_producer color_producer = mlt_properties_get_data( producer_properties, "_color_producer", NULL ); if( !color_producer ) { mlt_profile profile = mlt_service_profile( MLT_PRODUCER_SERVICE( producer ) ); color_producer = mlt_factory_producer( profile, mlt_environment( "MLT_PRODUCER" ), "colour:" ); mlt_properties_set_data( producer_properties, "_color_producer", color_producer, 0, ( mlt_destructor )mlt_producer_close, NULL ); mlt_properties color_properties = MLT_PRODUCER_PROPERTIES( color_producer ); mlt_properties_set( color_properties, "colour", FRAME_BACKGROUND_COLOR ); } if( color_producer ) { mlt_producer_seek( color_producer, 0 ); mlt_service_get_frame( MLT_PRODUCER_SERVICE( color_producer ), &bg_frame, 0 ); } return bg_frame; }
static mlt_properties metadata( mlt_service_type type, const char *id, char *data ) { char file[ PATH_MAX ]; if( type == filter_type ) { snprintf( file, PATH_MAX, "%s/jackrack/%s", mlt_environment( "MLT_DATA" ), strncmp( id, "ladspa.", 7 ) ? data : "filter_ladspa.yml" ); } else { snprintf( file, PATH_MAX, "%s/jackrack/%s", mlt_environment( "MLT_DATA" ), strncmp( id, "ladspa.", 7 ) ? data : "producer_ladspa.yml" ); } mlt_properties result = mlt_properties_parse_yaml( file ); #ifdef GPL if ( !strncmp( id, "ladspa.", 7 ) ) { // Annotate the yaml properties with ladspa control port info. plugin_desc_t *desc = plugin_mgr_get_any_desc( g_jackrack_plugin_mgr, strtol( id + 7, NULL, 10 ) ); if ( desc ) { mlt_properties params = mlt_properties_new(); mlt_properties p; char key[20]; int i; mlt_properties_set( result, "identifier", id ); mlt_properties_set( result, "title", desc->name ); mlt_properties_set( result, "creator", desc->maker ? desc->maker : "unknown" ); mlt_properties_set( result, "description", "LADSPA plugin" ); mlt_properties_set_data( result, "parameters", params, 0, (mlt_destructor) mlt_properties_close, NULL ); for ( i = 0; i < desc->control_port_count; i++ ) { int j = desc->control_port_indicies[i]; LADSPA_Data sample_rate = 48000; LADSPA_PortRangeHintDescriptor hint_descriptor = desc->port_range_hints[j].HintDescriptor; p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", i ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); snprintf( key, sizeof(key), "%d", j ); mlt_properties_set( p, "identifier", key ); mlt_properties_set( p, "title", desc->port_names[ j ] ); if ( LADSPA_IS_HINT_INTEGER( hint_descriptor ) ) { mlt_properties_set( p, "type", "integer" ); mlt_properties_set_int( p, "default", plugin_desc_get_default_control_value( desc, j, sample_rate ) ); } else if ( LADSPA_IS_HINT_TOGGLED( hint_descriptor ) ) { mlt_properties_set( p, "type", "boolean" ); mlt_properties_set_int( p, "default", plugin_desc_get_default_control_value( desc, j, sample_rate ) ); } else { mlt_properties_set( p, "type", "float" ); mlt_properties_set_double( p, "default", plugin_desc_get_default_control_value( desc, j, sample_rate ) ); } /* set upper and lower, possibly adjusted to the sample rate */ if ( LADSPA_IS_HINT_BOUNDED_BELOW( hint_descriptor ) ) { LADSPA_Data lower = desc->port_range_hints[j].LowerBound; if ( LADSPA_IS_HINT_SAMPLE_RATE( hint_descriptor ) ) lower *= sample_rate; if ( LADSPA_IS_HINT_LOGARITHMIC( hint_descriptor ) ) { if (lower < FLT_EPSILON) lower = FLT_EPSILON; } mlt_properties_set_double( p, "minimum", lower ); } if ( LADSPA_IS_HINT_BOUNDED_ABOVE( hint_descriptor ) ) { LADSPA_Data upper = desc->port_range_hints[j].UpperBound; if ( LADSPA_IS_HINT_SAMPLE_RATE( hint_descriptor ) ) upper *= sample_rate; mlt_properties_set_double( p, "maximum", upper ); } if ( LADSPA_IS_HINT_LOGARITHMIC( hint_descriptor ) ) mlt_properties_set( p, "scale", "log" ); mlt_properties_set( p, "mutable", "yes" ); } if( type == filter_type ) { p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", i ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); mlt_properties_set( p, "identifier", "wetness" ); mlt_properties_set( p, "title", "Wet/Dry" ); mlt_properties_set( p, "type", "float" ); mlt_properties_set_double( p, "default", 1 ); mlt_properties_set_double( p, "minimum", 0 ); mlt_properties_set_double( p, "maximum", 1 ); mlt_properties_set( p, "mutable", "yes" ); } } } #endif return result; }
static mlt_properties metadata( mlt_service_type type, const char *id, void *data ) { char file[ PATH_MAX ]; snprintf( file, PATH_MAX, "%s/opengl/%s", mlt_environment( "MLT_DATA" ), (char*) data ); return mlt_properties_parse_yaml( file ); }
static mlt_properties avformat_metadata( mlt_service_type type, const char *id, void *data ) { char file[ PATH_MAX ]; const char *service_type = NULL; mlt_properties result = NULL; // Convert the service type to a string. switch ( type ) { case consumer_type: service_type = "consumer"; break; case filter_type: service_type = "filter"; break; case producer_type: service_type = "producer"; break; case transition_type: service_type = "transition"; break; default: return NULL; } // Load the yaml file snprintf( file, PATH_MAX, "%s/avformat/%s_%s.yml", mlt_environment( "MLT_DATA" ), service_type, id ); result = mlt_properties_parse_yaml( file ); if ( result && ( type == consumer_type || type == producer_type ) ) { // Annotate the yaml properties with AVOptions. mlt_properties params = (mlt_properties) mlt_properties_get_data( result, "parameters", NULL ); AVFormatContext *avformat = avformat_alloc_context(); #if LIBAVCODEC_VERSION_INT > ((53<<16)+(8<<8)+0) AVCodecContext *avcodec = avcodec_alloc_context3( NULL ); #else AVCodecContext *avcodec = avcodec_alloc_context(); #endif int flags = ( type == consumer_type )? AV_OPT_FLAG_ENCODING_PARAM : AV_OPT_FLAG_DECODING_PARAM; add_parameters( params, avformat, flags, NULL, NULL ); #if LIBAVFORMAT_VERSION_MAJOR >= 53 avformat_init(); if ( type == producer_type ) { AVInputFormat *f = NULL; while ( ( f = av_iformat_next( f ) ) ) if ( f->priv_class ) add_parameters( params, &f->priv_class, flags, NULL, f->name ); } else { AVOutputFormat *f = NULL; while ( ( f = av_oformat_next( f ) ) ) if ( f->priv_class ) add_parameters( params, &f->priv_class, flags, NULL, f->name ); } #endif add_parameters( params, avcodec, flags, NULL, NULL ); #if LIBAVCODEC_VERSION_MAJOR >= 53 AVCodec *c = NULL; while ( ( c = av_codec_next( c ) ) ) if ( c->priv_class ) add_parameters( params, &c->priv_class, flags, NULL, c->name ); #endif av_free( avformat ); av_free( avcodec ); } return result; }
static mlt_properties fill_param_info ( mlt_service_type type, const char *service_name, char *name ) { char file[ PATH_MAX ]; char servicetype[ 1024 ]=""; struct stat stat_buff; switch ( type ) { case producer_type: strcpy ( servicetype , "producer" ); break; case filter_type: strcpy ( servicetype , "filter" ); break; case transition_type: strcpy ( servicetype , "transition" ) ; break; default: strcpy ( servicetype , "" ); }; snprintf( file, PATH_MAX, "%s/frei0r/%s_%s.yml", mlt_environment( "MLT_DATA" ), servicetype, service_name ); stat(file,&stat_buff); if (S_ISREG(stat_buff.st_mode)){ return mlt_properties_parse_yaml( file ); } void* handle=dlopen(name,RTLD_LAZY); if (!handle) return NULL; void (*plginfo)(f0r_plugin_info_t*)=dlsym(handle,"f0r_get_plugin_info"); void (*param_info)(f0r_param_info_t*,int param_index)=dlsym(handle,"f0r_get_param_info"); if (!plginfo || !param_info) { dlclose(handle); return NULL; } mlt_properties metadata = mlt_properties_new(); f0r_plugin_info_t info; char string[48]; int j=0; plginfo(&info); snprintf ( string, sizeof(string) , "%d.%d" , info.major_version , info.minor_version ); mlt_properties_set ( metadata, "schema_version" , "0.1" ); mlt_properties_set ( metadata, "title" , info.name ); mlt_properties_set ( metadata, "version", string ); mlt_properties_set ( metadata, "identifier" , service_name ); mlt_properties_set ( metadata, "description" , info.explanation ); mlt_properties_set ( metadata, "creator" , info.author ); switch (type){ case producer_type: mlt_properties_set ( metadata, "type" , "producer" ); break; case filter_type: mlt_properties_set ( metadata, "type" , "filter" ); break; case transition_type: mlt_properties_set ( metadata, "type" , "transition" ); break; default: break; } mlt_properties parameter = mlt_properties_new ( ); mlt_properties_set_data ( metadata , "parameters" , parameter , 0 , ( mlt_destructor )mlt_properties_close, NULL ); mlt_properties tags = mlt_properties_new ( ); mlt_properties_set_data ( metadata , "tags" , tags , 0 , ( mlt_destructor )mlt_properties_close, NULL ); mlt_properties_set ( tags , "0" , "Video" ); for (j=0;j<info.num_params;j++){ snprintf ( string , sizeof(string), "%d" , j ); mlt_properties pnum = mlt_properties_new ( ); mlt_properties_set_data ( parameter , string , pnum , 0 , ( mlt_destructor )mlt_properties_close, NULL ); f0r_param_info_t paraminfo; param_info(¶minfo,j); mlt_properties_set ( pnum , "identifier" , paraminfo.name ); mlt_properties_set ( pnum , "title" , paraminfo.name ); mlt_properties_set ( pnum , "description" , paraminfo.explanation); if ( paraminfo.type == F0R_PARAM_DOUBLE ){ mlt_properties_set ( pnum , "type" , "float" ); mlt_properties_set ( pnum , "minimum" , "0" ); mlt_properties_set ( pnum , "maximum" , "1" ); mlt_properties_set ( pnum , "readonly" , "no" ); mlt_properties_set ( pnum , "widget" , "spinner" ); }else if ( paraminfo.type == F0R_PARAM_BOOL ){ mlt_properties_set ( pnum , "type" , "boolean" ); mlt_properties_set ( pnum , "minimum" , "0" ); mlt_properties_set ( pnum , "maximum" , "1" ); mlt_properties_set ( pnum , "readonly" , "no" ); }else if ( paraminfo.type == F0R_PARAM_COLOR ){ mlt_properties_set ( pnum , "type" , "color" ); mlt_properties_set ( pnum , "readonly" , "no" ); }else if ( paraminfo.type == F0R_PARAM_STRING ){ mlt_properties_set ( pnum , "type" , "string" ); mlt_properties_set ( pnum , "readonly" , "no" ); } } dlclose(handle); free(name); return metadata; }
} static int filter_get_image( mlt_frame this, uint8_t **image, mlt_image_format *format, int *width, int *height, int writable ) { mlt_filter filter = mlt_frame_pop_service( this ); int maxdia = mlt_properties_get_int( MLT_FILTER_PROPERTIES( filter ), "maxdiameter" ); int maxcount = mlt_properties_get_int( MLT_FILTER_PROPERTIES( filter ), "maxcount" ); *format = mlt_image_yuv422; int error = mlt_frame_get_image( this, image, format, width, height, 1 ); // load svg mlt_properties properties = MLT_FILTER_PROPERTIES( filter ); char *factory = mlt_properties_get( properties, "factory" ); char temp[1204]=""; sprintf( temp, "%s/oldfilm/", mlt_environment( "MLT_DATA" ) ); mlt_properties direntries=mlt_properties_new(); mlt_properties_dir_list(direntries,temp,"dust*.svg",1); if (!maxcount) return 0; double position = mlt_filter_get_progress( filter, this ); srand(position*10000); mlt_service_lock( MLT_FILTER_SERVICE( filter ) ); int im=rand()%maxcount; int piccount=mlt_properties_count(direntries); while (im-- && piccount){
mlt_repository mlt_repository_init( const char *directory ) { // Safety check if ( directory == NULL || strcmp( directory, "" ) == 0 ) return NULL; // Construct the repository mlt_repository self = calloc( 1, sizeof( struct mlt_repository_s )); mlt_properties_init( &self->parent, self ); self->consumers = mlt_properties_new(); self->filters = mlt_properties_new(); self->producers = mlt_properties_new(); self->transitions = mlt_properties_new(); // Get the directory list mlt_properties dir = mlt_properties_new(); int count = mlt_properties_dir_list( dir, directory, NULL, 0 ); int i; #ifdef WIN32 char *syspath = getenv("PATH"); char *exedir = mlt_environment( "MLT_APPDIR" ); char *newpath = "PATH="; newpath = calloc( 1, strlen( newpath )+ strlen( exedir ) + 1 + strlen( syspath ) + 1 ); strcat( newpath, "PATH=" ); strcat( newpath, exedir ); strcat( newpath, ";" ); strcat( newpath, syspath ); putenv(newpath); #endif // Iterate over files for ( i = 0; i < count; i++ ) { int flags = RTLD_NOW; const char *object_name = mlt_properties_get_value( dir, i); // Very temporary hack to allow the quicktime plugins to work // TODO: extend repository to allow this to be used on a case by case basis if ( strstr( object_name, "libmltkino" ) ) flags |= RTLD_GLOBAL; // Open the shared object void *object = dlopen( object_name, flags ); if ( object != NULL ) { // Get the registration function mlt_repository_callback symbol_ptr = dlsym( object, "mlt_register" ); // Call the registration function if ( symbol_ptr != NULL ) { symbol_ptr( self ); // Register the object file for closure mlt_properties_set_data( &self->parent, object_name, object, 0, ( mlt_destructor )dlclose, NULL ); } else { dlclose( object ); } } else if ( strstr( object_name, "libmlt" ) ) { mlt_log( NULL, MLT_LOG_WARNING, "%s: failed to dlopen %s\n (%s)\n", __FUNCTION__, object_name, dlerror() ); } } mlt_properties_close( dir ); return self; }
static mlt_properties videostab_metadata( mlt_service_type type, const char *id, void *data ) { char file[ PATH_MAX ]; snprintf( file, PATH_MAX, "%s/videostab/filter_%s.yml", mlt_environment( "MLT_DATA" ), id ); return mlt_properties_parse_yaml( file ); }
/** Constructor for the filter. */ mlt_filter filter_dynamictext_init( mlt_profile profile, mlt_service_type type, const char *id, char *arg ) { mlt_filter filter = mlt_filter_new(); mlt_transition transition = mlt_factory_transition( profile, "composite", NULL ); mlt_producer producer = mlt_factory_producer( profile, mlt_environment( "MLT_PRODUCER" ), "qtext:" ); // Use pango if qtext is not available. if( !producer ) producer = mlt_factory_producer( profile, mlt_environment( "MLT_PRODUCER" ), "pango:" ); if ( filter && transition && producer ) { mlt_properties my_properties = MLT_FILTER_PROPERTIES( filter ); // Register the transition for reuse/destruction mlt_properties_set_data( my_properties, "_transition", transition, 0, ( mlt_destructor )mlt_transition_close, NULL ); // Register the producer for reuse/destruction mlt_properties_set_data( my_properties, "_producer", producer, 0, ( mlt_destructor )mlt_producer_close, NULL ); // Ensure that we loop mlt_properties_set( MLT_PRODUCER_PROPERTIES( producer ), "eof", "loop" ); // Assign default values mlt_properties_set( my_properties, "argument", arg ? arg: "#timecode#" ); mlt_properties_set( my_properties, "geometry", "0%/0%:100%x100%:100" ); mlt_properties_set( my_properties, "family", "Sans" ); mlt_properties_set( my_properties, "size", "48" ); mlt_properties_set( my_properties, "weight", "400" ); mlt_properties_set( my_properties, "fgcolour", "0x000000ff" ); mlt_properties_set( my_properties, "bgcolour", "0x00000020" ); mlt_properties_set( my_properties, "olcolour", "0x00000000" ); mlt_properties_set( my_properties, "pad", "0" ); mlt_properties_set( my_properties, "halign", "left" ); mlt_properties_set( my_properties, "valign", "top" ); mlt_properties_set( my_properties, "outline", "0" ); mlt_properties_set_int( my_properties, "_filter_private", 1 ); filter->process = filter_process; } else { if( filter ) { mlt_filter_close( filter ); } if( transition ) { mlt_transition_close( transition ); } if( producer ) { mlt_producer_close( producer ); } filter = NULL; } return filter; }
static mlt_properties fill_param_info ( mlt_service_type type, const char *service_name, char *name ) { char file[ PATH_MAX ]; char servicetype[ 1024 ]=""; struct stat stat_buff; switch ( type ) { case producer_type: strcpy ( servicetype , "producer" ); break; case filter_type: strcpy ( servicetype , "filter" ); break; case transition_type: strcpy ( servicetype , "transition" ) ; break; default: strcpy ( servicetype , "" ); }; snprintf( file, PATH_MAX, "%s/frei0r/%s_%s.yml", mlt_environment( "MLT_DATA" ), servicetype, service_name ); memset(&stat_buff, 0, sizeof(stat_buff)); stat(file,&stat_buff); if (S_ISREG(stat_buff.st_mode)){ return mlt_properties_parse_yaml( file ); } void* handle=dlopen(name,RTLD_LAZY); if (!handle) return NULL; void (*plginfo)(f0r_plugin_info_t*)=dlsym(handle,"f0r_get_plugin_info"); void (*param_info)(f0r_param_info_t*,int param_index)=dlsym(handle,"f0r_get_param_info"); void (*f0r_init)(void)=dlsym(handle,"f0r_init"); void (*f0r_deinit)(void)=dlsym(handle,"f0r_deinit"); f0r_instance_t (*f0r_construct)(unsigned int , unsigned int)=dlsym(handle, "f0r_construct"); void (*f0r_destruct)(f0r_instance_t)=dlsym(handle, "f0r_destruct"); void (*f0r_get_param_value)(f0r_instance_t instance, f0r_param_t param, int param_index)=dlsym(handle,"f0r_get_param_value" ); if (!plginfo || !param_info) { dlclose(handle); return NULL; } mlt_properties metadata = mlt_properties_new(); f0r_plugin_info_t info; char string[48]; int j=0; f0r_init(); f0r_instance_t instance = f0r_construct(720, 576); if (!instance) { f0r_deinit(); dlclose(handle); mlt_properties_close(metadata); return NULL; } plginfo(&info); snprintf ( string, sizeof(string) , "%d" , info.minor_version ); mlt_properties_set_double ( metadata, "schema_version" , 0.1 ); mlt_properties_set ( metadata, "title" , info.name ); mlt_properties_set_double ( metadata, "version", info.major_version + info.minor_version / pow( 10, strlen( string ) ) ); mlt_properties_set ( metadata, "identifier" , service_name ); mlt_properties_set ( metadata, "description" , info.explanation ); mlt_properties_set ( metadata, "creator" , info.author ); switch (type){ case producer_type: mlt_properties_set ( metadata, "type" , "producer" ); break; case filter_type: mlt_properties_set ( metadata, "type" , "filter" ); break; case transition_type: mlt_properties_set ( metadata, "type" , "transition" ); break; default: break; } mlt_properties tags = mlt_properties_new ( ); mlt_properties_set_data ( metadata , "tags" , tags , 0 , ( mlt_destructor )mlt_properties_close, NULL ); mlt_properties_set ( tags , "0" , "Video" ); mlt_properties parameter = mlt_properties_new ( ); mlt_properties_set_data ( metadata , "parameters" , parameter , 0 , ( mlt_destructor )mlt_properties_close, NULL ); for (j=0;j<info.num_params;j++){ snprintf ( string , sizeof(string), "%d" , j ); mlt_properties pnum = mlt_properties_new ( ); mlt_properties_set_data ( parameter , string , pnum , 0 , ( mlt_destructor )mlt_properties_close, NULL ); f0r_param_info_t paraminfo; param_info(¶minfo,j); mlt_properties_set ( pnum , "identifier" , string ); mlt_properties_set ( pnum , "title" , paraminfo.name ); mlt_properties_set ( pnum , "description" , paraminfo.explanation); if ( paraminfo.type == F0R_PARAM_DOUBLE ){ double deflt = 0; mlt_properties_set ( pnum , "type" , "float" ); mlt_properties_set ( pnum , "minimum" , "0" ); mlt_properties_set ( pnum , "maximum" , "1" ); f0r_get_param_value( instance, &deflt, j); mlt_properties_set_double ( pnum, "default", CLAMP(deflt, 0.0, 1.0) ); mlt_properties_set ( pnum , "mutable" , "yes" ); mlt_properties_set ( pnum , "widget" , "spinner" ); }else if ( paraminfo.type == F0R_PARAM_BOOL ){ double deflt = 0; mlt_properties_set ( pnum , "type" , "boolean" ); mlt_properties_set ( pnum , "minimum" , "0" ); mlt_properties_set ( pnum , "maximum" , "1" ); f0r_get_param_value( instance, &deflt, j); mlt_properties_set_int ( pnum, "default", deflt != 0.0 ); mlt_properties_set ( pnum , "mutable" , "yes" ); mlt_properties_set ( pnum , "widget" , "checkbox" ); }else if ( paraminfo.type == F0R_PARAM_COLOR ){ char colorstr[8]; f0r_param_color_t deflt = {0, 0, 0}; mlt_properties_set ( pnum , "type" , "color" ); f0r_get_param_value( instance, &deflt, j); sprintf( colorstr, "#%02x%02x%02x", (unsigned) CLAMP(deflt.r * 255, 0 , 255), (unsigned) CLAMP(deflt.g * 255, 0 , 255), (unsigned) CLAMP(deflt.b * 255, 0 , 255)); colorstr[7] = 0; mlt_properties_set ( pnum , "default", colorstr ); mlt_properties_set ( pnum , "mutable" , "yes" ); mlt_properties_set ( pnum , "widget" , "color" ); }else if ( paraminfo.type == F0R_PARAM_STRING ){ char *deflt = NULL; mlt_properties_set ( pnum , "type" , "string" ); f0r_get_param_value( instance, &deflt, j ); mlt_properties_set ( pnum , "default", deflt ); mlt_properties_set ( pnum , "mutable" , "yes" ); mlt_properties_set ( pnum , "widget" , "text" ); } } f0r_destruct(instance); f0r_deinit(); dlclose(handle); free(name); return metadata; }
static int filter_get_image( mlt_frame frame, uint8_t **image, mlt_image_format *format, int *width, int *height, int writable ) { mlt_filter filter = (mlt_filter) mlt_frame_pop_service( frame ); mlt_properties properties = MLT_FILTER_PROPERTIES( filter ); mlt_position pos = mlt_filter_get_position( filter, frame ); mlt_position len = mlt_filter_get_length2( filter, frame ); int maxdia = mlt_properties_anim_get_int( properties, "maxdiameter", pos, len ); int maxcount = mlt_properties_anim_get_int( properties, "maxcount", pos, len ); *format = mlt_image_yuv422; int error = mlt_frame_get_image( frame, image, format, width, height, 1 ); // Load svg char *factory = mlt_properties_get( properties, "factory" ); char temp[1204] = ""; sprintf( temp, "%s/oldfilm/", mlt_environment( "MLT_DATA" ) ); mlt_properties direntries = mlt_properties_new(); mlt_properties_dir_list( direntries, temp,"dust*.svg",1 ); if (!maxcount) return 0; double position = mlt_filter_get_progress( filter, frame ); srand( position * 10000 ); mlt_service_lock( MLT_FILTER_SERVICE( filter ) ); int im = rand() % maxcount; int piccount = mlt_properties_count( direntries ); while ( im-- && piccount ) { int picnum = rand() % piccount; int y1 = rand() % *height; int x1 = rand() % *width; char resource[1024] = ""; char savename[1024] = "", savename1[1024] = "", cachedy[100]; int dx = ( *width * maxdia / 100); int luma_width, luma_height; uint8_t *luma_image = NULL; uint8_t *alpha = NULL; int updown = rand() % 2; int mirror = rand() % 2; sprintf( resource, "%s", mlt_properties_get_value(direntries,picnum) ); sprintf( savename, "cache-%d-%d", picnum,dx ); sprintf( savename1, "cache-alpha-%d-%d", picnum, dx ); sprintf( cachedy, "cache-dy-%d-%d", picnum,dx ); luma_image = mlt_properties_get_data( properties , savename , NULL ); alpha = mlt_properties_get_data( properties , savename1 , NULL ); if ( luma_image == NULL || alpha == NULL ) { mlt_profile profile = mlt_service_profile( MLT_FILTER_SERVICE( filter ) ); mlt_producer producer = mlt_factory_producer( profile, factory, resource ); if ( producer != NULL ) { mlt_properties producer_properties = MLT_PRODUCER_PROPERTIES( producer ); mlt_properties_set( producer_properties, "eof", "loop" ); mlt_frame luma_frame = NULL; if ( mlt_service_get_frame( MLT_PRODUCER_SERVICE( producer ), &luma_frame, 0 ) == 0 ) { mlt_image_format luma_format = mlt_image_yuv422; luma_width = dx; luma_height = luma_width * mlt_properties_get_int( MLT_FRAME_PROPERTIES ( luma_frame ) , "height" ) / mlt_properties_get_int( MLT_FRAME_PROPERTIES ( luma_frame ) , "width" ); mlt_properties_set( MLT_FRAME_PROPERTIES( luma_frame ), "rescale.interp", "best" );// none/nearest/tiles/hyper mlt_frame_get_image( luma_frame, &luma_image, &luma_format, &luma_width, &luma_height, 0 ); alpha = mlt_frame_get_alpha_mask (luma_frame ); uint8_t* savealpha = mlt_pool_alloc( luma_width * luma_height ); uint8_t* savepic = mlt_pool_alloc( luma_width * luma_height * 2); if ( savealpha && savepic ) { memcpy( savealpha, alpha , luma_width * luma_height ); memcpy( savepic, luma_image , luma_width * luma_height * 2 ); mlt_properties_set_data( properties, savename, savepic, luma_width * luma_height * 2, mlt_pool_release, NULL ); mlt_properties_set_data( properties, savename1, savealpha, luma_width * luma_height, mlt_pool_release, NULL ); mlt_properties_set_int( properties, cachedy, luma_height ); overlay_image( *image, *width, *height, luma_image, luma_width, luma_height, alpha, x1, y1, updown, mirror ); } else { if ( savealpha ) mlt_pool_release( savealpha ); if ( savepic ) mlt_pool_release( savepic ); } mlt_frame_close( luma_frame ); } mlt_producer_close( producer ); } } else { overlay_image ( *image, *width, *height, luma_image, dx, mlt_properties_get_int ( properties, cachedy ), alpha, x1, y1, updown, mirror ); } } mlt_service_unlock( MLT_FILTER_SERVICE( filter ) ); if (piccount>0 ) return 0; if ( error == 0 && *image ) { int h = *height; int w = *width; int im = rand() % maxcount; while ( im-- ) { int type = im % 2; int y1 = rand() % h; int x1 = rand() % w; int dx = rand() % maxdia; int dy = rand() % maxdia; int x=0, y=0; double v = 0.0; for ( x = -dx ; x < dx ; x++ ) { for ( y = -dy ; y < dy ; y++ ) { if ( x1 + x < w && x1 + x > 0 && y1 + y < h && y1 + y > 0 ){ uint8_t *pix = *image + (y+y1) * w * 2 + (x + x1) * 2; v=pow((double) x /(double)dx * 5.0, 2.0) + pow((double)y / (double)dy * 5.0, 2.0); if (v>10) v=10; v = 1.0 - ( v / 10.0 ); switch(type) { case 0: *pix -= (*pix) * v; break; case 1: *pix += ( 255-*pix ) * v; break; } } } } } } return error; }
static mlt_properties metadata( mlt_service_type type, const char *id, char *data ) { char file[ PATH_MAX ]; if( type == filter_type ) { snprintf( file, PATH_MAX, "%s/jackrack/%s", mlt_environment( "MLT_DATA" ), strncmp( id, "ladspa.", 7 ) ? data : "filter_ladspa.yml" ); } else { snprintf( file, PATH_MAX, "%s/jackrack/%s", mlt_environment( "MLT_DATA" ), strncmp( id, "ladspa.", 7 ) ? data : "producer_ladspa.yml" ); } mlt_properties result = mlt_properties_parse_yaml( file ); #ifdef GPL if ( !strncmp( id, "ladspa.", 7 ) ) { // Annotate the yaml properties with ladspa control port info. plugin_desc_t *desc = plugin_mgr_get_any_desc( g_jackrack_plugin_mgr, strtol( id + 7, NULL, 10 ) ); if ( desc ) { mlt_properties params = mlt_properties_new(); mlt_properties p; char key[20]; int i; mlt_properties_set( result, "identifier", id ); mlt_properties_set( result, "title", desc->name ); mlt_properties_set( result, "creator", desc->maker ? desc->maker : "unknown" ); mlt_properties_set( result, "description", "LADSPA plugin" ); mlt_properties_set_data( result, "parameters", params, 0, (mlt_destructor) mlt_properties_close, NULL ); for ( i = 0; i < desc->control_port_count; i++ ) { int j = desc->control_port_indicies[i]; p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", mlt_properties_count( params ) ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); snprintf( key, sizeof(key), "%d", j ); mlt_properties_set( p, "identifier", key ); add_port_to_metadata( p, desc, j ); mlt_properties_set( p, "mutable", "yes" ); } for ( i = 0; i < desc->status_port_count; i++ ) { int j = desc->status_port_indicies[i]; p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", mlt_properties_count( params ) ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); snprintf( key, sizeof(key), "%d[*]", j ); mlt_properties_set( p, "identifier", key ); add_port_to_metadata( p, desc, j ); mlt_properties_set( p, "readonly", "yes" ); } p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", mlt_properties_count( params ) ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); mlt_properties_set( p, "identifier", "instances" ); mlt_properties_set( p, "title", "Instances" ); mlt_properties_set( p, "description", "The number of instances of the plugin that are in use.\n" "MLT will create the number of plugins that are required " "to support the number of audio channels.\n" "Status parameters (readonly) are provided for each instance " "and are accessed by specifying the instance number after the " "identifier (starting at zero).\n" "e.g. 9[0] provides the value of status 9 for the first instance." ); mlt_properties_set( p, "type", "integer" ); mlt_properties_set( p, "readonly", "yes" ); if( type == filter_type ) { p = mlt_properties_new(); snprintf( key, sizeof(key), "%d", mlt_properties_count( params ) ); mlt_properties_set_data( params, key, p, 0, (mlt_destructor) mlt_properties_close, NULL ); mlt_properties_set( p, "identifier", "wetness" ); mlt_properties_set( p, "title", "Wet/Dry" ); mlt_properties_set( p, "type", "float" ); mlt_properties_set_double( p, "default", 1 ); mlt_properties_set_double( p, "minimum", 0 ); mlt_properties_set_double( p, "maximum", 1 ); mlt_properties_set( p, "mutable", "yes" ); } } } #endif return result; }