static void serialize_localmotions(StabData* data, LocalMotions &vectors, mlt_position pos) { mlt_animation_item_s item; // Initialize animation item item.is_key = 1; item.frame = data->md.frameNum; item.keyframe_type = mlt_keyframe_discrete; item.property = mlt_property_init(); mlt_property_set_data(item.property, &vectors, 1, lm_destructor, (mlt_serialiser) lm_serializer); mlt_animation_insert(data->animation, &item); mlt_property_close(item.property); }
int mlt_animation_parse(mlt_animation self, const char *data, int length, double fps, locale_t locale ) { int error = 0; int i = 0; struct mlt_animation_item_s item; mlt_tokeniser tokens = mlt_tokeniser_init( ); // Clean the existing geometry mlt_animation_clean( self ); // Update the info on the data if ( data ) self->data = strdup( data ); self->length = length; self->fps = fps; self->locale = locale; item.property = mlt_property_init(); // Tokenise if ( data ) mlt_tokeniser_parse_new( tokens, (char*) data, ";" ); // Iterate through each token for ( i = 0; i < mlt_tokeniser_count( tokens ); i++ ) { char *value = mlt_tokeniser_get_string( tokens, i ); // If no data in keyframe, drop it (trailing semicolon) if ( !value || !strcmp( value, "" ) ) continue; // Reset item item.frame = item.is_key = 0; // Now parse the item mlt_animation_parse_item( self, &item, value ); // Now insert into place mlt_animation_insert( self, &item ); } mlt_animation_interpolate( self ); // Cleanup mlt_tokeniser_close( tokens ); mlt_property_close( item.property ); return error; }