• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Using OHAudio for Audio Playback (C/C++)
2
3**OHAudio** is a set of native APIs introduced in API version 10. These APIs are normalized in design and support both common and low-latency audio channels.
4
5## Prerequisites
6
7To use the playback or recording capability of **OHAudio**, you must first import the corresponding header files.
8
9### Linking the Dynamic Library in the CMake Script
10
11``` cmake
12target_link_libraries(sample PUBLIC libohaudio.so)
13```
14### Adding Header Files
15Specifically, to use APIs for audio playback, import <[native_audiostreambuilder.h](../reference/native-apis/native__audiostreambuilder_8h.md)> and <[native_audiorenderer.h](../reference/native-apis/native__audiorenderer_8h.md)>.
16
17```cpp
18#include <ohaudio/native_audiorenderer.h>
19#include <ohaudio/native_audiostreambuilder.h>
20```
21
22## Building Audio Streams
23
24**OHAudio** provides the **OH_AudioStreamBuilder** class, which complies with the builder design pattern and is used to build audio streams. You need to specify [OH_AudioStream_Type](../reference/native-apis/_o_h_audio.md#oh_audiostream_type) based on your service scenarios.
25
26**OH_AudioStream_Type** can be set to either of the following:
27
28- AUDIOSTREAM_TYPE_RENDERER
29- AUDIOSTREAM_TYPE_CAPTURER
30
31The following code snippet shows how to use [OH_AudioStreamBuilder_Create](../reference/native-apis/_o_h_audio.md#oh_audiostreambuilder_create) to create a builder:
32
33```
34OH_AudioStreamBuilder* builder;
35OH_AudioStreamBuilder_Create(&builder, streamType);
36```
37
38After the audio service is complete, call [OH_AudioStreamBuilder_Destroy](../reference/native-apis/_o_h_audio.md#oh_audiostreambuilder_destroy) to destroy the builder.
39
40```
41OH_AudioStreamBuilder_Destroy(builder);
42```
43
44## How to Develop
45
46Read [OHAudio](../reference/native-apis/_o_h_audio.md) for the API reference.
47
48The following walks you through how to implement simple playback:
49
501. Create an audio stream builder.
51
52    ```c++
53    OH_AudioStreamBuilder* builder;
54    OH_AudioStreamBuilder_Create(&builder, AUDIOSTREAM_TYPE_RENDERER);
55    ```
56
572. Set audio stream parameters.
58
59    After creating the builder for audio playback, set the parameters required.
60
61    ```c++
62    // Set the audio sampling rate.
63    OH_AudioStreamBuilder_SetSamplingRate(builder, 48000);
64    // Set the number of audio channels.
65    OH_AudioStreamBuilder_SetChannelCount(builder, 2);
66    // Set the audio sampling format.
67    OH_AudioStreamBuilder_SetSampleFormat(builder, (OH_AudioStream_SampleFormat)0);
68    // Set the encoding type of the audio stream.
69    OH_AudioStreamBuilder_SetEncodingType(builder, (OH_AudioStream_EncodingType)0);
70    // Set the usage scenario of the audio renderer.
71    OH_AudioStreamBuilder_SetRendererInfo(builder, (OH_AudioStream_Usage)1);
72    ```
73
74    Note that the audio data to play is written through callbacks. You must call **OH_AudioStreamBuilder_SetRendererCallback** to implement the callbacks. For details about the declaration of the callback functions, see [OH_AudioRenderer_Callbacks](../reference/native-apis/_o_h_audio.md#oh_audiorenderer_callbacks).
75
76
773. Set the callback functions.
78
79    ```c++
80    OH_AudioRenderer_Callbacks callbacks;
81    // Set callbacks for the audio renderer.
82    OH_AudioStreamBuilder_SetRendererCallback(builder, callbacks, nullptr);
83    ```
84
854. Create an audio renderer instance.
86
87    ```c++
88    OH_AudioRenderer* audioRenderer;
89    OH_AudioStreamBuilder_GenerateRenderer(builder, &audioRenderer);
90    ```
91
925. Use the audio renderer.
93
94    You can use the APIs listed below to control the audio streams.
95
96    | API                                                        | Description        |
97    | ------------------------------------------------------------ | ------------ |
98    | OH_AudioStream_Result OH_AudioRenderer_Start(OH_AudioRenderer* renderer) | Starts the audio renderer.    |
99    | OH_AudioStream_Result OH_AudioRenderer_Pause(OH_AudioRenderer* renderer) | Pauses the audio renderer.    |
100    | OH_AudioStream_Result OH_AudioRenderer_Stop(OH_AudioRenderer* renderer) | Stops the audio renderer.    |
101    | OH_AudioStream_Result OH_AudioRenderer_Flush(OH_AudioRenderer* renderer) | Flushes written audio data.|
102    | OH_AudioStream_Result OH_AudioRenderer_Release(OH_AudioRenderer* renderer) | Releases the audio renderer instance.|
103
1046. Destroy the audio stream builder.
105
106    When the builder is no longer used, release related resources.
107
108    ```c++
109    OH_AudioStreamBuilder_Destroy(builder);
110    ```
111## Sample Code
112
113```cpp
114#include <iostream>
115#include <cstdint>
116#include <cstdio>
117#include <cstring>
118#include <thread>
119#include <chrono>
120#include <ctime>
121#include <ohaudio/native_audiorenderer.h>
122#include <ohaudio/native_audiostreambuilder.h>
123
124#ifdef __cplusplus
125extern "C" {
126#endif
127namespace AudioTestConstants {
128constexpr int32_t WAIT_INTERVAL = 1000;
129} // namespace AudioTestConstants
130
131// Ensure that the file in the directory can be played.
132std::string g_filePath = "/data/data/oh_test_audio.pcm";
133FILE *g_file = nullptr;
134bool g_readEnd = false;
135// Audio sampling rate.
136int32_t g_samplingRate = 48000;
137// Number of audio channels.
138int32_t g_channelCount = 2;
139// Audio scenario. The value 0 indicates the normal scenario, and 1 indicates the low-latency scenario.
140int32_t g_latencyMode = 0;
141// Audio sample format.
142int32_t g_sampleFormat = 1;
143
144// Callback, through which the played audio data will be written.
145static int32_t AudioRendererOnWriteData(OH_AudioRenderer *capturer, void *userData, void *buffer, int32_t bufferLen) {
146    size_t readCount = fread(buffer, bufferLen, 1, g_file);
147    if (!readCount) {
148        if (ferror(g_file)) {
149            printf("Error reading myfile");
150        } else if (feof(g_file)) {
151            printf("EOF found");
152            g_readEnd = true;
153        }
154    }
155    return 0;
156}
157
158void PlayerTest() {
159    OH_AudioStream_Result ret;
160
161    // 1. Create an audio stream builder.
162    OH_AudioStreamBuilder *builder;
163    OH_AudioStream_Type type = AUDIOSTREAM_TYPE_RENDERER;
164    ret = OH_AudioStreamBuilder_Create(&builder, type);
165
166    // 2. Set the parameters required by the audio stream.
167    OH_AudioStreamBuilder_SetSamplingRate(builder, g_samplingRate);
168    OH_AudioStreamBuilder_SetChannelCount(builder, g_channelCount);
169    OH_AudioStreamBuilder_SetLatencyMode(builder, (OH_AudioStream_LatencyMode)g_latencyMode);
170    OH_AudioStreamBuilder_SetSampleFormat(builder, (OH_AudioStream_SampleFormat)g_sampleFormat);
171
172    // Set the callback, through which the played audio data will be written.
173    OH_AudioRenderer_Callbacks callbacks;
174    callbacks.OH_AudioRenderer_OnWriteData = AudioRendererOnWriteData;
175    ret = OH_AudioStreamBuilder_SetRendererCallback(builder, callbacks, nullptr);
176
177    // 3. Create an audio renderer instance.
178    OH_AudioRenderer *audioRenderer;
179    ret = OH_AudioStreamBuilder_GenerateRenderer(builder, &audioRenderer);
180
181    // 4. Start playback.
182    ret = OH_AudioRenderer_Start(audioRenderer);
183
184    int timer = 0;
185    while (!g_readEnd) {
186        std::this_thread::sleep_for(std::chrono::milliseconds(AudioTestConstants::WAIT_INTERVAL));
187        int64_t frames;
188        OH_AudioRenderer_GetFramesWritten(audioRenderer, &frames);
189        printf("Wait for the audio to finish playing.(..%d s) frames:%ld\n", ++timer, frames);
190        int64_t framePosition;
191        int64_t timestamp;
192        OH_AudioRenderer_GetTimestamp(audioRenderer, CLOCK_MONOTONIC, &framePosition, &timestamp);
193        printf("framePosition %ld timestamp:%ld\n", framePosition, timestamp);
194    }
195    // 5. Stop the playback.
196    ret = OH_AudioRenderer_Stop(audioRenderer);
197
198    // Release the audio renderer instance.
199    ret = OH_AudioRenderer_Release(audioRenderer);
200
201    // 6. Destroy the audio stream builder.
202    ret = OH_AudioStreamBuilder_Destroy(builder);
203}
204
205int main() {
206    // Open the file before playback.
207    g_file = fopen(g_filePath.c_str(), "rb");
208    if (g_file == nullptr) {
209        printf("OHAudioRendererTest: Unable to open file \n");
210        return 0;
211    }
212    // Start playback.
213    PlayerTest();
214    // Close the file after the playback is complete.
215    fclose(g_file);
216    g_file = nullptr;
217    return 0;
218}
219
220#ifdef __cplusplus
221}
222#endif
223```
224
225## Setting the Low Latency Mode
226
227If the device supports the low-latency channel, you can use the low-latency mode to create a player for a higher-quality audio experience.
228
229The development process is similar to that in the common playback scenario. The only difference is that you need to set the low delay mode by calling [OH_AudioStreamBuilder_SetLatencyMode()](../reference/native-apis/_o_h_audio.md#oh_audiostreambuilder_setlatencymode) when creating an audio stream builder.
230
231The code snippet is as follows:
232
233```C
234OH_AudioStream_LatencyMode latencyMode = AUDIOSTREAM_LATENCY_MODE_FAST;
235OH_AudioStreamBuilder_SetLatencyMode(builder, latencyMode);
236```
237