10

Octave 似乎假设系统上可以使用特定的声音播放实用程序,但似乎不提供指定替代的能力。在下面的错误中,Octave 正在寻找ofsndplay不是所有系统上都可用的实用程序。

八度:38> 声音(beamformed_20)

sh: ofsndplay: 找不到命令

是否有 Octave 配置设置或代码片段可用于指定适合系统的实用程序?

4

7 回答 7

8

我已经用以下函数覆盖了 octave 的 playaudio 函数。这仅在安装sox后才有效。

sudo apt-get install sox

(在ubuntu中)

function [ ] = playaudio (x, sampling_rate)

    if nargin == 1
        sampling_rate = 8000
    end
    file = tmpnam ();
    file= [file, '.wav'];
    wavwrite(x, sampling_rate, file);
    ['play ' file ]
    system(['play ' file ]);
    system(['rm ' file]);
end

类似的方法也可以让您记录:

% Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2003, 2004, 2005,
%               2006, 2007 John W. Eaton
%
% This file is part of Octave.
%
% Octave is free software; you can redistribute it and/or modify it
% under the terms of the GNU General Public License as published by
% the Free Software Foundation; either version 3 of the License, or (at
% your option) any later version.
%
% Octave is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of
% MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
% General Public License for more details.
%
% You should have received a copy of the GNU General Public License
% along with Octave; see the file COPYING.  If not, see
% <http://www.gnu.org/licenses/>.

% -*- texinfo -*-
% @deftypefn {Function File} {} record (@var{sec}, @var{sampling_rate})
% Records @var{sec} seconds of audio input into the vector @var{x}.  The
% default value for @var{sampling_rate} is 8000 samples per second, or
% 8kHz.  The program waits until the user types @key{RET} and then
% immediately starts to record.
% @seealso{lin2mu, mu2lin, loadaudio, saveaudio, playaudio, setaudio}
% @end deftypefn

% Author: AW <Andreas.Weingessel@ci.tuwien.ac.at>
% Created: 19 September 1994
% Adapted-By: jwe
% And adapted again 11/25/2010 by Rob Frohne    
function X = record (sec, sampling_rate)


  if (nargin == 1)
    sampling_rate = 8000;
  elseif (nargin != 2)
    print_usage ();
  endif

  file = tmpnam ();
  file= [file,".wav"];

  input ("Please hit ENTER and speak afterwards!\n", 1);

  cmd = sprintf ("rec -c1 -r%d %s trim 0 %d",
                   sampling_rate, file, sec)

  system (cmd);

  X = wavread(file);

end
于 2011-01-21T08:06:09.823 回答
3

安装alsa-utilspulseaudio-utils并将以下内容放入您的 ~/.octaverc:

global sound_play_utility = 'aplay';

或者

global sound_play_utility = 'paplay';
于 2009-10-01T18:31:05.733 回答
3

在我的一台 Linux 机器上,我创建了以下 ofsndplay 脚本来解决硬连线依赖:

$ cat /usr/bin/ofsndplay

#!/bin/sh
## Coping with stupid dependency on ofsndplay in octave
play -t au -

此特定脚本使用 SoXplay实用程序。

诚然,评论对于功能来说是不必要的,但它确实让我感觉更好......

于 2009-10-01T19:48:54.017 回答
3

playaudio被打破!

值得一读playsound(3.6.2版)的默认实现:

function playaudio (name, ext)

  if (nargin < 1 || nargin > 2)
    print_usage ();
  endif

  if (nargin == 1 && isnumeric (name))
    ## play a vector
    if (! isvector (name))
      error ("playaudio: X must be a vector");
    endif
    X = name(:) + 127;
    unwind_protect
      file = tmpnam ();
      fid = fopen (file, "wb");
      fwrite (fid, X, "uchar");
      fclose (fid);
      [status, out] = system (sprintf ('cat "%s" > /dev/dsp', file));
      if (status != 0)
        system (sprintf ("paplay --raw \"%s\"", file))
      endif
    unwind_protect_cleanup
      unlink (file);
    end_unwind_protect
  elseif (nargin >= 1 && ischar (name))
    ## play a file
    if (nargin == 1)
      name = [name ".lin"];
    elseif (nargin == 2)
      name = [name "." ext];
    endif
    if (any (strcmp (ext, {"lin", "raw"})))
      [status, out] = system (sprintf ('cat "%s" > /dev/dsp', name));
      if (status != 0)
        system (sprintf ('paplay --raw "%s"', name))
      endif
    elseif (any (strcmp (ext, {"mu", "au" "snd", "ul"})))
      [status, out] = system (sprintf ('cat "%s" > /dev/audio', name));
      if (status != 0)
        system (sprintf ('paplay "%s"', name))
      endif
    else
      error ("playaudio: unsupported extension '%s'", ext);
    endif
  else
    print_usage ();
  endif

endfunction

