开始

警告:OpenSL ES 已被弃用。开发者应使用 GitHub 上提供的开源 Oboe 库。Oboe 是一个 C++ 封装容器,提供与 AAudio 非常相似的 API。Oboe 在 AAudio 可用时对其进行调用,并在 AAudio 不可用时回退到 OpenSL ES。

本部分提供开始使用 OpenSL ES API 时所需了解的信息。

向您的应用添加 OpenSL ES

您可以从 C 和 C++ 代码调用 OpenSL ES。若要向您的应用添加核心 OpenSL ES 功能集,请添加 OpenSLES.h 头文件:

#include <SLES/OpenSLES.h>

若还要添加 OpenSL ES Android 扩展,请添加 OpenSLES_Android.h 头文件:

#include <SLES/OpenSLES_Android.h>

添加 OpenSLES_Android.h 头文件后,以下头文件将自动包括在内:

#include <SLES/OpenSLES_AndroidConfiguration.h>
#include <SLES/OpenSLES_AndroidMetadata.h>

注意:这些头文件不是必需的,显示它们是为了帮助您学习此 API。

构建和调试

您可以在用作 NDK 构建系统的一个 Makefile 的 Android.mk 文件中指定 OpenSL ES,从而将 OpenSL ES 添加到您的 build 中。将以下行添加到 Android.mk 中:

LOCAL_LDLIBS += -lOpenSLES

为了稳健地进行调试,建议您检查大部分 OpenSL ES API 所返回的 SLresult 值。您可以使用断言或更高级的错误处理逻辑进行调试;虽然其中一种或者另一种方式可能更适合给定用例,但在使用 OpenSL ES 时哪种方式都没有任何内在优势。

我们的示例中使用断言,因为断言有助于捕获可揭示编码错误的不切实际的情况。我们已经针对正式版中更可能出现的其他情况进行明确的错误处理。

在许多 API 错误出现时,系统不仅会返回非零结果代码,还会生成日志条目。此类日志条目能够提供额外的详细信息,对相对复杂的 API(如 Engine::CreateAudioPlayer)尤其有用。

您可以从命令行或 Android Studio 查看日志。如需从命令行检查日志,请输入以下命令:

$ adb logcat

若要从 Android Studio 检查日志,请依次选择 View > Tool Windows > Logcat。如需了解详情,请参阅使用 Logcat 写入和查看日志

示例代码

我们建议您使用受支持且经过测试的示例代码,这些代码位于 android-ndk GitHub 代码库的 audio-echonative-audio 文件夹中,您可以将其用作范本来编写自己的代码。

注意:OpenSL ES 1.0.1 规范在附录中提供示例代码(请参阅 Khronos OpenSL ES Registry 了解更多详情)。不过,“附录 B:示例代码”和“附录 C:用例示例代码”中的示例使用 Android 不支持的功能。某些示例中还存在排版错误,或者使用可能会发生改变的 API。参考这些示例时请务必谨慎;尽管这些代码对于理解完整的 OpenSL ES 标准可能非常有帮助,但不应照搬用在 Android 中。

音频内容

为应用打包音频内容的方法有很多种,下面介绍了其中几种:

  • 资源:将音频文件置于 res/raw/ 文件夹后,可以通过 Resources 的关联 API 轻松访问这些文件。不过,无法对资源进行直接原生访问,所以您必须编写 Java 编程语言代码,将其复制出来后再使用。
  • 资产:将您的音频文件置于 assets/ 文件夹后,可以通过 Android 原生资产管理器 API 直接访问这些文件。如需详细了解这些 API,请参阅头文件 android/asset_manager.handroid/asset_manager_jni.h。位于 android-ndk GitHub 代码库的示例代码将这些原生资产管理器 API 与 Android 文件描述符数据定位器结合使用。
  • 网络:您可以使用 URI 数据定位器直接从网络播放音频内容。不过,请务必阅读安全与权限中介绍的内容。
  • 本地文件系统:对于本地文件,URI 数据定位器支持 file: 架构,前提是这些文件可供应用访问。请注意,Android 安全框架限制通过 Linux 用户 ID 和组 ID 机制访问文件。
  • 录制的内容:您的应用可以从麦克风输入录制音频数据,存储此内容,然后回放。示例代码使用此方法来处理“回放”剪辑。
  • 编译和链接的内嵌内容:您可以将音频内容直接链接至共享库,然后使用支持缓冲区队列数据定位器的音频播放器播放。这最适合 PCM 格式的短剪辑。示例代码使用此方式处理 Hello 和 Android 剪辑。PCM 数据已通过 bin2c 工具(未提供)转换为十六进制字符串。
  • 实时合成:您的应用可以动态合成 PCM 数据,然后使用支持缓冲区队列数据定位器的音频播放器播放。这是一种相对先进的技术,详细的音频合成介绍不在本文讨论的范围内。

注意:为应用寻找或创建有用的音频内容不在本文讨论的范围内。您可以使用网页搜索字词(例如,“互动音频”、“游戏音频”、“音效设计”和“音频编程”)查找更多信息。

注意:您必须确保在法律允许的情况下播放或录制内容。录制内容时,需要注意一些隐私权注意事项。

代码示例

我们的 GitHub 页面提供了以下示例应用:

  • audio-echo 创建从输入到输出的往返循环。
  • native-audio 是一个简单的音频录制器/播放器。

OpenSL ES 的 Android NDK 实现与 OpenSL ES 1.0.1 的参考规范有诸多不同。从 OpenSL ES 参考规范中直接复制的示例代码之所以无法在您的 Android 应用中使用,这些差异就是一个很重要的原因。

如需详细了解参考规范与 Android 实现之间的差异,请参阅 OpenSL ES for Android