void PipelineStabDetect::onInput(InputImageInfo info, Magick::Image image) { try { if (!initialized) { init(image); } if (image.rows() != height || image.columns() != width) { throw runtime_error(QString("Not uniform image size! %").arg(info.file.fileName()).toStdString()); } Magick::Blob blob; // set raw RGBS output format & convert it into a Blob if (image.depth() > 8) *err << "Warning: we lost some information by converting to 8bit depth (now " << image.depth() << ")" << endl; image.depth(8); image.magick("RGB"); image.write(&blob); LocalMotions localmotions; VSFrame frame; size_t dataLen = blob.length(); Q_ASSERT(fi.planes == 1); Q_ASSERT(dataLen == image.baseColumns() * image.baseRows() * 3); if (stabConf->mdConf.show > 0) { // create copy of blob frame.data[0] = new uint8_t[dataLen]; memcpy(frame.data[0], blob.data(), dataLen); } else { frame.data[0] = (uint8_t*) blob.data(); } frame.linesize[0] = image.baseColumns() * 3; if (vsMotionDetection(&md, &localmotions, &frame) != VS_OK) { throw runtime_error("motion detection failed"); } else { if (vsWriteToFile(&md, f, &localmotions) != VS_OK) { throw runtime_error("cannot write to transform file"); } vs_vector_del(&localmotions); } if (stabConf->mdConf.show > 0) { // if we want to store transformations, we have to create new image... Magick::Geometry g(width, height); Magick::Blob oblob(frame.data[0], dataLen); Magick::Image oimage; oimage.read(oblob, g, 8, "RGB"); delete[] frame.data[0]; emit input(info, oimage); } else { emit input(info, image); } } catch (exception &e) { emit error(e.what()); } }
int test_store_restore(TestData* testdata){ MotionDetect md; test_bool(initMotionDetect(&md, &testdata->fi, "test") == VS_OK); test_bool(configureMotionDetect(&md)== VS_OK); LocalMotions lms; int i; for(i=0; i<2; i++){ test_bool(motionDetection(&md, &lms,&testdata->frames[i])== VS_OK); if (i==0) vs_vector_del(&lms); } FILE* f = fopen("lmtest","w"); storeLocalmotions(f,&lms); fclose(f); f = fopen("lmtest","r"); LocalMotions test = restoreLocalmotions(f); fclose(f); storeLocalmotions(stderr,&test); compare_localmotions(&lms,&test); fprintf(stderr,"\n** LM and LMS OKAY\n"); f = fopen("lmstest","w"); md.frameNum=1; prepareFile(&md,f); writeToFile(&md,f,&lms); md.frameNum=2; writeToFile(&md,f,&test); fclose(f); f = fopen("lmstest","r"); test_bool(readFileVersion(f)==1); LocalMotions read1; test_bool(readFromFile(f,&read1)==1); compare_localmotions(&lms,&read1); LocalMotions read2; test_bool(readFromFile(f,&read2)==2); compare_localmotions(&test,&read2); fclose(f); fprintf(stderr,"** Reading file stepwise OKAY\n"); vs_vector_del(&read1); vs_vector_del(&read2); vs_vector_del(&test); vs_vector_del(&lms); f = fopen("lmstest","r"); ManyLocalMotions mlms; test_bool(readLocalMotionsFile(f,&mlms)==VS_OK); test_bool(vs_vector_size(&mlms)==2); fprintf(stderr,"** Entire file routine OKAY\n\n"); for(i=0; i< vs_vector_size(&mlms); i++){ if(MLMGet(&mlms,i)) vs_vector_del(MLMGet(&mlms,i)); } vs_vector_del(&mlms); return 1; }
int test_store_restore(TestData* testdata){ VSMotionDetectConfig mdconf = vsMotionDetectGetDefaulfConfig("test_motionDetect"); VSMotionDetect md; test_bool(vsMotionDetectInit(&md, &mdconf, &testdata->fi) == VS_OK); LocalMotions lms; int i; for(i=0; i<2; i++){ test_bool(vsMotionDetection(&md, &lms,&testdata->frames[i])== VS_OK); if (i==0) vs_vector_del(&lms); } FILE* f = fopen("lmtest","w"); vsStoreLocalmotions(f,&lms); fclose(f); f = fopen("lmtest","r"); LocalMotions test = vsRestoreLocalmotions(f); fclose(f); vsStoreLocalmotions(stderr,&test); compare_localmotions(&lms,&test); fprintf(stderr,"\n** LM and LMS OKAY\n"); f = fopen("lmstest","w"); md.frameNum=1; vsPrepareFile(&md,f); vsWriteToFile(&md,f,&lms); md.frameNum=2; vsWriteToFile(&md,f,&test); fclose(f); f = fopen("lmstest","r"); test_bool(vsReadFileVersion(f)==1); LocalMotions read1; test_bool(vsReadFromFile(f,&read1)==1); compare_localmotions(&lms,&read1); LocalMotions read2; test_bool(vsReadFromFile(f,&read2)==2); compare_localmotions(&test,&read2); fclose(f); fprintf(stderr,"** Reading file stepwise OKAY\n"); vs_vector_del(&read1); vs_vector_del(&read2); vs_vector_del(&test); vs_vector_del(&lms); f = fopen("lmstest","r"); VSManyLocalMotions mlms; test_bool(vsReadLocalMotionsFile(f,&mlms)==VS_OK); test_bool(vs_vector_size(&mlms)==2); fprintf(stderr,"** Entire file routine OKAY\n\n"); for(i=0; i< vs_vector_size(&mlms); i++){ if(VSMLMGet(&mlms,i)) vs_vector_del(VSMLMGet(&mlms,i)); } vs_vector_del(&mlms); return 1; }
static void analyze_image( mlt_filter filter, mlt_frame frame, uint8_t* vs_image, VSPixelFormat vs_format, int width, int height ) { mlt_properties properties = MLT_FILTER_PROPERTIES( filter ); vs_data* data = (vs_data*)filter->child; mlt_position pos = mlt_filter_get_position( filter, frame ); // If any frames are skipped, analysis data will be incomplete. if( data->analyze_data && pos != data->analyze_data->last_position + 1 ) { mlt_log_error( MLT_FILTER_SERVICE(filter), "Bad frame sequence\n" ); destory_analyze_data( data->analyze_data ); data->analyze_data = NULL; } if ( !data->analyze_data && pos == 0 ) { // Analysis must start on the first frame init_analyze_data( filter, frame, vs_format, width, height ); } if( data->analyze_data ) { // Initialize the VSFrame to be analyzed. VSMotionDetect* md = &data->analyze_data->md; LocalMotions localmotions; VSFrame vsFrame; vsFrameFillFromBuffer( &vsFrame, vs_image, &md->fi ); // Detect and save motions. if( vsMotionDetection( md, &localmotions, &vsFrame ) == VS_OK ) { vsWriteToFile( md, data->analyze_data->results, &localmotions); vs_vector_del( &localmotions ); } else { mlt_log_error( MLT_FILTER_SERVICE(filter), "Motion detection failed\n" ); destory_analyze_data( data->analyze_data ); data->analyze_data = NULL; } // Publish the motions if this is the last frame. if ( pos + 1 == mlt_filter_get_length2( filter, frame ) ) { mlt_log_info( MLT_FILTER_SERVICE(filter), "Analysis complete\n" ); destory_analyze_data( data->analyze_data ); data->analyze_data = NULL; mlt_properties_set( properties, "results", mlt_properties_get( properties, "filename" ) ); } else { data->analyze_data->last_position = pos; } } }
static int deshake_filter_video(TCModuleInstance *self, vframe_list_t *frame) { DeshakeData *sd = NULL; TC_MODULE_SELF_CHECK(self, "filter_video"); TC_MODULE_SELF_CHECK(frame, "filter_video"); sd = self->userdata; MotionDetect* md = &(sd->md); TransformData* td = &(sd->td); LocalMotions localmotions; Transform motion; VSFrame vsFrame; fillFrameFromBuffer(&vsFrame,frame->video_buf, &td->fiSrc); if(motionDetection(md, &localmotions, &vsFrame)!= VS_OK){ tc_log_error(MOD_NAME, "motion detection failed"); return TC_ERROR; } if(writeToFile(md, sd->f, &localmotions) != VS_OK) motion = simpleMotionsToTransform(td, &localmotions); vs_vector_del(&localmotions); transformPrepare(td, &vsFrame, &vsFrame); Transform t = lowPassTransforms(td, &sd->avg, &motion); /* tc_log_error(MOD_NAME, "Trans: det: %f %f %f \n\t\t act: %f %f %f %f", */ /* motion.x, motion.y, motion.alpha, */ /* t.x, t.y, t.alpha, t.zoom); */ if (sd->vob->im_v_codec == CODEC_RGB) { transformRGB(td, t); } else if (sd->vob->im_v_codec == CODEC_YUV) { transformYUV(td, t); } else { tc_log_error(MOD_NAME, "unsupported Codec: %i\n", sd->vob->im_v_codec); return TC_ERROR; } transformFinish(td); return TC_OK; }
static void init_apply_data( mlt_filter filter, mlt_frame frame, VSPixelFormat vs_format, int width, int height ) { mlt_properties properties = MLT_FILTER_PROPERTIES( filter ); vs_data* data = (vs_data*)filter->child; vs_apply* apply_data = (vs_apply*)calloc( 1, sizeof(vs_apply) ); char* filename = mlt_properties_get( properties, "results" ); memset( apply_data, 0, sizeof( vs_apply ) ); mlt_log_info( MLT_FILTER_SERVICE(filter), "Load results from %s\n", filename ); // Initialize the VSTransformConfig get_transform_config( &apply_data->conf, filter, frame ); // Initialize VSTransformData VSFrameInfo fi_src, fi_dst; vsFrameInfoInit( &fi_src, width, height, vs_format ); vsFrameInfoInit( &fi_dst, width, height, vs_format ); vsTransformDataInit( &apply_data->td, &apply_data->conf, &fi_src, &fi_dst ); // Initialize VSTransformations vsTransformationsInit( &apply_data->trans ); // Convert file name string encoding. mlt_properties_from_utf8( properties, "results", "_results" ); filename = mlt_properties_get( properties, "_results" ); // Load the motions from the analyze step and convert them to VSTransformations FILE* f = fopen( filename, "r" ); VSManyLocalMotions mlms; if( vsReadLocalMotionsFile( f, &mlms ) == VS_OK ) { int i = 0; mlt_log_info( MLT_FILTER_SERVICE(filter), "Successfully loaded %d motions\n", vs_vector_size( &mlms ) ); vsLocalmotions2Transforms( &apply_data->td, &mlms, &apply_data->trans ); vsPreprocessTransforms( &apply_data->td, &apply_data->trans ); // Free the MultipleLocalMotions for( i = 0; i < vs_vector_size( &mlms ); i++ ) { LocalMotions* lms = (LocalMotions*)vs_vector_get( &mlms, i ); if( lms ) { vs_vector_del( lms ); } } vs_vector_del( &mlms ); data->apply_data = apply_data; } else { mlt_log_error( MLT_FILTER_SERVICE(filter), "Can not read results file: %s\n", filename ); destory_apply_data( apply_data ); data->apply_data = NULL; } if( f ) { fclose( f ); } }
void lm_destructor(void *lms) { vs_vector_del(static_cast<VSVector*>(lms)); }
static int 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); *format = mlt_image_yuv420p; DeshakeData *data = static_cast<DeshakeData*>(filter->child); int error = mlt_frame_get_image(frame, image, format, width, height, 1); if (!error) { // Service locks are for concurrency control mlt_service_lock(MLT_FILTER_SERVICE(filter)); // Handle signal from app to re-init data if (mlt_properties_get_int(properties, "refresh")) { mlt_properties_set(properties, "refresh", NULL); clear_deshake(data); data->initialized = false; } // clear deshake data, when seeking or dropping frames mlt_position pos = mlt_filter_get_position(filter, frame); if(pos != data->lastFrame+1) { clear_deshake(data); data->initialized = false; } data->lastFrame = pos; if (!data->initialized) { char *interps = mlt_properties_get(MLT_FRAME_PROPERTIES(frame), "rescale.interp"); init_deshake(data, properties, format, width, height, interps); data->initialized = true; } VSMotionDetect* md = &data->md; VSTransformData* td = &data->td; LocalMotions localmotions; VSTransform motion; VSFrame vsFrame; vsFrameFillFromBuffer(&vsFrame, *image, &md->fi); vsMotionDetection(md, &localmotions, &vsFrame); motion = vsSimpleMotionsToTransform(md->fi, FILTER_NAME, &localmotions); vs_vector_del(&localmotions); vsTransformPrepare(td, &vsFrame, &vsFrame); VSTransform t = vsLowPassTransforms(td, &data->avg, &motion); // mlt_log_warning(filter, "Trans: det: %f %f %f \n\t\t act: %f %f %f %f", // motion.x, motion.y, motion.alpha, // t.x, t.y, t.alpha, t.zoom); vsDoTransform(td, t); vsTransformFinish(td); mlt_service_unlock(MLT_FILTER_SERVICE(filter)); } return error; }