Redirecionar programaticamente a saída de áudio de um programa específico para o arquivo

8

Gostaria de redirecionar a saída de áudio de um programa para arquivo, na linha de comando, como em

$ redirect-wrapper file.wav my-program

de modo a

  • Não ouço a saída do programa, ou seja, a saída deve ir apenas para o arquivo
  • Não gravo nada além do programa, ou seja, apenas este programa específico é redirecionado para o arquivo
  • o restante do sistema de áudio é deixado completamente imperturbável, nenhuma opção de configuração é alterada para frente e para trás ou algo assim

Existe uma maneira de fazer isso? Esta questão relacionada não ajuda, preciso de uma solução de linha de comando, não "clique lá, depois lá". Esta é, provavelmente, também relacionado, mas também depende da pavucontrol aplicação gráfica. Encontrei uma alternativa terminal ao pavucontrol, pacmd.

Mas isso ainda apenas possibilita o seguinte compromisso:

  1. Obtenha o coletor padrão e salve o que era. Quão? Provavelmente grepping atravéspacmd list-sinks
  2. Defina coletor padrão como coletor snd-aloop com pacmd set-default-sink.
  3. Grave daquela pia.
  4. Iniciar aplicativo
  5. Aguarde até o aplicativo abrir sua entrada do coletor: pacmd list-sink-inputs | grep name-of-my-programse encontrar alguma coisa, a entrada está aberta.
  6. Mude o padrão de volta para o que era pacmd set-default-sink.
  7. Pare a gravação assim que o aplicativo fechar.

Mas isso ainda altera o coletor padrão por um período de tempo de até alguns minutos (a entrada do coletor normalmente não é aberta até que o programa esteja realmente reproduzindo sons que não precisam estar logo após o lançamento). Eu implementei esse compromisso; Github .

Ainda procurando respostas não comprometedoras.

Ninguém
fonte
Isso pode ajudar: swview.org/node/213 Ele está mudando temporariamente ~/.asoundrc. Talvez você possa evitar isso de alguma forma.
Rudimeier
@rudimeier Isso está configurando globalmente o dispositivo de saída padrão. Não importa de ~ / .asoundrc ou de outra maneira, ele sempre atrapalha o resto do sistema de áudio.
Ninguém
Não faço ideia, mas acho que você está no caminho certo. A saída de pacmd listmostra quais fontes e sumidouros estão anexados a programas específicos, portanto pode haver uma maneira de alterá-los. Tente perguntar na lista do pulseaudio em lists.freedesktop.org/mailman/listinfo/pulseaudio-discuss Os mantenedores / desenvolvedores estão lá e são bastante úteis.
19416 Joe
@Joe A reatribuição de pias é possível com o pacmd, sim, mas porque elas são alocadas apenas quando o áudio realmente é reproduzido (pelo menos em alguns programas; Firefox), isso significa que eu precisaria procurá-las em um loop apertado e possivelmente perderia o primeiro 0,5s ou mais do áudio. Obrigado pela dica sobre a lista de discussão. :-)
Ninguém

Respostas:

2

Umm, olhando a documentação do pulseaudio.

man pulseaudio

Temos as seguintes variáveis ​​de ambiente

   $PULSE_SERVER: the server string specifying the server to connect to when a client asks for a sound server connection  and  doesn't  explicitly  ask  for  a  specific
   server.  The server string is a list of server addresses separated by whitespace which are tried in turn. A server address consists of an optional address type speci‐
   fier (unix:, tcp:, tcp4:, tcp6:), followed by a path or host address. A host address may include an optional port number. A server address may be prefixed by a string
   enclosed in {}. In this case the following server address is ignored unless the prefix string equals the local hostname or the machine id (/etc/machine-id).

   $PULSE_SINK: the symbolic name of the sink to connect to when a client creates a playback stream and doesn't explicitly ask for a specific sink.

Esperamos que isso permita que você complete a substituição do coletor pulseaudio e, se isso não for suficiente, execute nosso próprio servidor pulseaudio de uso único.

Referindo-se a esta página ( /ubuntu/60837/record-a-programs-output-with-pulseaudio ), descobrimos o comando parec/ pacat(eles são aliases) que pode gravar e gravar em pias e córregos.

Juntando isso, temos o seguinte wrapper (que na verdade eu não executei - embora eu tenha conseguido que esse método funcione de maneira ad-hoc)

sink_name="sink-$(date +%s)"
pacat $sink_name.monitor 
parec -d steam.monitor | oggenc -b 192 -o /tmp/steam.ogg --raw - &
pid=$!
PULSE_SINK=$sink_name "$@"
kill $pid
Att Righ
fonte
Agora me sinto idiota. Obrigado. ^^ Eventualmente, aprenderei a ler a documentação primeiro.
Ninguém