int vout_GetSnapshot( vout_thread_t *p_vout, block_t **pp_image, picture_t **pp_picture, video_format_t *p_fmt, const char *psz_format, mtime_t i_timeout ) { vout_thread_sys_t *p_sys = p_vout->p; vlc_mutex_lock( &p_sys->snapshot.lock ); p_sys->snapshot.i_request++; const mtime_t i_deadline = mdate() + i_timeout; while( p_sys->snapshot.b_available && !p_sys->snapshot.p_picture ) { if( vlc_cond_timedwait( &p_sys->snapshot.wait, &p_sys->snapshot.lock, i_deadline ) ) break; } picture_t *p_picture = p_sys->snapshot.p_picture; if( p_picture ) p_sys->snapshot.p_picture = p_picture->p_next; else if( p_sys->snapshot.i_request > 0 ) p_sys->snapshot.i_request--; vlc_mutex_unlock( &p_sys->snapshot.lock ); if( !p_picture ) { msg_Err( p_vout, "Failed to grab a snapshot" ); return VLC_EGENERIC; } if( pp_image ) { vlc_fourcc_t i_format = VLC_CODEC_PNG; if( psz_format && image_Type2Fourcc( psz_format ) ) i_format = image_Type2Fourcc( psz_format ); const int i_override_width = var_GetInteger( p_vout, "snapshot-width" ); const int i_override_height = var_GetInteger( p_vout, "snapshot-height" ); if( picture_Export( VLC_OBJECT(p_vout), pp_image, p_fmt, p_picture, i_format, i_override_width, i_override_height ) ) { msg_Err( p_vout, "Failed to convert image for snapshot" ); picture_Release( p_picture ); return VLC_EGENERIC; } } if( pp_picture ) *pp_picture = p_picture; else picture_Release( p_picture ); return VLC_SUCCESS; }
vlc_fourcc_t image_Ext2Fourcc( const char *psz_name ) { psz_name = strrchr( psz_name, '.' ); if( !psz_name ) return 0; psz_name++; return image_Type2Fourcc( psz_name ); }
/***************************************************************************** * Create: initialize and set pf_video_filter() *****************************************************************************/ static int Create( vlc_object_t *p_this ) { filter_t *p_filter = (filter_t *)p_this; filter_sys_t *p_sys; const vlc_chroma_description_t *p_chroma = vlc_fourcc_GetChromaDescription( p_filter->fmt_in.video.i_chroma ); if( p_chroma == NULL || p_chroma->plane_count == 0 ) return VLC_EGENERIC; config_ChainParse( p_filter, CFG_PREFIX, ppsz_vfilter_options, p_filter->p_cfg ); p_filter->p_sys = p_sys = calloc( 1, sizeof( filter_sys_t ) ); if( p_filter->p_sys == NULL ) return VLC_ENOMEM; p_sys->p_image = image_HandlerCreate( p_this ); if( !p_sys->p_image ) { msg_Err( p_this, "Couldn't get handle to image conversion routines." ); free( p_sys ); return VLC_EGENERIC; } p_sys->psz_format = var_CreateGetString( p_this, CFG_PREFIX "format" ); p_sys->i_format = image_Type2Fourcc( p_sys->psz_format ); if( !p_sys->i_format ) { msg_Err( p_filter, "Could not find FOURCC for image type '%s'", p_sys->psz_format ); image_HandlerDelete( p_sys->p_image ); free( p_sys->psz_format ); free( p_sys ); return VLC_EGENERIC; } p_sys->i_width = var_CreateGetInteger( p_this, CFG_PREFIX "width" ); p_sys->i_height = var_CreateGetInteger( p_this, CFG_PREFIX "height" ); p_sys->i_ratio = var_CreateGetInteger( p_this, CFG_PREFIX "ratio" ); if( p_sys->i_ratio <= 0) p_sys->i_ratio = 1; p_sys->b_replace = var_CreateGetBool( p_this, CFG_PREFIX "replace" ); p_sys->psz_prefix = var_CreateGetString( p_this, CFG_PREFIX "prefix" ); p_sys->psz_path = var_GetNonEmptyString( p_this, CFG_PREFIX "path" ); if( p_sys->psz_path == NULL ) p_sys->psz_path = config_GetUserDir( VLC_PICTURES_DIR ); p_filter->pf_video_filter = Filter; return VLC_SUCCESS; }