📄 transcode.c
字号:
/***************************************************************************** * Open: *****************************************************************************/static int Open( vlc_object_t *p_this ){ sout_stream_t *p_stream = (sout_stream_t*)p_this; sout_stream_sys_t *p_sys; vlc_value_t val; p_sys = vlc_object_create( p_this, sizeof( sout_stream_sys_t ) ); p_sys->p_out = sout_StreamNew( p_stream->p_sout, p_stream->psz_next ); if( !p_sys->p_out ) { msg_Err( p_stream, "cannot create chain" ); vlc_object_release( p_sys ); return VLC_EGENERIC; } p_sys->i_master_drift = 0; config_ChainParse( p_stream, SOUT_CFG_PREFIX, ppsz_sout_options, p_stream->p_cfg ); /* Audio transcoding parameters */ var_Get( p_stream, SOUT_CFG_PREFIX "aenc", &val ); p_sys->psz_aenc = NULL; p_sys->p_audio_cfg = NULL; if( val.psz_string && *val.psz_string ) { char *psz_next; psz_next = config_ChainCreate( &p_sys->psz_aenc, &p_sys->p_audio_cfg, val.psz_string ); free( psz_next ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "acodec", &val ); p_sys->i_acodec = 0; if( val.psz_string && *val.psz_string ) { char fcc[4] = " "; memcpy( fcc, val.psz_string, __MIN( strlen( val.psz_string ), 4 ) ); p_sys->i_acodec = VLC_FOURCC( fcc[0], fcc[1], fcc[2], fcc[3] ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "ab", &val ); p_sys->i_abitrate = val.i_int; if( p_sys->i_abitrate < 4000 ) p_sys->i_abitrate *= 1000; var_Get( p_stream, SOUT_CFG_PREFIX "samplerate", &val ); p_sys->i_sample_rate = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "channels", &val ); p_sys->i_channels = val.i_int; if( p_sys->i_acodec ) { if( p_sys->i_acodec == VLC_FOURCC('m','p','3',0) && p_sys->i_channels > 2 ) { msg_Warn( p_stream, "%d channels invalid for mp3, forcing to 2", p_sys->i_channels ); p_sys->i_channels = 2; } msg_Dbg( p_stream, "codec audio=%4.4s %dHz %d channels %dKb/s", (char *)&p_sys->i_acodec, p_sys->i_sample_rate, p_sys->i_channels, p_sys->i_abitrate / 1000 ); } var_Get( p_stream, SOUT_CFG_PREFIX "afilter", &val ); if( val.psz_string && *val.psz_string ) p_sys->psz_af2 = val.psz_string; else { free( val.psz_string ); p_sys->psz_af2 = NULL; } /* Video transcoding parameters */ var_Get( p_stream, SOUT_CFG_PREFIX "venc", &val ); p_sys->psz_venc = NULL; p_sys->p_video_cfg = NULL; if( val.psz_string && *val.psz_string ) { char *psz_next; psz_next = config_ChainCreate( &p_sys->psz_venc, &p_sys->p_video_cfg, val.psz_string ); free( psz_next ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "vcodec", &val ); p_sys->i_vcodec = 0; if( val.psz_string && *val.psz_string ) { char fcc[4] = " "; memcpy( fcc, val.psz_string, __MIN( strlen( val.psz_string ), 4 ) ); p_sys->i_vcodec = VLC_FOURCC( fcc[0], fcc[1], fcc[2], fcc[3] ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "vb", &val ); p_sys->i_vbitrate = val.i_int; if( p_sys->i_vbitrate < 16000 ) p_sys->i_vbitrate *= 1000; var_Get( p_stream, SOUT_CFG_PREFIX "scale", &val ); p_sys->f_scale = val.f_float; var_Get( p_stream, SOUT_CFG_PREFIX "fps", &val ); p_sys->f_fps = val.f_float; var_Get( p_stream, SOUT_CFG_PREFIX "hurry-up", &val ); p_sys->b_hurry_up = val.b_bool; var_Get( p_stream, SOUT_CFG_PREFIX "width", &val ); p_sys->i_width = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "height", &val ); p_sys->i_height = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "maxwidth", &val ); p_sys->i_maxwidth = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "maxheight", &val ); p_sys->i_maxheight = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "vfilter", &val ); if( val.psz_string && *val.psz_string ) p_sys->psz_vf2 = val.psz_string; else { free( val.psz_string ); p_sys->psz_vf2 = NULL; } var_Get( p_stream, SOUT_CFG_PREFIX "deinterlace", &val ); p_sys->b_deinterlace = val.b_bool; var_Get( p_stream, SOUT_CFG_PREFIX "deinterlace-module", &val ); p_sys->psz_deinterlace = NULL; p_sys->p_deinterlace_cfg = NULL; if( val.psz_string && *val.psz_string ) { char *psz_next; psz_next = config_ChainCreate( &p_sys->psz_deinterlace, &p_sys->p_deinterlace_cfg, val.psz_string ); free( psz_next ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "threads", &val ); p_sys->i_threads = val.i_int; var_Get( p_stream, SOUT_CFG_PREFIX "high-priority", &val ); p_sys->b_high_priority = val.b_bool; if( p_sys->i_vcodec ) { msg_Dbg( p_stream, "codec video=%4.4s %dx%d scaling: %f %dkb/s", (char *)&p_sys->i_vcodec, p_sys->i_width, p_sys->i_height, p_sys->f_scale, p_sys->i_vbitrate / 1000 ); } /* Subpictures transcoding parameters */ p_sys->p_spu = NULL; p_sys->psz_senc = NULL; p_sys->p_spu_cfg = NULL; p_sys->i_scodec = 0; var_Get( p_stream, SOUT_CFG_PREFIX "senc", &val ); if( val.psz_string && *val.psz_string ) { char *psz_next; psz_next = config_ChainCreate( &p_sys->psz_senc, &p_sys->p_spu_cfg, val.psz_string ); free( psz_next ); } free( val.psz_string ); var_Get( p_stream, SOUT_CFG_PREFIX "scodec", &val ); if( val.psz_string && *val.psz_string ) { char fcc[4] = " "; memcpy( fcc, val.psz_string, __MIN( strlen( val.psz_string ), 4 ) ); p_sys->i_scodec = VLC_FOURCC( fcc[0], fcc[1], fcc[2], fcc[3] ); } free( val.psz_string ); if( p_sys->i_scodec ) { msg_Dbg( p_stream, "codec spu=%4.4s", (char *)&p_sys->i_scodec ); } var_Get( p_stream, SOUT_CFG_PREFIX "soverlay", &val ); p_sys->b_soverlay = val.b_bool; var_Get( p_stream, SOUT_CFG_PREFIX "sfilter", &val ); if( val.psz_string && *val.psz_string ) { p_sys->p_spu = spu_Create( p_stream ); var_Create( p_sys->p_spu, "sub-filter", VLC_VAR_STRING ); var_Set( p_sys->p_spu, "sub-filter", val ); spu_Init( p_sys->p_spu ); } free( val.psz_string ); /* OSD menu transcoding parameters */ p_sys->psz_osdenc = NULL; p_sys->p_osd_cfg = NULL; p_sys->i_osdcodec = 0; p_sys->b_osd = false; var_Get( p_stream, SOUT_CFG_PREFIX "osd", &val ); if( val.b_bool ) { vlc_value_t osd_val; char *psz_next; psz_next = config_ChainCreate( &p_sys->psz_osdenc, &p_sys->p_osd_cfg, strdup( "dvbsub") ); free( psz_next ); p_sys->i_osdcodec = VLC_FOURCC('Y','U','V','P' ); msg_Dbg( p_stream, "codec osd=%4.4s", (char *)&p_sys->i_osdcodec ); if( !p_sys->p_spu ) { osd_val.psz_string = strdup("osdmenu"); p_sys->p_spu = spu_Create( p_stream ); var_Create( p_sys->p_spu, "sub-filter", VLC_VAR_STRING ); var_Set( p_sys->p_spu, "sub-filter", osd_val ); spu_Init( p_sys->p_spu ); free( osd_val.psz_string ); } else { osd_val.psz_string = strdup("osdmenu"); var_Set( p_sys->p_spu, "sub-filter", osd_val ); free( osd_val.psz_string ); } } /* Audio settings */ var_Get( p_stream, SOUT_CFG_PREFIX "audio-sync", &val ); p_sys->b_master_sync = val.b_bool; if( p_sys->f_fps > 0 ) p_sys->b_master_sync = true; p_stream->pf_add = Add; p_stream->pf_del = Del; p_stream->pf_send = Send; p_stream->p_sys = p_sys; return VLC_SUCCESS;}/***************************************************************************** * Close: *****************************************************************************/static void Close( vlc_object_t * p_this ){ sout_stream_t *p_stream = (sout_stream_t*)p_this; sout_stream_sys_t *p_sys = p_stream->p_sys; sout_StreamDelete( p_sys->p_out ); free( p_sys->psz_af2 ); while( p_sys->p_audio_cfg != NULL ) { config_chain_t *p_next = p_sys->p_audio_cfg->p_next; free( p_sys->p_audio_cfg->psz_name ); free( p_sys->p_audio_cfg->psz_value ); free( p_sys->p_audio_cfg ); p_sys->p_audio_cfg = p_next; } free( p_sys->psz_aenc ); free( p_sys->psz_vf2 ); while( p_sys->p_video_cfg != NULL ) { config_chain_t *p_next = p_sys->p_video_cfg->p_next; free( p_sys->p_video_cfg->psz_name ); free( p_sys->p_video_cfg->psz_value ); free( p_sys->p_video_cfg ); p_sys->p_video_cfg = p_next; } free( p_sys->psz_venc ); while( p_sys->p_deinterlace_cfg != NULL ) { config_chain_t *p_next = p_sys->p_deinterlace_cfg->p_next; free( p_sys->p_deinterlace_cfg->psz_name ); free( p_sys->p_deinterlace_cfg->psz_value ); free( p_sys->p_deinterlace_cfg ); p_sys->p_deinterlace_cfg = p_next; } free( p_sys->psz_deinterlace ); while( p_sys->p_spu_cfg != NULL ) { config_chain_t *p_next = p_sys->p_spu_cfg->p_next; free( p_sys->p_spu_cfg->psz_name ); free( p_sys->p_spu_cfg->psz_value ); free( p_sys->p_spu_cfg ); p_sys->p_spu_cfg = p_next; } free( p_sys->psz_senc ); if( p_sys->p_spu ) spu_Destroy( p_sys->p_spu ); while( p_sys->p_osd_cfg != NULL ) { config_chain_t *p_next = p_sys->p_osd_cfg->p_next; free( p_sys->p_osd_cfg->psz_name ); free( p_sys->p_osd_cfg->psz_value ); free( p_sys->p_osd_cfg ); p_sys->p_osd_cfg = p_next; } free( p_sys->psz_osdenc ); vlc_object_release( p_sys );}struct sout_stream_id_t{ vlc_fourcc_t b_transcode; /* id of the out stream */ void *id; /* Decoder */ decoder_t *p_decoder; /* Filters */ filter_chain_t *p_f_chain; /* User specified filters */ filter_chain_t *p_uf_chain; /* Encoder */ encoder_t *p_encoder; /* Sync */ date_t interpolated_pts;};static sout_stream_id_t *Add( sout_stream_t *p_stream, es_format_t *p_fmt ){ sout_stream_sys_t *p_sys = p_stream->p_sys; sout_stream_id_t *id; id = malloc( sizeof( sout_stream_id_t ) ); if( !id ) goto error; memset( id, 0, sizeof(sout_stream_id_t) ); id->id = NULL; id->p_decoder = NULL; id->p_encoder = NULL; /* Create decoder object */ id->p_decoder = vlc_object_create( p_stream, VLC_OBJECT_DECODER );
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -