ossaudiodev — 访问兼容 OSS 的音频设备

自版本 3.11 起已弃用,将在版本 3.13 中移除: The ossaudiodev 模块已弃用(有关详细信息,请参阅 PEP 594)。


此模块允许您访问 OSS(开放声音系统)音频接口。OSS 可用于各种开源和商业类 Unix 系统,并且是 Linux 和最新版本的 FreeBSD 的标准音频接口。

在版本 3.3 中更改: 此模块中的操作现在会引发 OSError,之前会引发 IOError

另请参阅

开放声音系统程序员指南

OSS C API 的官方文档

此模块定义了由 OSS 设备驱动程序提供的许多常量;有关列表,请参阅 Linux 或 FreeBSD 上的 <sys/soundcard.h>

ossaudiodev 定义了以下变量和函数

exception ossaudiodev.OSSAudioError

此异常在某些错误情况下引发。参数是一个描述错误原因的字符串。

(如果 ossaudiodev 从系统调用(如 open()write()ioctl())接收到错误,它会引发 OSError。由 ossaudiodev 直接检测到的错误会导致 OSSAudioError。)

(为了向后兼容,异常类也可以作为 ossaudiodev.error 使用。)

ossaudiodev.open(mode)
ossaudiodev.open(device, mode)

打开一个音频设备并返回一个 OSS 音频设备对象。此对象支持许多类似文件的函数,例如 read()write()fileno()(尽管传统 Unix 读/写语义与 OSS 音频设备的语义之间存在细微差别)。它还支持许多音频专用函数;有关完整函数列表,请参见下文。

device 是要使用的音频设备文件名。如果未指定,此模块首先在环境变量 AUDIODEV 中查找要使用的设备。如果未找到,它将回退到 /dev/dsp

mode 是以下之一:'r' 表示只读(录制)访问,'w' 表示只写(播放)访问,'rw' 表示两者。由于许多声卡一次只允许一个进程打开录制器或播放器,因此最好只为需要的活动打开设备。此外,某些声卡是半双工的:它们可以打开以进行读取或写入,但不能同时进行两者。

请注意不寻常的调用语法:第一个参数是可选的,第二个参数是必需的。这是为了与旧的 linuxaudiodev 模块保持兼容,ossaudiodev 取代了该模块。

ossaudiodev.openmixer([device])

打开一个混音器设备并返回一个 OSS 混音器设备对象。device 是要使用的混音器设备文件名。如果未指定,此模块首先在环境变量 MIXERDEV 中查找要使用的设备。如果未找到,它将回退到 /dev/mixer

音频设备对象

在您可以写入或读取音频设备之前,您必须按正确的顺序调用三个函数

  1. setfmt() 用于设置输出格式

  2. channels() 用于设置通道数量

  3. speed() 用于设置采样率

或者,您可以使用 setparameters() 函数一次设置所有三个音频参数。这更方便,但在某些情况下可能不如灵活。

open() 返回的音频设备对象定义了以下函数和(只读)属性

oss_audio_device.close()

显式关闭音频设备。完成写入或读取音频设备后,您应该显式关闭它。关闭的设备无法再次使用。

oss_audio_device.fileno()

返回与设备关联的文件描述符。

oss_audio_device.read(size)

从音频输入读取size字节并将其作为 Python 字符串返回。与大多数 Unix 设备驱动程序不同,处于阻塞模式(默认)的 OSS 音频设备将阻塞 read() 直到所有请求的数据都可用。

oss_audio_device.write(data)

字节类对象 data 写入音频设备并返回写入的字节数。如果音频设备处于阻塞模式(默认),则始终写入所有数据(同样,这与通常的 Unix 设备语义不同)。如果设备处于非阻塞模式,则可能无法写入一些数据——请参阅 writeall()

在 3.5 版更改: 现在接受可写的 字节类对象

oss_audio_device.writeall(data)

字节类对象 data 写入音频设备:等待音频设备能够接受数据,写入尽可能多的数据,并重复此操作,直到完全写入data。如果设备处于阻塞模式(默认),则这与 write() 的效果相同;writeall() 仅在非阻塞模式下有用。没有返回值,因为写入的数据量始终等于提供的数据量。

在 3.5 版更改: 现在接受可写的 字节类对象

在 3.2 版更改: 音频设备对象还支持上下文管理协议,即它们可以在 with 语句中使用。

以下方法分别对应一个 ioctl() 系统调用。对应关系很明显:例如,setfmt() 对应于 SNDCTL_DSP_SETFMT ioctl,而 sync() 对应于 SNDCTL_DSP_SYNC(这在查阅 OSS 文档时很有用)。如果底层的 ioctl() 失败,它们都会引发 OSError

oss_audio_device.nonblock()

将设备置于非阻塞模式。一旦进入非阻塞模式,就无法将其恢复为阻塞模式。

oss_audio_device.getfmts()

返回声卡支持的音频输出格式的位掩码。OSS 支持的一些格式是

格式

描述

AFMT_MU_LAW

对数编码(由 Sun .au 文件和 /dev/audio 使用)

AFMT_A_LAW

对数编码

AFMT_IMA_ADPCM

交互式多媒体协会定义的 4:1 压缩格式

AFMT_U8

无符号 8 位音频

AFMT_S16_LE

有符号 16 位音频,小端字节序(如 Intel 处理器使用)

AFMT_S16_BE

有符号 16 位音频,大端字节序(如 68k、PowerPC、Sparc 使用)

AFMT_S8

有符号 8 位音频

AFMT_U16_LE

无符号 16 位小端音频

AFMT_U16_BE

无符号 16 位大端音频

请参阅 OSS 文档以获取音频格式的完整列表,并注意大多数设备仅支持这些格式的子集。一些较旧的设备仅支持 AFMT_U8;如今最常用的格式是 AFMT_S16_LE

oss_audio_device.setfmt(format)

尝试将当前音频格式设置为format——请参阅 getfmts() 以获取列表。返回设备设置为的音频格式,这可能与请求的格式不同。也可以用来返回当前音频格式——通过传递“音频格式” AFMT_QUERY 来实现。

oss_audio_device.channels(nchannels)

将输出通道数设置为nchannels。值为 1 表示单声道声音,2 表示立体声。一些设备可能具有超过 2 个通道,而一些高端设备可能不支持单声道。返回设备设置为的通道数。

oss_audio_device.speed(samplerate)

尝试将音频采样率设置为每秒samplerate个样本。返回实际设置的速率。大多数声卡不支持任意采样率。常见的速率是

速率

描述

8000

/dev/audio 的默认速率

11025

语音录制

22050

44100

CD 音质音频(以 16 位/样本和 2 个通道)

96000

DVD 音质音频(以 24 位/样本)

oss_audio_device.sync()

等待声卡播放完缓冲区中的所有字节。(这在关闭设备时会隐式发生。)OSS 文档建议关闭并重新打开设备,而不是使用 sync()

oss_audio_device.reset()

立即停止播放或录制,并将设备恢复到可以接受命令的状态。OSS 文档建议在调用 reset() 后关闭并重新打开设备。

oss_audio_device.post()

告诉驱动程序输出可能会有暂停,使设备能够更智能地处理暂停。您可以在播放完点声音效果后、等待用户输入之前或进行磁盘 I/O 之前使用此方法。

以下便捷方法组合了多个 ioctl,或一个 ioctl 和一些简单的计算。

oss_audio_device.setparameters(format, nchannels, samplerate[, strict=False])

在一个方法调用中设置关键音频采样参数——采样格式、声道数和采样率。formatnchannelssamplerate 应与 setfmt()channels()speed() 方法中指定的一致。如果 strict 为真,setparameters() 会检查每个参数是否实际设置为请求的值,如果没有则会引发 OSSAudioError。返回一个元组 (format, nchannels, samplerate),指示设备驱动程序实际设置的参数值(即与 setfmt()channels()speed() 的返回值相同)。