有几点需要注意:

  1. 在最新的 linux 发行版中,直接写入 /dev/dsp 总是失败,因此每次运行命令时都会出现错误(cat > /dev/dsp在线)。
  2. 它是硬编码的paplay,一个命令行pulseaudio播放器。
  3. paplay调用将永远不会起作用,因为paplay默认为s16ne(可能是错字;我认为他们的意思是s16be- 有符号的 16 位大端序),并playaudio写入无符号的 8 位!
  4. 它使用system(). 总是一个坏主意。
  5. 它将音频写入文件而不是流式传输。可能会导致大文件出现问题。
  6. 与 matlab 不同,它不处理浮点音频。它实际上只支持 8 位音频!有点愚蠢,因为这是 wavread 返回的结果!
  7. 与 matlab 不同的是,它只支持一种采样率(44100 Hz)。

此功能非常hacky,不安全且不可靠。如果它以任何方式代表 Octave 中其他地方的代码质量……嗯,这令人担忧。它真的应该在 Octave 中使用 portaudio 重新实现为适当的功能。

稍微好一点的版本

我真的没有时间或动力在 octave 上做很多黑客攻击,所以同时我建议你改用这个稍微好一点的函数:

function playsound(wav, samplerate)
  # Play a single-channel wave at a certain sample rate (defaults to 44100 Hz).
  # Input can be integer, in which case it is assumed to be signed 16-bit, or
  # float, in which case it is in the range -1:1.

  if (nargin < 1 || nargin > 2)
    print_usage();
  endif

  if (nargin < 2)
    samplerate = 44100;
  end

  if (!isvector(wav))
    error("playsound: X must be a vector");
  endif

  # Write it as a 16-bit signed, little endian (though the amaaazing docs don't say the endianness)

  # If it is integers we assume it is 16 bit signed. Otherwise we assume in the range -1:1
  if (isfloat(wav))
    X = min(max(wav(:), -1), 1) * 32767; # Why matlab & octave do not have a clip() function... I do not know.
  else
    X = min(max(wav(:), -32767), 32767) + 32767;
  endif
  unwind_protect
    file = tmpnam ();
    fid = fopen (file, "wb");
    fwrite (fid, X, "int16");
    fclose (fid);
    # Making aplay (alsa) the default, because let's be honest: it is still way more reliable than
    # the mess that is pulseaudio.
    if (exist("/usr/bin/aplay") == 2)
      system(sprintf("/usr/bin/aplay --format=S16_LE --channels=1 --rate=%d \"%s\"", samplerate, file))
    elseif (exist("/usr/bin/paplay") == 2)
      system(sprintf("/usr/bin/paplay --format=s16le --channels=1 --rate=%d --raw \"%s\"", samplerate, file))
    endif
  unwind_protect_cleanup
    unlink (file);
  end_unwind_protect

endfunction

这仍然是一个非常 hacky 的功能。但它至少应该比playaudio! 我将把实现soundsc作为练习留给读者。

于 2013-03-27T20:52:04.077 回答
2

我在 Mac (Yosemite) 上,发现了一个比其他人建议的更简单的解决方案。以防万一这仍然与任何人相关:

首先安装 SoX:http ://sox.sourceforge.net/

(通过自制)

brew install sox

现在在终端命令行上,您可以使用:

play “/path/to/sound file.wav"

...你会听到美妙的音乐。

但是该命令在 Octave 中不起作用。这确实有效:

system(‘play “/path/to/sound file.wav”’);
于 2015-01-02T05:00:43.843 回答
1

在 OSX 上,这是我为使声音正常工作所做的:

sound命令帮助:

This function writes the audio data through a pipe to the program "play" from the sox distribution. sox runs pretty much anywhere, but it only has audio drivers for OSS (primarily linux and freebsd) and SunOS. In case your local machine is not one of these, write a shell script such as ~/bin/octaveplay, substituting AUDIO_UTILITY with whatever audio utility you happen to have on your system: #!/bin/sh cat > ~/.octave_play.au SYSTEM_AUDIO_UTILITY ~/.octave_play.au rm -f ~/.octave_play.au and set the global variable (e.g., in .octaverc) global sound_play_utility="~/bin/octaveplay";

我将以下脚本命名为“octaveplay”并将其放入 ~/bin:

cat > ~/.octave_play.aif
afplay ~/.octave_play.aif
rm -f ~/.octave_play.aif

然后我创建了 .octaverc 并添加了: global sound_play_utility="~/bin/octaveplay";

瞧!

于 2010-01-12T08:12:09.333 回答
1

在八度 4.2.1 上。您可以按如下方式播放wav文件

将以下代码保存在文件 playWav.m 中

function playWav(inputFilePath)
  [y, fs] = audioread(inputFilePath);
  player  = audioplayer(y, fs);
  playblocking(player)
end

然后您可以playWav('/path/to/wavfile');从 Octave 命令行调用该函数。

在 Windows 7 上测试。

于 2018-02-04T07:33:19.967 回答