• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# OpenSL ES音频播放开发指导
2
3## 简介
4
5开发者可以通过本文档了解在**OpenHarmony**中如何使用**OpenSL ES**进行音频播放相关操作;当前仅实现了部分[**OpenSL ES**接口](https://gitee.com/openharmony/third_party_opensles/blob/master/api/1.0.1/OpenSLES.h),因此调用未实现接口后会返回**SL_RESULT_FEATURE_UNSUPPORTED**
6
7## 开发指导
8
9以下步骤描述了在**OpenHarmony**如何使用**OpenSL ES**开发音频播放功能:
10
111. 添加头文件
12
13    ```c++
14    #include <OpenSLES.h>
15    #include <OpenSLES_OpenHarmony.h>
16    #include <OpenSLES_Platform.h>
17    ```
18
192. 使用 **slCreateEngine** 接口和获取 **engine** 实例
20
21    ```c++
22    SLObjectItf engineObject = nullptr;
23    slCreateEngine(&engineObject, 0, nullptr, 0, nullptr, nullptr);
24    (*engineObject)->Realize(engineObject, SL_BOOLEAN_FALSE);
25    ```
26
273. 获取接口 **SL_IID_ENGINE** 的 **engineEngine** 实例
28
29    ```c++
30    SLEngineItf engineEngine = nullptr;
31    (*engineObject)->GetInterface(engineObject, SL_IID_ENGINE, &engineEngine);
32    ```
33
344. 配置播放器信息,创建 **AudioPlayer**
35
36    ```c++
37    SLDataLocator_BufferQueue slBufferQueue = {
38        SL_DATALOCATOR_BUFFERQUEUE,
39        0
40    };
41
42    // 具体参数需要根据音频文件格式进行适配
43    SLDataFormat_PCM pcmFormat = {
44        SL_DATAFORMAT_PCM,
45        2,
46        48000,
47        16,
48        0,
49        0,
50        0
51    };
52    SLDataSource slSource = {&slBufferQueue, &pcmFormat};
53
54    SLObjectItf pcmPlayerObject = nullptr;
55    (*engineEngine)->CreateAudioPlayer(engineEngine, &pcmPlayerObject, &slSource, null, 0, nullptr, nullptr);
56    (*pcmPlayerObject)->Realize(pcmPlayerObject, SL_BOOLEAN_FALSE);
57    ```
58
595. 获取接口 **SL_IID_OH_BUFFERQUEUE** 的 **bufferQueueItf** 实例
60
61    ```c++
62    SLOHBufferQueueItf bufferQueueItf;
63    (*pcmPlayerObject)->GetInterface(pcmPlayerObject, SL_IID_OH_BUFFERQUEUE, &bufferQueueItf);
64    ```
65
666. 打开音频文件,注册 **BufferQueueCallback** 回调
67
68    ```c++
69    FILE *wavFile_ = nullptr;
70
71    static void BufferQueueCallback (SLOHBufferQueueItf bufferQueueItf, void *pContext, SLuint32 size)
72    {
73        FILE *wavFile = (FILE *)pContext;
74        if (!feof(wavFile)) {
75            SLuint8 *buffer = nullptr;
76            SLuint32 pSize = 0;
77            (*bufferQueueItf)->GetBuffer(bufferQueueItf, &buffer, pSize);
78            //从文件读取数据
79            fread(buffer, 1, size, wavFile);
80            (*bufferQueueItf)->Enqueue(bufferQueueItf, buffer, size);
81        }
82        return;
83    }
84
85    // wavFile_ 需要设置为用户想要播放的文件描述符
86    wavFile_ = fopen(path, "rb");
87    (*bufferQueueItf)->RegisterCallback(bufferQueueItf, BufferQueueCallback, wavFile_);
88    ```
89
907. 获取接口 **SL_PLAYSTATE_PLAYING** 的 **playItf** 实例,开始播放
91
92    ```c++
93    SLPlayItf playItf = nullptr;
94    (*pcmPlayerObject)->GetInterface(pcmPlayerObject, SL_IID_PLAY, &playItf);
95    (*playItf)->SetPlayState(playItf, SL_PLAYSTATE_PLAYING);
96    ```
97
988. 结束音频播放
99
100    ```c++
101    (*playItf)->SetPlayState(playItf, SL_PLAYSTATE_STOPPED);
102    (*pcmPlayerObject)->Destroy(pcmPlayerObject);
103    (*engineObject)->Destroy(engineObject);
104    ```