例如,

(fmt, channels, rate) = dsp.setparameters(fmt, channels, rate)

等效于

fmt = dsp.setfmt(fmt)
channels = dsp.channels(channels)
rate = dsp.rate(rate)
oss_audio_device.bufsize()

返回硬件缓冲区的大小,以样本为单位。

oss_audio_device.obufcount()

返回硬件缓冲区中尚未播放的样本数量。

oss_audio_device.obuffree()

返回可以在不阻塞的情况下排队到硬件缓冲区以播放的样本数量。

音频设备对象还支持几个只读属性

oss_audio_device.closed

布尔值,指示设备是否已关闭。

oss_audio_device.name

包含设备文件名称的字符串。

oss_audio_device.mode

文件的 I/O 模式,可以是 "r""rw""w"

混音器设备对象

混音器对象提供两个类似文件的方法

oss_mixer_device.close()

此方法关闭打开的混音器设备文件。在此文件关闭后,任何进一步尝试使用混音器都会引发 OSError

oss_mixer_device.fileno()

返回打开的混音器设备文件的句柄编号。

Changed in version 3.2: 混音器对象还支持上下文管理协议。

其余方法特定于音频混音

oss_mixer_device.controls()

此方法返回一个位掩码,指定可用的混音器控件(“控件”是可混音的特定“通道”,例如 SOUND_MIXER_PCMSOUND_MIXER_SYNTH)。此位掩码指示所有可用混音器控件的子集——在模块级别定义的 SOUND_MIXER_* 常量。要确定当前混音器对象是否支持 PCM 混音器,请使用以下 Python 代码

mixer=ossaudiodev.openmixer()
if mixer.controls() & (1 << ossaudiodev.SOUND_MIXER_PCM):
    # PCM is supported
    ... code ...

对于大多数目的,SOUND_MIXER_VOLUME(主音量)和 SOUND_MIXER_PCM 控件应该足够了——但使用混音器的代码在选择混音器控件时应该灵活。例如,在 Gravis Ultrasound 上,SOUND_MIXER_VOLUME 不存在。

oss_mixer_device.stereocontrols()

返回一个位掩码,指示立体声混音器控件。如果设置了位,则相应的控件为立体声;如果未设置,则控件为单声道或不受混音器支持(与 controls() 结合使用以确定哪些控件)。

有关从位掩码获取数据的示例,请参阅 controls() 函数的代码示例。

oss_mixer_device.reccontrols()

返回一个位掩码,指定可用于录音的混音器控件。有关从位掩码读取的示例,请参阅 controls() 的代码示例。

oss_mixer_device.get(control)

返回给定混音器控件的音量。返回的音量是一个 2 元组 (left_volume,right_volume)。音量指定为从 0(静音)到 100(全音量)的数字。如果控件为单声道,则仍返回一个 2 元组,但两个音量相同。

如果指定了无效控件,则引发 OSSAudioError,如果指定了不受支持的控件,则引发 OSError

oss_mixer_device.set(control, (left, right))

将给定混音器控件的音量设置为 (left,right)leftright 必须是整数,介于 0(静音)和 100(全音量)之间。成功后,新的音量将作为 2 元组返回。请注意,这可能与指定的音量不完全相同,因为某些声卡混音器的分辨率有限。

如果指定了无效的混音器控件,或者指定的音量超出范围,则引发 OSSAudioError

oss_mixer_device.get_recsrc()

此方法返回一个位掩码,指示当前用作录音源的控件。

oss_mixer_device.set_recsrc(bitmask)

调用此函数以指定录音源。如果成功,则返回一个位掩码,指示新的录音源(或源);如果指定了无效源,则引发 OSError。要将当前录音源设置为麦克风输入

mixer.setrecsrc (1 << ossaudiodev.SOUND_MIXER_MIC)