1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef OBOE_STREAM_CALLBACK_H 18 #define OBOE_STREAM_CALLBACK_H 19 20 #include "oboe/Definitions.h" 21 22 namespace oboe { 23 24 class AudioStream; 25 26 /** 27 * AudioStreamCallback defines a callback interface for: 28 * 29 * 1) moving data to/from an audio stream using `onAudioReady` 30 * 2) being alerted when a stream has an error using `onError*` methods 31 * 32 */ 33 class AudioStreamCallback { 34 public: 35 virtual ~AudioStreamCallback() = default; 36 37 /** 38 * A buffer is ready for processing. 39 * 40 * For an output stream, this function should render and write numFrames of data 41 * in the stream's current data format to the audioData buffer. 42 * 43 * For an input stream, this function should read and process numFrames of data 44 * from the audioData buffer. 45 * 46 * The audio data is passed through the buffer. So do NOT call read() or 47 * write() on the stream that is making the callback. 48 * 49 * Note that numFrames can vary unless AudioStreamBuilder::setFramesPerCallback() 50 * is called. 51 * 52 * Also note that this callback function should be considered a "real-time" function. 53 * It must not do anything that could cause an unbounded delay because that can cause the 54 * audio to glitch or pop. 55 * 56 * These are things the function should NOT do: 57 * <ul> 58 * <li>allocate memory using, for example, malloc() or new</li> 59 * <li>any file operations such as opening, closing, reading or writing</li> 60 * <li>any network operations such as streaming</li> 61 * <li>use any mutexes or other synchronization primitives</li> 62 * <li>sleep</li> 63 * <li>oboeStream->stop(), pause(), flush() or close()</li> 64 * <li>oboeStream->read()</li> 65 * <li>oboeStream->write()</li> 66 * </ul> 67 * 68 * The following are OK to call from the data callback: 69 * <ul> 70 * <li>oboeStream->get*()</li> 71 * <li>oboe::convertToText()</li> 72 * <li>oboeStream->setBufferSizeInFrames()</li> 73 * </ul> 74 * 75 * If you need to move data, eg. MIDI commands, in or out of the callback function then 76 * we recommend the use of non-blocking techniques such as an atomic FIFO. 77 * 78 * @param oboeStream pointer to the associated stream 79 * @param audioData buffer containing input data or a place to put output data 80 * @param numFrames number of frames to be processed 81 * @return DataCallbackResult::Continue or DataCallbackResult::Stop 82 */ 83 virtual DataCallbackResult onAudioReady( 84 AudioStream *oboeStream, 85 void *audioData, 86 int32_t numFrames) = 0; 87 88 /** 89 * This will be called when an error occurs on a stream or when the stream is disconnected. 90 * 91 * Note that this will be called on a different thread than the onAudioReady() thread. 92 * This thread will be created by Oboe. 93 * 94 * The underlying stream will already be stopped by Oboe but not yet closed. 95 * So the stream can be queried. 96 * 97 * Do not close or delete the stream in this method because it will be 98 * closed after this method returns. 99 * 100 * @param oboeStream pointer to the associated stream 101 * @param error 102 */ onErrorBeforeClose(AudioStream *,Result)103 virtual void onErrorBeforeClose(AudioStream* /* oboeStream */, Result /* error */) {} 104 105 /** 106 * This will be called when an error occurs on a stream or when the stream is disconnected. 107 * The underlying AAudio or OpenSL ES stream will already be stopped AND closed by Oboe. 108 * So the underlying stream cannot be referenced. 109 * But you can still query most parameters. 110 * 111 * This callback could be used to reopen a new stream on another device. 112 * You can safely delete the old AudioStream in this method. 113 * 114 * @param oboeStream pointer to the associated stream 115 * @param error 116 */ onErrorAfterClose(AudioStream *,Result)117 virtual void onErrorAfterClose(AudioStream* /* oboeStream */, Result /* error */) {} 118 119 }; 120 121 } // namespace oboe 122 123 #endif //OBOE_STREAM_CALLBACK_H 124