Uso la biblioteca FFmpeg para un proyecto personal y necesito ayuda sobre una cosa. Tengo un archivo de música en sonido estéreo y quiero convertir este sonido estéreo en sonido mono. ¿Es posible con esta biblioteca? ¿Hay una función interna para hacer este trabajo? Mi proyecto está en C/C++.
Busqué en la documentación de Doxygen en el sitio web de FFmpeg y en este foro, pero no encontré nada interesante.
Gracias por leer !
Puedes simplemente usar ffmpeg. El comando directo está presente para el propósito-
ffmpeg -i stereo.flac -ac 1 mono.flac
Convertiría su archivo estéreo en un canal mono. Para más detalles, puede consultar esta página-
https://trac.ffmpeg.org/wiki/Manipulación de canales de audio
-
Gracias, me ayudó mucho! Por cierto, si alguien más necesita convertir la mayor parte de los archivos seguidos, como hice yo:
find . -name '*.mp4' -exec ./convert.sh {} \;
– Marco Arruda
10 dic 2019 a las 22:44
-
Entonces, dentro de la
convert.sh
expediente:– Marco Arruda
10 dic 2019 a las 22:45
-
ffmpeg -i $1 -ac 1 $1.mono.mp4
– Marco Arruda
10 dic 2019 a las 22:45
-
@MarcoArruda Puedes saltarte el
convert.sh
archivo invocandoffmpeg
directamente con:find . -name '*.mp4' -exec ffmpeg -i '{}' -ac 1 '{}.mono.mp4' \;
– joshtch
4 de marzo de 2021 a las 0:12
-
Tenga en cuenta que
-ac 1
voluntad mezclar ambos canales estéreo a uno solo mono, lo que podría no ser lo que desea, especialmente si es solo “una fuente mono grabada erróneamente en estéreo”. En ese caso, tira uno de los canales así:ffmpeg -i INPUT -filter_complex '[0:a]channelsplit=channel_layout=stereo:channels=FL[left]' -map '[left]' OUTPUT
(reemplazarINPUT
&OUTPUT
por supuesto). Esto seleccionará el canal izquierdo, si quiere el derecho, useFR
y[right]
en cambio.– scy
26 de marzo a las 9:21
steve m
Usar swr_convert
de libswresample para convertir entre formatos. Algo como:
#include "libswresample/swresample.h"
au_convert_ctx = swr_alloc();
out_channel_layout = AV_CH_LAYOUT_MONO;
out_sample_fmt = AV_SAMPLE_FMT_S16;
out_sample_rate = 44100;
out_channels = av_get_channel_layout_nb_channels(out_channel_layout);
in_sample_fmt = pCodecCtx->sample_fmt;
in_channel_layout=av_get_default_channel_layout(pCodecCtx->channels);
au_convert_ctx=swr_alloc_set_opts(au_convert_ctx,out_channel_layout, out_sample_fmt, out_sample_rate,
in_channel_layout, in_sample_fmt, pCodecCtx->sample_rate, 0, NULL);
swr_init(au_convert_ctx);
//Generate your frame of original audio, then use swr_convert to convert to mono,
//converted number of samples will now be in out_buffer.
int converted = swr_convert(au_convert_ctx, &out_buffer, MAX_AUDIO_FRAME_SIZE, (const uint8_t **)&pFrame->data , pFrame->nb_samples);
//...
swr_free(&au_convert_ctx);
para empezar Esto convertirá el formato original a 44100 kHz mono. También podrías usar pCodecCtx->sample_rate
como la frecuencia de muestreo de salida también.
Es la solución más flexible y fácil.
usuario1810087
Como mencioné en el comentario, podría volver a muestrearlo usted mismo. Depende de lo que ya tengas y del formato que utilices. No puedo darle un código que funcione instantáneamente, pero le daré un ejemplo (mezcla de código pseudo/real).
Después de codificar el cuadro y haber hecho las cosas que tiene que hacer, su búfer de datos se llenará con el audio. Ahora depende de cómo sea tu formato (ver aquí) y cuántos canales tiene. Supongamos que está firmado en estéreo de 16 bits, entonces su búfer se vería así:
+-----+-----+-----+-----+-----+
| LS1 | RS1 | LS2 | RS2 | ... |
+-----+-----+-----+-----+-----+
// LS = LEFT SAMPLE 16 Bit
// RS = RIGHT SAMPLE 16 Bit
Ahora itere a través del búfer y calcule la muestra izquierda y derecha juntas.
for(int i=0; i<sample_size; i+=2) {
auto r = (static_cast<int32_t>(buffer[i]) + buffer[i+1]) / 2;
buffer[i] = buffer[i+1] = r;
}
-
esto simplemente no es una buena estrategia, los números en una señal de audio no son solo números, representan una señal que involucra el cambio en esos números más que esos números en sí mismos … como si tuviera una onda sinusoidal donde izquierda y derecha estuviera fuera de fase 180 grados, simplemente no tendría señal en la mezcla mono.
– Jugador Grady
1 de julio a las 15:52
Como recuerdo, no hay ninguna función, pero puede convertirla fácilmente usted mismo calculando ambos flujos juntos.
– usuario1810087
14/09/2016 a las 10:13
¿Tiene algún fragmento de código para dar como ejemplo?
– Meugiwara
14/09/2016 a las 11:11