add stream copy mode, fix #324
This commit is contained in:
parent
a739a9f670
commit
b44efde8f1
@ -47,6 +47,7 @@ Check the [releases](https://github.com/ffplayout/ffplayout/releases/latest) for
|
||||
- image source (will loop until out duration is reached)
|
||||
- extra audio source, has priority over audio from video (experimental *)
|
||||
- [multiple audio tracks](/docs/multi_audio.md) (experimental *)
|
||||
- stream copy mode (experimental *)
|
||||
- [custom filters](/docs/custom_filters.md) globally in config, or in playlist for specific clips
|
||||
- import playlist from text or m3u file, with CLI or frontend
|
||||
- audio only, for radio mode (experimental *)
|
||||
|
@ -57,6 +57,8 @@ processing:
|
||||
[c_v_out] for video filter, and [c_a_out] for audio filter.
|
||||
mode: playlist
|
||||
audio_only: false
|
||||
copy_audio: true
|
||||
copy_video: false
|
||||
width: 1024
|
||||
height: 576
|
||||
aspect: 1.778
|
||||
|
@ -177,6 +177,12 @@ pub fn write_hls(
|
||||
);
|
||||
|
||||
let mut enc_prefix = vec_strings!["-hide_banner", "-nostats", "-v", &ff_log_format];
|
||||
|
||||
if config.processing.copy_video
|
||||
|| (!config.processing.audio_only && config.processing.copy_audio)
|
||||
{
|
||||
enc_prefix.push("-re".to_string());
|
||||
}
|
||||
enc_prefix.append(&mut cmd);
|
||||
let enc_cmd = prepare_output_cmd(config, enc_prefix, &node.filter);
|
||||
|
||||
|
@ -518,7 +518,7 @@ pub fn filter_chains(
|
||||
return filters;
|
||||
}
|
||||
|
||||
if !config.processing.audio_only {
|
||||
if !config.processing.audio_only && !config.processing.copy_video {
|
||||
if let Some(probe) = node.probe.as_ref() {
|
||||
if Path::new(&node.audio).is_file() {
|
||||
filters.audio_position = 1;
|
||||
@ -560,42 +560,44 @@ pub fn filter_chains(
|
||||
|
||||
let (list_vf, list_af) = custom::filter_node(&node.custom_filter);
|
||||
|
||||
if config.processing.audio_only {
|
||||
if config.processing.audio_only && !config.processing.copy_audio {
|
||||
realtime(node, &mut filters, config, Audio);
|
||||
} else {
|
||||
} else if !config.processing.copy_video {
|
||||
custom(&proc_vf, &mut filters, 0, Video);
|
||||
custom(&list_vf, &mut filters, 0, Video);
|
||||
}
|
||||
|
||||
for i in 0..config.processing.audio_tracks {
|
||||
if node
|
||||
.probe
|
||||
.as_ref()
|
||||
.and_then(|p| p.audio_streams.get(i as usize))
|
||||
.is_some()
|
||||
|| Path::new(&node.audio).is_file()
|
||||
{
|
||||
extend_audio(node, &mut filters, i);
|
||||
} else if node.unit == Decoder {
|
||||
if !node.source.contains("color=c=") {
|
||||
warn!(
|
||||
"Missing audio track (id {i}) from <b><magenta>{}</></b>",
|
||||
node.source
|
||||
);
|
||||
if !config.processing.copy_audio {
|
||||
for i in 0..config.processing.audio_tracks {
|
||||
if node
|
||||
.probe
|
||||
.as_ref()
|
||||
.and_then(|p| p.audio_streams.get(i as usize))
|
||||
.is_some()
|
||||
|| Path::new(&node.audio).is_file()
|
||||
{
|
||||
extend_audio(node, &mut filters, i);
|
||||
} else if node.unit == Decoder {
|
||||
if !node.source.contains("color=c=") {
|
||||
warn!(
|
||||
"Missing audio track (id {i}) from <b><magenta>{}</></b>",
|
||||
node.source
|
||||
);
|
||||
}
|
||||
|
||||
add_audio(node, &mut filters, i);
|
||||
}
|
||||
|
||||
add_audio(node, &mut filters, i);
|
||||
// add at least anull filter, for correct filter construction,
|
||||
// is important for split filter in HLS mode
|
||||
filters.add_filter("anull", i, Audio);
|
||||
|
||||
fade(node, &mut filters, i, Audio);
|
||||
audio_volume(&mut filters, config, i);
|
||||
|
||||
custom(&proc_af, &mut filters, i, Audio);
|
||||
custom(&list_af, &mut filters, i, Audio);
|
||||
}
|
||||
|
||||
// add at least anull filter, for correct filter construction,
|
||||
// is important for split filter in HLS mode
|
||||
filters.add_filter("anull", i, Audio);
|
||||
|
||||
fade(node, &mut filters, i, Audio);
|
||||
audio_volume(&mut filters, config, i);
|
||||
|
||||
custom(&proc_af, &mut filters, i, Audio);
|
||||
custom(&list_af, &mut filters, i, Audio);
|
||||
}
|
||||
|
||||
if config.out.mode == HLS {
|
||||
|
@ -213,6 +213,10 @@ pub struct Processing {
|
||||
pub mode: ProcessMode,
|
||||
#[serde(default)]
|
||||
pub audio_only: bool,
|
||||
#[serde(default)]
|
||||
pub copy_audio: bool,
|
||||
#[serde(default)]
|
||||
pub copy_video: bool,
|
||||
pub width: i64,
|
||||
pub height: i64,
|
||||
pub aspect: f64,
|
||||
@ -406,6 +410,8 @@ impl PlayoutConfig {
|
||||
|
||||
if config.processing.audio_only {
|
||||
process_cmd.append(&mut vec_strings!["-vn"]);
|
||||
} else if config.processing.copy_video {
|
||||
process_cmd.append(&mut vec_strings!["-c:v", "copy"]);
|
||||
} else {
|
||||
process_cmd.append(&mut vec_strings![
|
||||
"-pix_fmt",
|
||||
@ -427,19 +433,17 @@ impl PlayoutConfig {
|
||||
]);
|
||||
}
|
||||
|
||||
process_cmd.append(&mut pre_audio_codec(
|
||||
&config.processing.custom_filter,
|
||||
&config.ingest.custom_filter,
|
||||
));
|
||||
process_cmd.append(&mut vec_strings![
|
||||
"-ar",
|
||||
"48000",
|
||||
"-ac",
|
||||
config.processing.audio_channels,
|
||||
"-f",
|
||||
"mpegts",
|
||||
"-"
|
||||
]);
|
||||
if config.processing.copy_audio {
|
||||
process_cmd.append(&mut vec_strings!["-c:a", "copy"]);
|
||||
} else {
|
||||
process_cmd.append(&mut pre_audio_codec(
|
||||
&config.processing.custom_filter,
|
||||
&config.ingest.custom_filter,
|
||||
config.processing.audio_channels,
|
||||
));
|
||||
}
|
||||
|
||||
process_cmd.append(&mut vec_strings!["-f", "mpegts", "-"]);
|
||||
|
||||
config.processing.cmd = Some(process_cmd);
|
||||
|
||||
@ -498,11 +502,31 @@ impl Default for PlayoutConfig {
|
||||
/// When custom_filter contains loudnorm filter use a different audio encoder,
|
||||
/// s302m has higher quality, but is experimental
|
||||
/// and works not well together with the loudnorm filter.
|
||||
fn pre_audio_codec(proc_filter: &str, ingest_filter: &str) -> Vec<String> {
|
||||
let mut codec = vec_strings!["-c:a", "s302m", "-strict", "-2", "-sample_fmt", "s16"];
|
||||
fn pre_audio_codec(proc_filter: &str, ingest_filter: &str, channel_count: u8) -> Vec<String> {
|
||||
let mut codec = vec_strings![
|
||||
"-c:a",
|
||||
"s302m",
|
||||
"-strict",
|
||||
"-2",
|
||||
"-sample_fmt",
|
||||
"s16",
|
||||
"-ar",
|
||||
"48000",
|
||||
"-ac",
|
||||
channel_count
|
||||
];
|
||||
|
||||
if proc_filter.contains("loudnorm") || ingest_filter.contains("loudnorm") {
|
||||
codec = vec_strings!["-c:a", "mp2", "-b:a", "384k"];
|
||||
codec = vec_strings![
|
||||
"-c:a",
|
||||
"mp2",
|
||||
"-b:a",
|
||||
"384k",
|
||||
"-ar",
|
||||
"48000",
|
||||
"-ac",
|
||||
channel_count
|
||||
];
|
||||
}
|
||||
|
||||
codec
|
||||
|
Loading…
Reference in New Issue
Block a user