diff --git a/app/build.gradle b/app/build.gradle index 754d42eb..d33fafe5 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -101,4 +101,5 @@ dependencies { implementation 'androidx.navigation:navigation-ui:2.4.2' implementation 'androidx.recyclerview:recyclerview:1.2.1' implementation 'androidx.swiperefreshlayout:swiperefreshlayout:1.1.0' + implementation 'com.google.oboe:oboe:1.6.1' } diff --git a/app/src/main/cpp/CMakeLists.txt b/app/src/main/cpp/CMakeLists.txt index ca2d89b9..1ccae7fb 100644 --- a/app/src/main/cpp/CMakeLists.txt +++ b/app/src/main/cpp/CMakeLists.txt @@ -2,13 +2,6 @@ cmake_minimum_required(VERSION 3.21) project(love-android LANGUAGES C CXX) -# Oboe -set(Oboe_DIR "${CMAKE_CURRENT_SOURCE_DIR}/oboe") - -# Set LOVE set(MEGA_LOVE "${CMAKE_CURRENT_SOURCE_DIR}/love") -# Finally, load megasource that will handle everything. add_subdirectory(megasource) - -# TODO: Third-party libraries. diff --git a/app/src/main/cpp/oboe/include/.DS_Store b/app/src/main/cpp/oboe/include/.DS_Store deleted file mode 100644 index f904b69f..00000000 Binary files a/app/src/main/cpp/oboe/include/.DS_Store and /dev/null differ diff --git a/app/src/main/cpp/oboe/include/oboe/AudioStream.h b/app/src/main/cpp/oboe/include/oboe/AudioStream.h deleted file mode 100644 index 825ffc89..00000000 --- a/app/src/main/cpp/oboe/include/oboe/AudioStream.h +++ /dev/null @@ -1,567 +0,0 @@ -/* - * Copyright 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_STREAM_H_ -#define OBOE_STREAM_H_ - -#include -#include -#include -#include -#include "oboe/Definitions.h" -#include "oboe/ResultWithValue.h" -#include "oboe/AudioStreamBuilder.h" -#include "oboe/AudioStreamBase.h" - -/** WARNING - UNDER CONSTRUCTION - THIS API WILL CHANGE. */ - -namespace oboe { - -/** - * The default number of nanoseconds to wait for when performing state change operations on the - * stream, such as `start` and `stop`. - * - * @see oboe::AudioStream::start - */ -constexpr int64_t kDefaultTimeoutNanos = (2000 * kNanosPerMillisecond); - -/** - * Base class for Oboe C++ audio stream. - */ -class AudioStream : public AudioStreamBase { - friend class AudioStreamBuilder; // allow access to setWeakThis() and lockWeakThis() -public: - - AudioStream() {} - - /** - * Construct an `AudioStream` using the given `AudioStreamBuilder` - * - * @param builder containing all the stream's attributes - */ - explicit AudioStream(const AudioStreamBuilder &builder); - - virtual ~AudioStream() = default; - - /** - * Open a stream based on the current settings. - * - * Note that we do not recommend re-opening a stream that has been closed. - * TODO Should we prevent re-opening? - * - * @return - */ - virtual Result open() { - return Result::OK; // Called by subclasses. Might do more in the future. - } - - /** - * Close the stream and deallocate any resources from the open() call. - */ - virtual Result close(); - - /** - * Start the stream. This will block until the stream has been started, an error occurs - * or `timeoutNanoseconds` has been reached. - */ - virtual Result start(int64_t timeoutNanoseconds = kDefaultTimeoutNanos); - - /** - * Pause the stream. This will block until the stream has been paused, an error occurs - * or `timeoutNanoseconds` has been reached. - */ - virtual Result pause(int64_t timeoutNanoseconds = kDefaultTimeoutNanos); - - /** - * Flush the stream. This will block until the stream has been flushed, an error occurs - * or `timeoutNanoseconds` has been reached. - */ - virtual Result flush(int64_t timeoutNanoseconds = kDefaultTimeoutNanos); - - /** - * Stop the stream. This will block until the stream has been stopped, an error occurs - * or `timeoutNanoseconds` has been reached. - */ - virtual Result stop(int64_t timeoutNanoseconds = kDefaultTimeoutNanos); - - /* Asynchronous requests. - * Use waitForStateChange() if you need to wait for completion. - */ - - /** - * Start the stream asynchronously. Returns immediately (does not block). Equivalent to calling - * `start(0)`. - */ - virtual Result requestStart() = 0; - - /** - * Pause the stream asynchronously. Returns immediately (does not block). Equivalent to calling - * `pause(0)`. - */ - virtual Result requestPause() = 0; - - /** - * Flush the stream asynchronously. Returns immediately (does not block). Equivalent to calling - * `flush(0)`. - */ - virtual Result requestFlush() = 0; - - /** - * Stop the stream asynchronously. Returns immediately (does not block). Equivalent to calling - * `stop(0)`. - */ - virtual Result requestStop() = 0; - - /** - * Query the current state, eg. StreamState::Pausing - * - * @return state or a negative error. - */ - virtual StreamState getState() = 0; - - /** - * Wait until the stream's current state no longer matches the input state. - * The input state is passed to avoid race conditions caused by the state - * changing between calls. - * - * Note that generally applications do not need to call this. It is considered - * an advanced technique and is mostly used for testing. - * - *

-     * int64_t timeoutNanos = 500 * kNanosPerMillisecond; // arbitrary 1/2 second
-     * StreamState currentState = stream->getState();
-     * StreamState nextState = StreamState::Unknown;
-     * while (result == Result::OK && currentState != StreamState::Paused) {
-     *     result = stream->waitForStateChange(
-     *                                   currentState, &nextState, timeoutNanos);
-     *     currentState = nextState;
-     * }
-     * 
- * - * If the state does not change within the timeout period then it will - * return ErrorTimeout. This is true even if timeoutNanoseconds is zero. - * - * @param inputState The state we want to change away from. - * @param nextState Pointer to a variable that will be set to the new state. - * @param timeoutNanoseconds The maximum time to wait in nanoseconds. - * @return Result::OK or a Result::Error. - */ - virtual Result waitForStateChange(StreamState inputState, - StreamState *nextState, - int64_t timeoutNanoseconds) = 0; - - /** - * This can be used to adjust the latency of the buffer by changing - * the threshold where blocking will occur. - * By combining this with getXRunCount(), the latency can be tuned - * at run-time for each device. - * - * This cannot be set higher than getBufferCapacity(). - * - * @param requestedFrames requested number of frames that can be filled without blocking - * @return the resulting buffer size in frames (obtained using value()) or an error (obtained - * using error()) - */ - virtual ResultWithValue setBufferSizeInFrames(int32_t /* requestedFrames */) { - return Result::ErrorUnimplemented; - } - - /** - * An XRun is an Underrun or an Overrun. - * During playing, an underrun will occur if the stream is not written in time - * and the system runs out of valid data. - * During recording, an overrun will occur if the stream is not read in time - * and there is no place to put the incoming data so it is discarded. - * - * An underrun or overrun can cause an audible "pop" or "glitch". - * - * @return a result which is either Result::OK with the xRun count as the value, or a - * Result::Error* code - */ - virtual ResultWithValue getXRunCount() { - return ResultWithValue(Result::ErrorUnimplemented); - } - - /** - * @return true if XRun counts are supported on the stream - */ - virtual bool isXRunCountSupported() const = 0; - - /** - * Query the number of frames that are read or written by the endpoint at one time. - * - * @return burst size - */ - int32_t getFramesPerBurst() const { - return mFramesPerBurst; - } - - /** - * Get the number of bytes in each audio frame. This is calculated using the channel count - * and the sample format. For example, a 2 channel floating point stream will have - * 2 * 4 = 8 bytes per frame. - * - * @return number of bytes in each audio frame. - */ - int32_t getBytesPerFrame() const { return mChannelCount * getBytesPerSample(); } - - /** - * Get the number of bytes per sample. This is calculated using the sample format. For example, - * a stream using 16-bit integer samples will have 2 bytes per sample. - * - * @return the number of bytes per sample. - */ - int32_t getBytesPerSample() const; - - /** - * The number of audio frames written into the stream. - * This monotonic counter will never get reset. - * - * @return the number of frames written so far - */ - virtual int64_t getFramesWritten(); - - /** - * The number of audio frames read from the stream. - * This monotonic counter will never get reset. - * - * @return the number of frames read so far - */ - virtual int64_t getFramesRead(); - - /** - * Calculate the latency of a stream based on getTimestamp(). - * - * Output latency is the time it takes for a given frame to travel from the - * app to some type of digital-to-analog converter. If the DAC is external, for example - * in a USB interface or a TV connected by HDMI, then there may be additional latency - * that the Android device is unaware of. - * - * Input latency is the time it takes to a given frame to travel from an analog-to-digital - * converter (ADC) to the app. - * - * Note that the latency of an OUTPUT stream will increase abruptly when you write data to it - * and then decrease slowly over time as the data is consumed. - * - * The latency of an INPUT stream will decrease abruptly when you read data from it - * and then increase slowly over time as more data arrives. - * - * The latency of an OUTPUT stream is generally higher than the INPUT latency - * because an app generally tries to keep the OUTPUT buffer full and the INPUT buffer empty. - * - * @return a ResultWithValue which has a result of Result::OK and a value containing the latency - * in milliseconds, or a result of Result::Error*. - */ - virtual ResultWithValue calculateLatencyMillis() { - return ResultWithValue(Result::ErrorUnimplemented); - } - - /** - * Get the estimated time that the frame at `framePosition` entered or left the audio processing - * pipeline. - * - * This can be used to coordinate events and interactions with the external environment, and to - * estimate the latency of an audio stream. An example of usage can be found in the hello-oboe - * sample (search for "calculateCurrentOutputLatencyMillis"). - * - * The time is based on the implementation's best effort, using whatever knowledge is available - * to the system, but cannot account for any delay unknown to the implementation. - * - * @deprecated since 1.0, use AudioStream::getTimestamp(clockid_t clockId) instead, which - * returns ResultWithValue - * @param clockId the type of clock to use e.g. CLOCK_MONOTONIC - * @param framePosition the frame number to query - * @param timeNanoseconds an output parameter which will contain the presentation timestamp - */ - virtual Result getTimestamp(clockid_t /* clockId */, - int64_t* /* framePosition */, - int64_t* /* timeNanoseconds */) { - return Result::ErrorUnimplemented; - } - - /** - * Get the estimated time that the frame at `framePosition` entered or left the audio processing - * pipeline. - * - * This can be used to coordinate events and interactions with the external environment, and to - * estimate the latency of an audio stream. An example of usage can be found in the hello-oboe - * sample (search for "calculateCurrentOutputLatencyMillis"). - * - * The time is based on the implementation's best effort, using whatever knowledge is available - * to the system, but cannot account for any delay unknown to the implementation. - * - * @param clockId the type of clock to use e.g. CLOCK_MONOTONIC - * @return a FrameTimestamp containing the position and time at which a particular audio frame - * entered or left the audio processing pipeline, or an error if the operation failed. - */ - virtual ResultWithValue getTimestamp(clockid_t /* clockId */); - - // ============== I/O =========================== - /** - * Write data from the supplied buffer into the stream. This method will block until the write - * is complete or it runs out of time. - * - * If `timeoutNanoseconds` is zero then this call will not wait. - * - * @param buffer The address of the first sample. - * @param numFrames Number of frames to write. Only complete frames will be written. - * @param timeoutNanoseconds Maximum number of nanoseconds to wait for completion. - * @return a ResultWithValue which has a result of Result::OK and a value containing the number - * of frames actually written, or result of Result::Error*. - */ - virtual ResultWithValue write(const void* /* buffer */, - int32_t /* numFrames */, - int64_t /* timeoutNanoseconds */ ) { - return ResultWithValue(Result::ErrorUnimplemented); - } - - /** - * Read data into the supplied buffer from the stream. This method will block until the read - * is complete or it runs out of time. - * - * If `timeoutNanoseconds` is zero then this call will not wait. - * - * @param buffer The address of the first sample. - * @param numFrames Number of frames to read. Only complete frames will be read. - * @param timeoutNanoseconds Maximum number of nanoseconds to wait for completion. - * @return a ResultWithValue which has a result of Result::OK and a value containing the number - * of frames actually read, or result of Result::Error*. - */ - virtual ResultWithValue read(void* /* buffer */, - int32_t /* numFrames */, - int64_t /* timeoutNanoseconds */) { - return ResultWithValue(Result::ErrorUnimplemented); - } - - /** - * Get the underlying audio API which the stream uses. - * - * @return the API that this stream uses. - */ - virtual AudioApi getAudioApi() const = 0; - - /** - * Returns true if the underlying audio API is AAudio. - * - * @return true if this stream is implemented using the AAudio API. - */ - bool usesAAudio() const { - return getAudioApi() == AudioApi::AAudio; - } - - /** - * Only for debugging. Do not use in production. - * If you need to call this method something is wrong. - * If you think you need it for production then please let us know - * so we can modify Oboe so that you don't need this. - * - * @return nullptr or a pointer to a stream from the system API - */ - virtual void *getUnderlyingStream() const { - return nullptr; - } - - /** - * Update mFramesWritten. - * For internal use only. - */ - virtual void updateFramesWritten() = 0; - - /** - * Update mFramesRead. - * For internal use only. - */ - virtual void updateFramesRead() = 0; - - /* - * Swap old callback for new callback. - * This not atomic. - * This should only be used internally. - * @param dataCallback - * @return previous dataCallback - */ - AudioStreamDataCallback *swapDataCallback(AudioStreamDataCallback *dataCallback) { - AudioStreamDataCallback *previousCallback = mDataCallback; - mDataCallback = dataCallback; - return previousCallback; - } - - /* - * Swap old callback for new callback. - * This not atomic. - * This should only be used internally. - * @param errorCallback - * @return previous errorCallback - */ - AudioStreamErrorCallback *swapErrorCallback(AudioStreamErrorCallback *errorCallback) { - AudioStreamErrorCallback *previousCallback = mErrorCallback; - mErrorCallback = errorCallback; - return previousCallback; - } - - /** - * @return number of frames of data currently in the buffer - */ - ResultWithValue getAvailableFrames(); - - /** - * Wait until the stream has a minimum amount of data available in its buffer. - * This can be used with an EXCLUSIVE MMAP input stream to avoid reading data too close to - * the DSP write position, which may cause glitches. - * - * @param numFrames minimum frames available - * @param timeoutNanoseconds - * @return number of frames available, ErrorTimeout - */ - ResultWithValue waitForAvailableFrames(int32_t numFrames, - int64_t timeoutNanoseconds); - - /** - * @return last result passed from an error callback - */ - virtual oboe::Result getLastErrorCallbackResult() const { - return mErrorCallbackResult; - } - -protected: - - /** - * This is used to detect more than one error callback from a stream. - * These were bugs in some versions of Android that caused multiple error callbacks. - * Internal bug b/63087953 - * - * Calling this sets an atomic true and returns the previous value. - * - * @return false on first call, true on subsequent calls - */ - bool wasErrorCallbackCalled() { - return mErrorCallbackCalled.exchange(true); - } - - /** - * Wait for a transition from one state to another. - * @return OK if the endingState was observed, or ErrorUnexpectedState - * if any state that was not the startingState or endingState was observed - * or ErrorTimeout. - */ - virtual Result waitForStateTransition(StreamState startingState, - StreamState endingState, - int64_t timeoutNanoseconds); - - /** - * Override this to provide a default for when the application did not specify a callback. - * - * @param audioData - * @param numFrames - * @return result - */ - virtual DataCallbackResult onDefaultCallback(void* /* audioData */, int /* numFrames */) { - return DataCallbackResult::Stop; - } - - /** - * Override this to provide your own behaviour for the audio callback - * - * @param audioData container array which audio frames will be written into or read from - * @param numFrames number of frames which were read/written - * @return the result of the callback: stop or continue - * - */ - DataCallbackResult fireDataCallback(void *audioData, int numFrames); - - /** - * @return true if callbacks may be called - */ - bool isDataCallbackEnabled() { - return mDataCallbackEnabled; - } - - /** - * This can be set false internally to prevent callbacks - * after DataCallbackResult::Stop has been returned. - */ - void setDataCallbackEnabled(bool enabled) { - mDataCallbackEnabled = enabled; - } - - /* - * Set a weak_ptr to this stream from the shared_ptr so that we can - * later use a shared_ptr in the error callback. - */ - void setWeakThis(std::shared_ptr &sharedStream) { - mWeakThis = sharedStream; - } - - /* - * Make a shared_ptr that will prevent this stream from being deleted. - */ - std::shared_ptr lockWeakThis() { - return mWeakThis.lock(); - } - - std::weak_ptr mWeakThis; // weak pointer to this object - - /** - * Number of frames which have been written into the stream - * - * This is signed integer to match the counters in AAudio. - * At audio rates, the counter will overflow in about six million years. - */ - std::atomic mFramesWritten{}; - - /** - * Number of frames which have been read from the stream. - * - * This is signed integer to match the counters in AAudio. - * At audio rates, the counter will overflow in about six million years. - */ - std::atomic mFramesRead{}; - - std::mutex mLock; // for synchronizing start/stop/close - - oboe::Result mErrorCallbackResult = oboe::Result::OK; - - /** - * Number of frames which will be copied to/from the audio device in a single read/write - * operation - */ - int32_t mFramesPerBurst = kUnspecified; - -private: - - // Log the scheduler if it changes. - void checkScheduler(); - int mPreviousScheduler = -1; - - std::atomic mDataCallbackEnabled{false}; - std::atomic mErrorCallbackCalled{false}; -}; - -/** - * This struct is a stateless functor which closes an AudioStream prior to its deletion. - * This means it can be used to safely delete a smart pointer referring to an open stream. - */ - struct StreamDeleterFunctor { - void operator()(AudioStream *audioStream) { - if (audioStream) { - audioStream->close(); - } - delete audioStream; - } - }; -} // namespace oboe - -#endif /* OBOE_STREAM_H_ */ diff --git a/app/src/main/cpp/oboe/include/oboe/AudioStreamBase.h b/app/src/main/cpp/oboe/include/oboe/AudioStreamBase.h deleted file mode 100644 index 148e3178..00000000 --- a/app/src/main/cpp/oboe/include/oboe/AudioStreamBase.h +++ /dev/null @@ -1,263 +0,0 @@ -/* - * Copyright 2015 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_STREAM_BASE_H_ -#define OBOE_STREAM_BASE_H_ - -#include -#include -#include "oboe/AudioStreamCallback.h" -#include "oboe/Definitions.h" - -namespace oboe { - -/** - * Base class containing parameters for audio streams and builders. - **/ -class AudioStreamBase { - -public: - - AudioStreamBase() {} - - virtual ~AudioStreamBase() = default; - - // This class only contains primitives so we can use default constructor and copy methods. - - /** - * Default copy constructor - */ - AudioStreamBase(const AudioStreamBase&) = default; - - /** - * Default assignment operator - */ - AudioStreamBase& operator=(const AudioStreamBase&) = default; - - /** - * @return number of channels, for example 2 for stereo, or kUnspecified - */ - int32_t getChannelCount() const { return mChannelCount; } - - /** - * @return Direction::Input or Direction::Output - */ - Direction getDirection() const { return mDirection; } - - /** - * @return sample rate for the stream or kUnspecified - */ - int32_t getSampleRate() const { return mSampleRate; } - - /** - * @deprecated use `getFramesPerDataCallback` instead. - */ - int32_t getFramesPerCallback() const { return getFramesPerDataCallback(); } - - /** - * @return the number of frames in each data callback or kUnspecified. - */ - int32_t getFramesPerDataCallback() const { return mFramesPerCallback; } - - /** - * @return the audio sample format (e.g. Float or I16) - */ - AudioFormat getFormat() const { return mFormat; } - - /** - * Query the maximum number of frames that can be filled without blocking. - * If the stream has been closed the last known value will be returned. - * - * @return buffer size - */ - virtual int32_t getBufferSizeInFrames() { return mBufferSizeInFrames; } - - /** - * @return capacityInFrames or kUnspecified - */ - virtual int32_t getBufferCapacityInFrames() const { return mBufferCapacityInFrames; } - - /** - * @return the sharing mode of the stream. - */ - SharingMode getSharingMode() const { return mSharingMode; } - - /** - * @return the performance mode of the stream. - */ - PerformanceMode getPerformanceMode() const { return mPerformanceMode; } - - /** - * @return the device ID of the stream. - */ - int32_t getDeviceId() const { return mDeviceId; } - - /** - * For internal use only. - * @return the data callback object for this stream, if set. - */ - AudioStreamDataCallback *getDataCallback() const { - return mDataCallback; - } - - /** - * For internal use only. - * @return the error callback object for this stream, if set. - */ - AudioStreamErrorCallback *getErrorCallback() const { - return mErrorCallback; - } - - /** - * @return true if a data callback was set for this stream - */ - bool isDataCallbackSpecified() const { - return mDataCallback != nullptr; - } - - /** - * Note that if the app does not set an error callback then a - * default one may be provided. - * @return true if an error callback was set for this stream - */ - bool isErrorCallbackSpecified() const { - return mErrorCallback != nullptr; - } - - /** - * @return the usage for this stream. - */ - Usage getUsage() const { return mUsage; } - - /** - * @return the stream's content type. - */ - ContentType getContentType() const { return mContentType; } - - /** - * @return the stream's input preset. - */ - InputPreset getInputPreset() const { return mInputPreset; } - - /** - * @return the stream's session ID allocation strategy (None or Allocate). - */ - SessionId getSessionId() const { return mSessionId; } - - /** - * @return true if Oboe can convert channel counts to achieve optimal results. - */ - bool isChannelConversionAllowed() const { - return mChannelConversionAllowed; - } - - /** - * @return true if Oboe can convert data formats to achieve optimal results. - */ - bool isFormatConversionAllowed() const { - return mFormatConversionAllowed; - } - - /** - * @return whether and how Oboe can convert sample rates to achieve optimal results. - */ - SampleRateConversionQuality getSampleRateConversionQuality() const { - return mSampleRateConversionQuality; - } - -protected: - /** The callback which will be fired when new data is ready to be read/written. **/ - AudioStreamDataCallback *mDataCallback = nullptr; - - /** The callback which will be fired when an error or a disconnect occurs. **/ - AudioStreamErrorCallback *mErrorCallback = nullptr; - - /** Number of audio frames which will be requested in each callback */ - int32_t mFramesPerCallback = kUnspecified; - /** Stream channel count */ - int32_t mChannelCount = kUnspecified; - /** Stream sample rate */ - int32_t mSampleRate = kUnspecified; - /** Stream audio device ID */ - int32_t mDeviceId = kUnspecified; - /** Stream buffer capacity specified as a number of audio frames */ - int32_t mBufferCapacityInFrames = kUnspecified; - /** Stream buffer size specified as a number of audio frames */ - int32_t mBufferSizeInFrames = kUnspecified; - - /** Stream sharing mode */ - SharingMode mSharingMode = SharingMode::Shared; - /** Format of audio frames */ - AudioFormat mFormat = AudioFormat::Unspecified; - /** Stream direction */ - Direction mDirection = Direction::Output; - /** Stream performance mode */ - PerformanceMode mPerformanceMode = PerformanceMode::None; - - /** Stream usage. Only active on Android 28+ */ - Usage mUsage = Usage::Media; - /** Stream content type. Only active on Android 28+ */ - ContentType mContentType = ContentType::Music; - /** Stream input preset. Only active on Android 28+ - * TODO InputPreset::Unspecified should be considered as a possible default alternative. - */ - InputPreset mInputPreset = InputPreset::VoiceRecognition; - /** Stream session ID allocation strategy. Only active on Android 28+ */ - SessionId mSessionId = SessionId::None; - - /** Control the name of the package creating the stream. Only active on Android 31+ */ - std::string mPackageName; - /** Control the attribution tag of the context creating the stream. Only active on Android 31+ */ - std::string mAttributionTag; - - // Control whether Oboe can convert channel counts to achieve optimal results. - bool mChannelConversionAllowed = false; - // Control whether Oboe can convert data formats to achieve optimal results. - bool mFormatConversionAllowed = false; - // Control whether and how Oboe can convert sample rates to achieve optimal results. - SampleRateConversionQuality mSampleRateConversionQuality = SampleRateConversionQuality::None; - - /** Validate stream parameters that might not be checked in lower layers */ - virtual Result isValidConfig() { - switch (mFormat) { - case AudioFormat::Unspecified: - case AudioFormat::I16: - case AudioFormat::Float: - case AudioFormat::I24: - case AudioFormat::I32: - break; - - default: - return Result::ErrorInvalidFormat; - } - - switch (mSampleRateConversionQuality) { - case SampleRateConversionQuality::None: - case SampleRateConversionQuality::Fastest: - case SampleRateConversionQuality::Low: - case SampleRateConversionQuality::Medium: - case SampleRateConversionQuality::High: - case SampleRateConversionQuality::Best: - return Result::OK; - default: - return Result::ErrorIllegalArgument; - } - } -}; - -} // namespace oboe - -#endif /* OBOE_STREAM_BASE_H_ */ diff --git a/app/src/main/cpp/oboe/include/oboe/AudioStreamBuilder.h b/app/src/main/cpp/oboe/include/oboe/AudioStreamBuilder.h deleted file mode 100644 index c7ea7af3..00000000 --- a/app/src/main/cpp/oboe/include/oboe/AudioStreamBuilder.h +++ /dev/null @@ -1,520 +0,0 @@ -/* - * Copyright 2015 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_STREAM_BUILDER_H_ -#define OBOE_STREAM_BUILDER_H_ - -#include "oboe/Definitions.h" -#include "oboe/AudioStreamBase.h" -#include "ResultWithValue.h" - -namespace oboe { - - // This depends on AudioStream, so we use forward declaration, it will close and delete the stream - struct StreamDeleterFunctor; - using ManagedStream = std::unique_ptr; - -/** - * Factory class for an audio Stream. - */ -class AudioStreamBuilder : public AudioStreamBase { -public: - - AudioStreamBuilder() : AudioStreamBase() {} - - AudioStreamBuilder(const AudioStreamBase &audioStreamBase): AudioStreamBase(audioStreamBase) {} - - /** - * Request a specific number of channels. - * - * Default is kUnspecified. If the value is unspecified then - * the application should query for the actual value after the stream is opened. - */ - AudioStreamBuilder *setChannelCount(int channelCount) { - mChannelCount = channelCount; - return this; - } - - /** - * Request the direction for a stream. The default is Direction::Output. - * - * @param direction Direction::Output or Direction::Input - */ - AudioStreamBuilder *setDirection(Direction direction) { - mDirection = direction; - return this; - } - - /** - * Request a specific sample rate in Hz. - * - * Default is kUnspecified. If the value is unspecified then - * the application should query for the actual value after the stream is opened. - * - * Technically, this should be called the "frame rate" or "frames per second", - * because it refers to the number of complete frames transferred per second. - * But it is traditionally called "sample rate". Se we use that term. - * - */ - AudioStreamBuilder *setSampleRate(int32_t sampleRate) { - mSampleRate = sampleRate; - return this; - } - - /** - * @deprecated use `setFramesPerDataCallback` instead. - */ - AudioStreamBuilder *setFramesPerCallback(int framesPerCallback) { - return setFramesPerDataCallback(framesPerCallback); - } - - /** - * Request a specific number of frames for the data callback. - * - * Default is kUnspecified. If the value is unspecified then - * the actual number may vary from callback to callback. - * - * If an application can handle a varying number of frames then we recommend - * leaving this unspecified. This allow the underlying API to optimize - * the callbacks. But if your application is, for example, doing FFTs or other block - * oriented operations, then call this function to get the sizes you need. - * - * @param framesPerCallback - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setFramesPerDataCallback(int framesPerCallback) { - mFramesPerCallback = framesPerCallback; - return this; - } - - /** - * Request a sample data format, for example Format::Float. - * - * Default is Format::Unspecified. If the value is unspecified then - * the application should query for the actual value after the stream is opened. - */ - AudioStreamBuilder *setFormat(AudioFormat format) { - mFormat = format; - return this; - } - - /** - * Set the requested buffer capacity in frames. - * BufferCapacityInFrames is the maximum possible BufferSizeInFrames. - * - * The final stream capacity may differ. For AAudio it should be at least this big. - * For OpenSL ES, it could be smaller. - * - * Default is kUnspecified. - * - * @param bufferCapacityInFrames the desired buffer capacity in frames or kUnspecified - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setBufferCapacityInFrames(int32_t bufferCapacityInFrames) { - mBufferCapacityInFrames = bufferCapacityInFrames; - return this; - } - - /** - * Get the audio API which will be requested when opening the stream. No guarantees that this is - * the API which will actually be used. Query the stream itself to find out the API which is - * being used. - * - * If you do not specify the API, then AAudio will be used if isAAudioRecommended() - * returns true. Otherwise OpenSL ES will be used. - * - * @return the requested audio API - */ - AudioApi getAudioApi() const { return mAudioApi; } - - /** - * If you leave this unspecified then Oboe will choose the best API - * for the device and SDK version at runtime. - * - * This should almost always be left unspecified, except for debugging purposes. - * Specifying AAudio will force Oboe to use AAudio on 8.0, which is extremely risky. - * Specifying OpenSLES should mainly be used to test legacy performance/functionality. - * - * If the caller requests AAudio and it is supported then AAudio will be used. - * - * @param audioApi Must be AudioApi::Unspecified, AudioApi::OpenSLES or AudioApi::AAudio. - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setAudioApi(AudioApi audioApi) { - mAudioApi = audioApi; - return this; - } - - /** - * Is the AAudio API supported on this device? - * - * AAudio was introduced in the Oreo 8.0 release. - * - * @return true if supported - */ - static bool isAAudioSupported(); - - /** - * Is the AAudio API recommended this device? - * - * AAudio may be supported but not recommended because of version specific issues. - * AAudio is not recommended for Android 8.0 or earlier versions. - * - * @return true if recommended - */ - static bool isAAudioRecommended(); - - /** - * Request a mode for sharing the device. - * The requested sharing mode may not be available. - * So the application should query for the actual mode after the stream is opened. - * - * @param sharingMode SharingMode::Shared or SharingMode::Exclusive - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setSharingMode(SharingMode sharingMode) { - mSharingMode = sharingMode; - return this; - } - - /** - * Request a performance level for the stream. - * This will determine the latency, the power consumption, and the level of - * protection from glitches. - * - * @param performanceMode for example, PerformanceMode::LowLatency - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setPerformanceMode(PerformanceMode performanceMode) { - mPerformanceMode = performanceMode; - return this; - } - - - /** - * Set the intended use case for an output stream. - * - * The system will use this information to optimize the behavior of the stream. - * This could, for example, affect how volume and focus is handled for the stream. - * The usage is ignored for input streams. - * - * The default, if you do not call this function, is Usage::Media. - * - * Added in API level 28. - * - * @param usage the desired usage, eg. Usage::Game - */ - AudioStreamBuilder *setUsage(Usage usage) { - mUsage = usage; - return this; - } - - /** - * Set the type of audio data that an output stream will carry. - * - * The system will use this information to optimize the behavior of the stream. - * This could, for example, affect whether a stream is paused when a notification occurs. - * The contentType is ignored for input streams. - * - * The default, if you do not call this function, is ContentType::Music. - * - * Added in API level 28. - * - * @param contentType the type of audio data, eg. ContentType::Speech - */ - AudioStreamBuilder *setContentType(ContentType contentType) { - mContentType = contentType; - return this; - } - - /** - * Set the input (capture) preset for the stream. - * - * The system will use this information to optimize the behavior of the stream. - * This could, for example, affect which microphones are used and how the - * recorded data is processed. - * - * The default, if you do not call this function, is InputPreset::VoiceRecognition. - * That is because VoiceRecognition is the preset with the lowest latency - * on many platforms. - * - * Added in API level 28. - * - * @param inputPreset the desired configuration for recording - */ - AudioStreamBuilder *setInputPreset(InputPreset inputPreset) { - mInputPreset = inputPreset; - return this; - } - - /** Set the requested session ID. - * - * The session ID can be used to associate a stream with effects processors. - * The effects are controlled using the Android AudioEffect Java API. - * - * The default, if you do not call this function, is SessionId::None. - * - * If set to SessionId::Allocate then a session ID will be allocated - * when the stream is opened. - * - * The allocated session ID can be obtained by calling AudioStream::getSessionId() - * and then used with this function when opening another stream. - * This allows effects to be shared between streams. - * - * Session IDs from Oboe can be used the Android Java APIs and vice versa. - * So a session ID from an Oboe stream can be passed to Java - * and effects applied using the Java AudioEffect API. - * - * Allocated session IDs will always be positive and nonzero. - * - * Added in API level 28. - * - * @param sessionId an allocated sessionID or SessionId::Allocate - */ - AudioStreamBuilder *setSessionId(SessionId sessionId) { - mSessionId = sessionId; - return this; - } - - /** - * Request a stream to a specific audio input/output device given an audio device ID. - * - * In most cases, the primary device will be the appropriate device to use, and the - * deviceId can be left kUnspecified. - * - * On Android, for example, the ID could be obtained from the Java AudioManager. - * AudioManager.getDevices() returns an array of AudioDeviceInfo[], which contains - * a getId() method (as well as other type information), that should be passed - * to this method. - * - * - * Note that when using OpenSL ES, this will be ignored and the created - * stream will have deviceId kUnspecified. - * - * @param deviceId device identifier or kUnspecified - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setDeviceId(int32_t deviceId) { - mDeviceId = deviceId; - return this; - } - - /** - * Specifies an object to handle data related callbacks from the underlying API. - * - * Important: See AudioStreamCallback for restrictions on what may be called - * from the callback methods. - * - * @param dataCallback - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setDataCallback(oboe::AudioStreamDataCallback *dataCallback) { - mDataCallback = dataCallback; - return this; - } - - /** - * Specifies an object to handle error related callbacks from the underlying API. - * This can occur when a stream is disconnected because a headset is plugged in or unplugged. - * It can also occur if the audio service fails or if an exclusive stream is stolen by - * another stream. - * - * Important: See AudioStreamCallback for restrictions on what may be called - * from the callback methods. - * - * When an error callback occurs, the associated stream must be stopped and closed - * in a separate thread. - * - * @param errorCallback - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setErrorCallback(oboe::AudioStreamErrorCallback *errorCallback) { - mErrorCallback = errorCallback; - return this; - } - - /** - * Specifies an object to handle data or error related callbacks from the underlying API. - * - * This is the equivalent of calling both setDataCallback() and setErrorCallback(). - * - * Important: See AudioStreamCallback for restrictions on what may be called - * from the callback methods. - * - * When an error callback occurs, the associated stream will be stopped and closed in a separate thread. - * - * A note on why the streamCallback parameter is a raw pointer rather than a smart pointer: - * - * The caller should retain ownership of the object streamCallback points to. At first glance weak_ptr may seem like - * a good candidate for streamCallback as this implies temporary ownership. However, a weak_ptr can only be created - * from a shared_ptr. A shared_ptr incurs some performance overhead. The callback object is likely to be accessed - * every few milliseconds when the stream requires new data so this overhead is something we want to avoid. - * - * This leaves a raw pointer as the logical type choice. The only caveat being that the caller must not destroy - * the callback before the stream has been closed. - * - * @param streamCallback - * @return pointer to the builder so calls can be chained - */ - AudioStreamBuilder *setCallback(AudioStreamCallback *streamCallback) { - // Use the same callback object for both, dual inheritance. - mDataCallback = streamCallback; - mErrorCallback = streamCallback; - return this; - } - - /** - * If true then Oboe might convert channel counts to achieve optimal results. - * On some versions of Android for example, stereo streams could not use a FAST track. - * So a mono stream might be used instead and duplicated to two channels. - * On some devices, mono streams might be broken, so a stereo stream might be opened - * and converted to mono. - * - * Default is true. - */ - AudioStreamBuilder *setChannelConversionAllowed(bool allowed) { - mChannelConversionAllowed = allowed; - return this; - } - - /** - * If true then Oboe might convert data formats to achieve optimal results. - * On some versions of Android, for example, a float stream could not get a - * low latency data path. So an I16 stream might be opened and converted to float. - * - * Default is false. - */ - AudioStreamBuilder *setFormatConversionAllowed(bool allowed) { - mFormatConversionAllowed = allowed; - return this; - } - - /** - * Specify the quality of the sample rate converter in Oboe. - * - * If set to None then Oboe will not do sample rate conversion. But the underlying APIs might - * still do sample rate conversion if you specify a sample rate. - * That can prevent you from getting a low latency stream. - * - * If you do the conversion in Oboe then you might still get a low latency stream. - * - * Default is SampleRateConversionQuality::None - */ - AudioStreamBuilder *setSampleRateConversionQuality(SampleRateConversionQuality quality) { - mSampleRateConversionQuality = quality; - return this; - } - - /** - * Declare the name of the package creating the stream. - * - * This is usually Context#getPackageName() - * - * The default, if you do not call this function, is a random package in the calling uid. - * - * Added in API level 31. - * - * @param packageName packageName of the calling app. - */ - AudioStreamBuilder *setPackageName(std::string packageName) { - mPackageName = packageName; - return this; - } - - /** - * Declare the attribution tag of the context creating the stream. - * - * This is usually Context#getAttributionTag() - * - * The default, if you do not call this function, is the default attribution tag. - * - * Added in API level 31. - * - * @param attributionTag attributionTag of the calling context. - */ - AudioStreamBuilder *setAttributionTag(std::string attributionTag) { - mAttributionTag = attributionTag; - return this; - } - - /** - * @return true if AAudio will be used based on the current settings. - */ - bool willUseAAudio() const { - return (mAudioApi == AudioApi::AAudio && isAAudioSupported()) - || (mAudioApi == AudioApi::Unspecified && isAAudioRecommended()); - } - - /** - * Create and open a stream object based on the current settings. - * - * The caller owns the pointer to the AudioStream object - * and must delete it when finished. - * - * @deprecated Use openStream(std::shared_ptr &stream) instead. - * @param stream pointer to a variable to receive the stream address - * @return OBOE_OK if successful or a negative error code - */ - Result openStream(AudioStream **stream); - - /** - * Create and open a stream object based on the current settings. - * - * The caller shares the pointer to the AudioStream object. - * The shared_ptr is used internally by Oboe to prevent the stream from being - * deleted while it is being used by callbacks. - * - * @param stream reference to a shared_ptr to receive the stream address - * @return OBOE_OK if successful or a negative error code - */ - Result openStream(std::shared_ptr &stream); - - /** - * Create and open a ManagedStream object based on the current builder state. - * - * The caller must create a unique ptr, and pass by reference so it can be - * modified to point to an opened stream. The caller owns the unique ptr, - * and it will be automatically closed and deleted when going out of scope. - * - * @deprecated Use openStream(std::shared_ptr &stream) instead. - * @param stream Reference to the ManagedStream (uniqueptr) used to keep track of stream - * @return OBOE_OK if successful or a negative error code. - */ - Result openManagedStream(ManagedStream &stream); - -private: - - /** - * @param other - * @return true if channels, format and sample rate match - */ - bool isCompatible(AudioStreamBase &other); - - /** - * Create an AudioStream object. The AudioStream must be opened before use. - * - * The caller owns the pointer. - * - * @return pointer to an AudioStream object or nullptr. - */ - oboe::AudioStream *build(); - - AudioApi mAudioApi = AudioApi::Unspecified; -}; - -} // namespace oboe - -#endif /* OBOE_STREAM_BUILDER_H_ */ diff --git a/app/src/main/cpp/oboe/include/oboe/AudioStreamCallback.h b/app/src/main/cpp/oboe/include/oboe/AudioStreamCallback.h deleted file mode 100644 index 915c3d71..00000000 --- a/app/src/main/cpp/oboe/include/oboe/AudioStreamCallback.h +++ /dev/null @@ -1,189 +0,0 @@ -/* - * Copyright (C) 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_STREAM_CALLBACK_H -#define OBOE_STREAM_CALLBACK_H - -#include "oboe/Definitions.h" - -namespace oboe { - -class AudioStream; - -/** - * AudioStreamDataCallback defines a callback interface for - * moving data to/from an audio stream using `onAudioReady` - * 2) being alerted when a stream has an error using `onError*` methods - * - * It is used with AudioStreamBuilder::setDataCallback(). - */ - -class AudioStreamDataCallback { -public: - virtual ~AudioStreamDataCallback() = default; - - /** - * A buffer is ready for processing. - * - * For an output stream, this function should render and write numFrames of data - * in the stream's current data format to the audioData buffer. - * - * For an input stream, this function should read and process numFrames of data - * from the audioData buffer. - * - * The audio data is passed through the buffer. So do NOT call read() or - * write() on the stream that is making the callback. - * - * Note that numFrames can vary unless AudioStreamBuilder::setFramesPerCallback() - * is called. - * - * Also note that this callback function should be considered a "real-time" function. - * It must not do anything that could cause an unbounded delay because that can cause the - * audio to glitch or pop. - * - * These are things the function should NOT do: - *
    - *
  • allocate memory using, for example, malloc() or new
  • - *
  • any file operations such as opening, closing, reading or writing
  • - *
  • any network operations such as streaming
  • - *
  • use any mutexes or other synchronization primitives
  • - *
  • sleep
  • - *
  • oboeStream->stop(), pause(), flush() or close()
  • - *
  • oboeStream->read()
  • - *
  • oboeStream->write()
  • - *
- * - * The following are OK to call from the data callback: - *
    - *
  • oboeStream->get*()
  • - *
  • oboe::convertToText()
  • - *
  • oboeStream->setBufferSizeInFrames()
  • - *
- * - * If you need to move data, eg. MIDI commands, in or out of the callback function then - * we recommend the use of non-blocking techniques such as an atomic FIFO. - * - * @param audioStream pointer to the associated stream - * @param audioData buffer containing input data or a place to put output data - * @param numFrames number of frames to be processed - * @return DataCallbackResult::Continue or DataCallbackResult::Stop - */ - virtual DataCallbackResult onAudioReady( - AudioStream *audioStream, - void *audioData, - int32_t numFrames) = 0; -}; - -/** - * AudioStreamErrorCallback defines a callback interface for - * being alerted when a stream has an error or is disconnected - * using `onError*` methods. - * - * It is used with AudioStreamBuilder::setErrorCallback(). - */ -class AudioStreamErrorCallback { -public: - virtual ~AudioStreamErrorCallback() = default; - - /** - * This will be called before other `onError` methods when an error occurs on a stream, - * such as when the stream is disconnected. - * - * It can be used to override and customize the normal error processing. - * Use of this method is considered an advanced technique. - * It might, for example, be used if an app want to use a high level lock when - * closing and reopening a stream. - * Or it might be used when an app want to signal a management thread that handles - * all of the stream state. - * - * If this method returns false it indicates that the stream has *not been stopped and closed - * by the application. In this case it will be stopped by Oboe in the following way: - * onErrorBeforeClose() will be called, then the stream will be closed and onErrorAfterClose() - * will be closed. - * - * If this method returns true it indicates that the stream *has* been stopped and closed - * by the application and Oboe will not do this. - * In that case, the app MUST stop() and close() the stream. - * - * This method will be called on a thread created by Oboe. - * - * @param audioStream pointer to the associated stream - * @param error - * @return true if the stream has been stopped and closed, false if not - */ - virtual bool onError(AudioStream* /* audioStream */, Result /* error */) { - return false; - } - - /** - * This will be called when an error occurs on a stream, - * such as when the stream is disconnected, - * and if onError() returns false (indicating that the error has not already been handled). - * - * Note that this will be called on a thread created by Oboe. - * - * The underlying stream will already be stopped by Oboe but not yet closed. - * So the stream can be queried. - * - * Do not close or delete the stream in this method because it will be - * closed after this method returns. - * - * @param audioStream pointer to the associated stream - * @param error - */ - virtual void onErrorBeforeClose(AudioStream* /* audioStream */, Result /* error */) {} - - /** - * This will be called when an error occurs on a stream, - * such as when the stream is disconnected, - * and if onError() returns false (indicating that the error has not already been handled). - * - * The underlying AAudio or OpenSL ES stream will already be stopped AND closed by Oboe. - * So the underlying stream cannot be referenced. - * But you can still query most parameters. - * - * This callback could be used to reopen a new stream on another device. - * - * @param audioStream pointer to the associated stream - * @param error - */ - virtual void onErrorAfterClose(AudioStream* /* audioStream */, Result /* error */) {} - -}; - -/** - * AudioStreamCallback defines a callback interface for: - * - * 1) moving data to/from an audio stream using `onAudioReady` - * 2) being alerted when a stream has an error using `onError*` methods - * - * It is used with AudioStreamBuilder::setCallback(). - * - * It combines the interfaces defined by AudioStreamDataCallback and AudioStreamErrorCallback. - * This was the original callback object. We now recommend using the individual interfaces - * and using setDataCallback() and setErrorCallback(). - * - * @deprecated Use `AudioStreamDataCallback` and `AudioStreamErrorCallback` instead - */ -class AudioStreamCallback : public AudioStreamDataCallback, - public AudioStreamErrorCallback { -public: - virtual ~AudioStreamCallback() = default; -}; - -} // namespace oboe - -#endif //OBOE_STREAM_CALLBACK_H diff --git a/app/src/main/cpp/oboe/include/oboe/Definitions.h b/app/src/main/cpp/oboe/include/oboe/Definitions.h deleted file mode 100644 index 566518f0..00000000 --- a/app/src/main/cpp/oboe/include/oboe/Definitions.h +++ /dev/null @@ -1,545 +0,0 @@ -/* - * Copyright (C) 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_DEFINITIONS_H -#define OBOE_DEFINITIONS_H - -#include -#include - -// Oboe needs to be able to build on old NDKs so we use hard coded constants. -// The correctness of these constants is verified in "aaudio/AAudioLoader.cpp". - -namespace oboe { - - /** - * Represents any attribute, property or value which hasn't been specified. - */ - constexpr int32_t kUnspecified = 0; - - // TODO: Investigate using std::chrono - /** - * The number of nanoseconds in a microsecond. 1,000. - */ - constexpr int64_t kNanosPerMicrosecond = 1000; - - /** - * The number of nanoseconds in a millisecond. 1,000,000. - */ - constexpr int64_t kNanosPerMillisecond = kNanosPerMicrosecond * 1000; - - /** - * The number of milliseconds in a second. 1,000. - */ - constexpr int64_t kMillisPerSecond = 1000; - - /** - * The number of nanoseconds in a second. 1,000,000,000. - */ - constexpr int64_t kNanosPerSecond = kNanosPerMillisecond * kMillisPerSecond; - - /** - * The state of the audio stream. - */ - enum class StreamState : int32_t { // aaudio_stream_state_t - Uninitialized = 0, // AAUDIO_STREAM_STATE_UNINITIALIZED, - Unknown = 1, // AAUDIO_STREAM_STATE_UNKNOWN, - Open = 2, // AAUDIO_STREAM_STATE_OPEN, - Starting = 3, // AAUDIO_STREAM_STATE_STARTING, - Started = 4, // AAUDIO_STREAM_STATE_STARTED, - Pausing = 5, // AAUDIO_STREAM_STATE_PAUSING, - Paused = 6, // AAUDIO_STREAM_STATE_PAUSED, - Flushing = 7, // AAUDIO_STREAM_STATE_FLUSHING, - Flushed = 8, // AAUDIO_STREAM_STATE_FLUSHED, - Stopping = 9, // AAUDIO_STREAM_STATE_STOPPING, - Stopped = 10, // AAUDIO_STREAM_STATE_STOPPED, - Closing = 11, // AAUDIO_STREAM_STATE_CLOSING, - Closed = 12, // AAUDIO_STREAM_STATE_CLOSED, - Disconnected = 13, // AAUDIO_STREAM_STATE_DISCONNECTED, - }; - - /** - * The direction of the stream. - */ - enum class Direction : int32_t { // aaudio_direction_t - - /** - * Used for playback. - */ - Output = 0, // AAUDIO_DIRECTION_OUTPUT, - - /** - * Used for recording. - */ - Input = 1, // AAUDIO_DIRECTION_INPUT, - }; - - /** - * The format of audio samples. - */ - enum class AudioFormat : int32_t { // aaudio_format_t - /** - * Invalid format. - */ - Invalid = -1, // AAUDIO_FORMAT_INVALID, - - /** - * Unspecified format. Format will be decided by Oboe. - */ - Unspecified = 0, // AAUDIO_FORMAT_UNSPECIFIED, - - /** - * Signed 16-bit integers. - */ - I16 = 1, // AAUDIO_FORMAT_PCM_I16, - - /** - * Single precision floating point. - * - * This is the recommended format for most applications. - * But note that the use of Float may prevent the opening of - * a low-latency input path on OpenSL ES or Legacy AAudio streams. - */ - Float = 2, // AAUDIO_FORMAT_PCM_FLOAT, - - /** - * Signed 24-bit integers, packed into 3 bytes. - * - * Note that the use of this format does not guarantee that - * the full precision will be provided. The underlying device may - * be using I16 format. - * - * Added in API 31 (S). - */ - I24 = 3, // AAUDIO_FORMAT_PCM_I24_PACKED - - /** - * Signed 32-bit integers. - * - * Note that the use of this format does not guarantee that - * the full precision will be provided. The underlying device may - * be using I16 format. - * - * Added in API 31 (S). - */ - I32 = 4, // AAUDIO_FORMAT_PCM_I32 - - }; - - /** - * The result of an audio callback. - */ - enum class DataCallbackResult : int32_t { // aaudio_data_callback_result_t - // Indicates to the caller that the callbacks should continue. - Continue = 0, // AAUDIO_CALLBACK_RESULT_CONTINUE, - - // Indicates to the caller that the callbacks should stop immediately. - Stop = 1, // AAUDIO_CALLBACK_RESULT_STOP, - }; - - /** - * The result of an operation. All except the `OK` result indicates that an error occurred. - * The `Result` can be converted into a human readable string using `convertToText`. - */ - enum class Result : int32_t { // aaudio_result_t - OK = 0, // AAUDIO_OK - ErrorBase = -900, // AAUDIO_ERROR_BASE, - ErrorDisconnected = -899, // AAUDIO_ERROR_DISCONNECTED, - ErrorIllegalArgument = -898, // AAUDIO_ERROR_ILLEGAL_ARGUMENT, - ErrorInternal = -896, // AAUDIO_ERROR_INTERNAL, - ErrorInvalidState = -895, // AAUDIO_ERROR_INVALID_STATE, - ErrorInvalidHandle = -892, // AAUDIO_ERROR_INVALID_HANDLE, - ErrorUnimplemented = -890, // AAUDIO_ERROR_UNIMPLEMENTED, - ErrorUnavailable = -889, // AAUDIO_ERROR_UNAVAILABLE, - ErrorNoFreeHandles = -888, // AAUDIO_ERROR_NO_FREE_HANDLES, - ErrorNoMemory = -887, // AAUDIO_ERROR_NO_MEMORY, - ErrorNull = -886, // AAUDIO_ERROR_NULL, - ErrorTimeout = -885, // AAUDIO_ERROR_TIMEOUT, - ErrorWouldBlock = -884, // AAUDIO_ERROR_WOULD_BLOCK, - ErrorInvalidFormat = -883, // AAUDIO_ERROR_INVALID_FORMAT, - ErrorOutOfRange = -882, // AAUDIO_ERROR_OUT_OF_RANGE, - ErrorNoService = -881, // AAUDIO_ERROR_NO_SERVICE, - ErrorInvalidRate = -880, // AAUDIO_ERROR_INVALID_RATE, - // Reserved for future AAudio result types - Reserved1, - Reserved2, - Reserved3, - Reserved4, - Reserved5, - Reserved6, - Reserved7, - Reserved8, - Reserved9, - Reserved10, - ErrorClosed = -869, - }; - - /** - * The sharing mode of the audio stream. - */ - enum class SharingMode : int32_t { // aaudio_sharing_mode_t - - /** - * This will be the only stream using a particular source or sink. - * This mode will provide the lowest possible latency. - * You should close EXCLUSIVE streams immediately when you are not using them. - * - * If you do not need the lowest possible latency then we recommend using Shared, - * which is the default. - */ - Exclusive = 0, // AAUDIO_SHARING_MODE_EXCLUSIVE, - - /** - * Multiple applications can share the same device. - * The data from output streams will be mixed by the audio service. - * The data for input streams will be distributed by the audio service. - * - * This will have higher latency than the EXCLUSIVE mode. - */ - Shared = 1, // AAUDIO_SHARING_MODE_SHARED, - }; - - /** - * The performance mode of the audio stream. - */ - enum class PerformanceMode : int32_t { // aaudio_performance_mode_t - - /** - * No particular performance needs. Default. - */ - None = 10, // AAUDIO_PERFORMANCE_MODE_NONE, - - /** - * Extending battery life is most important. - */ - PowerSaving = 11, // AAUDIO_PERFORMANCE_MODE_POWER_SAVING, - - /** - * Reducing latency is most important. - */ - LowLatency = 12, // AAUDIO_PERFORMANCE_MODE_LOW_LATENCY - }; - - /** - * The underlying audio API used by the audio stream. - */ - enum class AudioApi : int32_t { - /** - * Try to use AAudio. If not available then use OpenSL ES. - */ - Unspecified = kUnspecified, - - /** - * Use OpenSL ES. - */ - OpenSLES, - - /** - * Try to use AAudio. Fail if unavailable. - */ - AAudio - }; - - /** - * Specifies the quality of the sample rate conversion performed by Oboe. - * Higher quality will require more CPU load. - * Higher quality conversion will probably be implemented using a sinc based resampler. - */ - enum class SampleRateConversionQuality : int32_t { - /** - * No conversion by Oboe. Underlying APIs may still do conversion. - */ - None, - /** - * Fastest conversion but may not sound great. - * This may be implemented using bilinear interpolation. - */ - Fastest, - Low, - Medium, - High, - /** - * Highest quality conversion, which may be expensive in terms of CPU. - */ - Best, - }; - - /** - * The Usage attribute expresses *why* you are playing a sound, what is this sound used for. - * This information is used by certain platforms or routing policies - * to make more refined volume or routing decisions. - * - * Note that these match the equivalent values in AudioAttributes in the Android Java API. - * - * This attribute only has an effect on Android API 28+. - */ - enum class Usage : int32_t { // aaudio_usage_t - /** - * Use this for streaming media, music performance, video, podcasts, etcetera. - */ - Media = 1, // AAUDIO_USAGE_MEDIA - - /** - * Use this for voice over IP, telephony, etcetera. - */ - VoiceCommunication = 2, // AAUDIO_USAGE_VOICE_COMMUNICATION - - /** - * Use this for sounds associated with telephony such as busy tones, DTMF, etcetera. - */ - VoiceCommunicationSignalling = 3, // AAUDIO_USAGE_VOICE_COMMUNICATION_SIGNALLING - - /** - * Use this to demand the users attention. - */ - Alarm = 4, // AAUDIO_USAGE_ALARM - - /** - * Use this for notifying the user when a message has arrived or some - * other background event has occured. - */ - Notification = 5, // AAUDIO_USAGE_NOTIFICATION - - /** - * Use this when the phone rings. - */ - NotificationRingtone = 6, // AAUDIO_USAGE_NOTIFICATION_RINGTONE - - /** - * Use this to attract the users attention when, for example, the battery is low. - */ - NotificationEvent = 10, // AAUDIO_USAGE_NOTIFICATION_EVENT - - /** - * Use this for screen readers, etcetera. - */ - AssistanceAccessibility = 11, // AAUDIO_USAGE_ASSISTANCE_ACCESSIBILITY - - /** - * Use this for driving or navigation directions. - */ - AssistanceNavigationGuidance = 12, // AAUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE - - /** - * Use this for user interface sounds, beeps, etcetera. - */ - AssistanceSonification = 13, // AAUDIO_USAGE_ASSISTANCE_SONIFICATION - - /** - * Use this for game audio and sound effects. - */ - Game = 14, // AAUDIO_USAGE_GAME - - /** - * Use this for audio responses to user queries, audio instructions or help utterances. - */ - Assistant = 16, // AAUDIO_USAGE_ASSISTANT - }; - - - /** - * The ContentType attribute describes *what* you are playing. - * It expresses the general category of the content. This information is optional. - * But in case it is known (for instance {@link Movie} for a - * movie streaming service or {@link Speech} for - * an audio book application) this information might be used by the audio framework to - * enforce audio focus. - * - * Note that these match the equivalent values in AudioAttributes in the Android Java API. - * - * This attribute only has an effect on Android API 28+. - */ - enum ContentType : int32_t { // aaudio_content_type_t - - /** - * Use this for spoken voice, audio books, etcetera. - */ - Speech = 1, // AAUDIO_CONTENT_TYPE_SPEECH - - /** - * Use this for pre-recorded or live music. - */ - Music = 2, // AAUDIO_CONTENT_TYPE_MUSIC - - /** - * Use this for a movie or video soundtrack. - */ - Movie = 3, // AAUDIO_CONTENT_TYPE_MOVIE - - /** - * Use this for sound is designed to accompany a user action, - * such as a click or beep sound made when the user presses a button. - */ - Sonification = 4, // AAUDIO_CONTENT_TYPE_SONIFICATION - }; - - /** - * Defines the audio source. - * An audio source defines both a default physical source of audio signal, and a recording - * configuration. - * - * Note that these match the equivalent values in MediaRecorder.AudioSource in the Android Java API. - * - * This attribute only has an effect on Android API 28+. - */ - enum InputPreset : int32_t { // aaudio_input_preset_t - /** - * Use this preset when other presets do not apply. - */ - Generic = 1, // AAUDIO_INPUT_PRESET_GENERIC - - /** - * Use this preset when recording video. - */ - Camcorder = 5, // AAUDIO_INPUT_PRESET_CAMCORDER - - /** - * Use this preset when doing speech recognition. - */ - VoiceRecognition = 6, // AAUDIO_INPUT_PRESET_VOICE_RECOGNITION - - /** - * Use this preset when doing telephony or voice messaging. - */ - VoiceCommunication = 7, // AAUDIO_INPUT_PRESET_VOICE_COMMUNICATION - - /** - * Use this preset to obtain an input with no effects. - * Note that this input will not have automatic gain control - * so the recorded volume may be very low. - */ - Unprocessed = 9, // AAUDIO_INPUT_PRESET_UNPROCESSED - - /** - * Use this preset for capturing audio meant to be processed in real time - * and played back for live performance (e.g karaoke). - * The capture path will minimize latency and coupling with playback path. - */ - VoicePerformance = 10, // AAUDIO_INPUT_PRESET_VOICE_PERFORMANCE - - }; - - /** - * This attribute can be used to allocate a session ID to the audio stream. - * - * This attribute only has an effect on Android API 28+. - */ - enum SessionId { - /** - * Do not allocate a session ID. - * Effects cannot be used with this stream. - * Default. - */ - None = -1, // AAUDIO_SESSION_ID_NONE - - /** - * Allocate a session ID that can be used to attach and control - * effects using the Java AudioEffects API. - * Note that the use of this flag may result in higher latency. - * - * Note that this matches the value of AudioManager.AUDIO_SESSION_ID_GENERATE. - */ - Allocate = 0, // AAUDIO_SESSION_ID_ALLOCATE - }; - - /** - * The channel count of the audio stream. The underlying type is `int32_t`. - * Use of this enum is convenient to avoid "magic" - * numbers when specifying the channel count. - * - * For example, you can write - * `builder.setChannelCount(ChannelCount::Stereo)` - * rather than `builder.setChannelCount(2)` - * - */ - enum ChannelCount : int32_t { - /** - * Audio channel count definition, use Mono or Stereo - */ - Unspecified = kUnspecified, - - /** - * Use this for mono audio - */ - Mono = 1, - - /** - * Use this for stereo audio. - */ - Stereo = 2, - }; - - /** - * On API 16 to 26 OpenSL ES will be used. When using OpenSL ES the optimal values for sampleRate and - * framesPerBurst are not known by the native code. - * On API 17+ these values should be obtained from the AudioManager using this code: - * - *

-     * // Note that this technique only works for built-in speakers and headphones.
-     * AudioManager myAudioMgr = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
-     * String sampleRateStr = myAudioMgr.getProperty(AudioManager.PROPERTY_OUTPUT_SAMPLE_RATE);
-     * int defaultSampleRate = Integer.parseInt(sampleRateStr);
-     * String framesPerBurstStr = myAudioMgr.getProperty(AudioManager.PROPERTY_OUTPUT_FRAMES_PER_BUFFER);
-     * int defaultFramesPerBurst = Integer.parseInt(framesPerBurstStr);
-     * 
- * - * It can then be passed down to Oboe through JNI. - * - * AAudio will get the optimal framesPerBurst from the HAL and will ignore this value. - */ - class DefaultStreamValues { - - public: - - /** The default sample rate to use when opening new audio streams */ - static int32_t SampleRate; - /** The default frames per burst to use when opening new audio streams */ - static int32_t FramesPerBurst; - /** The default channel count to use when opening new audio streams */ - static int32_t ChannelCount; - - }; - - /** - * The time at which the frame at `position` was presented - */ - struct FrameTimestamp { - int64_t position; // in frames - int64_t timestamp; // in nanoseconds - }; - - class OboeGlobals { - public: - - static bool areWorkaroundsEnabled() { - return mWorkaroundsEnabled; - } - - /** - * Disable this when writing tests to reproduce bugs in AAudio or OpenSL ES - * that have workarounds in Oboe. - * @param enabled - */ - static void setWorkaroundsEnabled(bool enabled) { - mWorkaroundsEnabled = enabled; - } - - private: - static bool mWorkaroundsEnabled; - }; -} // namespace oboe - -#endif // OBOE_DEFINITIONS_H diff --git a/app/src/main/cpp/oboe/include/oboe/LatencyTuner.h b/app/src/main/cpp/oboe/include/oboe/LatencyTuner.h deleted file mode 100644 index 8b8404d9..00000000 --- a/app/src/main/cpp/oboe/include/oboe/LatencyTuner.h +++ /dev/null @@ -1,150 +0,0 @@ -/* - * Copyright 2017 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_LATENCY_TUNER_ -#define OBOE_LATENCY_TUNER_ - -#include -#include -#include "oboe/Definitions.h" -#include "oboe/AudioStream.h" - -namespace oboe { - -/** - * LatencyTuner can be used to dynamically tune the latency of an output stream. - * It adjusts the stream's bufferSize by monitoring the number of underruns. - * - * This only affects the latency associated with the first level of buffering that is closest - * to the application. It does not affect low latency in the HAL, or touch latency in the UI. - * - * Call tune() right before returning from your data callback function if using callbacks. - * Call tune() right before calling write() if using blocking writes. - * - * If you want to see the ongoing results of this tuning process then call - * stream->getBufferSize() periodically. - * - */ -class LatencyTuner { -public: - - /** - * Construct a new LatencyTuner object which will act on the given audio stream - * - * @param stream the stream who's latency will be tuned - */ - explicit LatencyTuner(AudioStream &stream); - - /** - * Construct a new LatencyTuner object which will act on the given audio stream. - * - * @param stream the stream who's latency will be tuned - * @param the maximum buffer size which the tune() operation will set the buffer size to - */ - explicit LatencyTuner(AudioStream &stream, int32_t maximumBufferSize); - - /** - * Adjust the bufferSizeInFrames to optimize latency. - * It will start with a low latency and then raise it if an underrun occurs. - * - * Latency tuning is only supported for AAudio. - * - * @return OK or negative error, ErrorUnimplemented for OpenSL ES - */ - Result tune(); - - /** - * This may be called from another thread. Then tune() will call reset(), - * which will lower the latency to the minimum and then allow it to rise back up - * if there are glitches. - * - * This is typically called in response to a user decision to minimize latency. In other words, - * call this from a button handler. - */ - void requestReset(); - - /** - * @return true if the audio stream's buffer size is at the maximum value. If no maximum value - * was specified when constructing the LatencyTuner then the value of - * stream->getBufferCapacityInFrames is used - */ - bool isAtMaximumBufferSize(); - - /** - * Set the minimum bufferSize in frames that is used when the tuner is reset. - * You may wish to call requestReset() after calling this. - * @param bufferSize - */ - void setMinimumBufferSize(int32_t bufferSize) { - mMinimumBufferSize = bufferSize; - } - - int32_t getMinimumBufferSize() const { - return mMinimumBufferSize; - } - - /** - * Set the amount the bufferSize will be incremented while tuning. - * By default, this will be one burst. - * - * Note that AAudio will quantize the buffer size to a multiple of the burstSize. - * So the final buffer sizes may not be a multiple of this increment. - * - * @param sizeIncrement - */ - void setBufferSizeIncrement(int32_t sizeIncrement) { - mBufferSizeIncrement = sizeIncrement; - } - - int32_t getBufferSizeIncrement() const { - return mBufferSizeIncrement; - } - -private: - - /** - * Drop the latency down to the minimum and then let it rise back up. - * This is useful if a glitch caused the latency to increase and it hasn't gone back down. - * - * This should only be called in the same thread as tune(). - */ - void reset(); - - enum class State { - Idle, - Active, - AtMax, - Unsupported - } ; - - // arbitrary number of calls to wait before bumping up the latency - static constexpr int32_t kIdleCount = 8; - static constexpr int32_t kDefaultNumBursts = 2; - - AudioStream &mStream; - State mState = State::Idle; - int32_t mMaxBufferSize = 0; - int32_t mPreviousXRuns = 0; - int32_t mIdleCountDown = 0; - int32_t mMinimumBufferSize; - int32_t mBufferSizeIncrement; - std::atomic mLatencyTriggerRequests{0}; // TODO user atomic requester from AAudio - std::atomic mLatencyTriggerResponses{0}; -}; - -} // namespace oboe - -#endif // OBOE_LATENCY_TUNER_ diff --git a/app/src/main/cpp/oboe/include/oboe/Oboe.h b/app/src/main/cpp/oboe/include/oboe/Oboe.h deleted file mode 100644 index c3a0bcab..00000000 --- a/app/src/main/cpp/oboe/include/oboe/Oboe.h +++ /dev/null @@ -1,37 +0,0 @@ -/* - * Copyright (C) 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_OBOE_H -#define OBOE_OBOE_H - -/** - * \mainpage API reference - * - * All documentation is found in the oboe namespace section - * - */ - -#include "oboe/Definitions.h" -#include "oboe/ResultWithValue.h" -#include "oboe/LatencyTuner.h" -#include "oboe/AudioStream.h" -#include "oboe/AudioStreamBase.h" -#include "oboe/AudioStreamBuilder.h" -#include "oboe/Utilities.h" -#include "oboe/Version.h" -#include "oboe/StabilizedCallback.h" - -#endif //OBOE_OBOE_H diff --git a/app/src/main/cpp/oboe/include/oboe/ResultWithValue.h b/app/src/main/cpp/oboe/include/oboe/ResultWithValue.h deleted file mode 100644 index fcb1fac1..00000000 --- a/app/src/main/cpp/oboe/include/oboe/ResultWithValue.h +++ /dev/null @@ -1,155 +0,0 @@ -/* - * Copyright (C) 2018 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_RESULT_WITH_VALUE_H -#define OBOE_RESULT_WITH_VALUE_H - -#include "oboe/Definitions.h" -#include -#include - -namespace oboe { - -/** - * A ResultWithValue can store both the result of an operation (either OK or an error) and a value. - * - * It has been designed for cases where the caller needs to know whether an operation succeeded and, - * if it did, a value which was obtained during the operation. - * - * For example, when reading from a stream the caller needs to know the result of the read operation - * and, if it was successful, how many frames were read. Note that ResultWithValue can be evaluated - * as a boolean so it's simple to check whether the result is OK. - * - * - * ResultWithValue resultOfRead = myStream.read(&buffer, numFrames, timeoutNanoseconds); - * - * if (resultOfRead) { - * LOGD("Frames read: %d", resultOfRead.value()); - * } else { - * LOGD("Error reading from stream: %s", resultOfRead.error()); - * } - * - */ -template -class ResultWithValue { -public: - - /** - * Construct a ResultWithValue containing an error result. - * - * @param error The error - */ - ResultWithValue(oboe::Result error) - : mValue{} - , mError(error) {} - - /** - * Construct a ResultWithValue containing an OK result and a value. - * - * @param value the value to store - */ - explicit ResultWithValue(T value) - : mValue(value) - , mError(oboe::Result::OK) {} - - /** - * Get the result. - * - * @return the result - */ - oboe::Result error() const { - return mError; - } - - /** - * Get the value - * @return - */ - T value() const { - return mValue; - } - - /** - * @return true if OK - */ - explicit operator bool() const { return mError == oboe::Result::OK; } - - /** - * Quick way to check for an error. - * - * The caller could write something like this: - * - * if (!result) { printf("Got error %s\n", convertToText(result.error())); } - * - * - * @return true if an error occurred - */ - bool operator !() const { return mError != oboe::Result::OK; } - - /** - * Implicitly convert to a Result. This enables easy comparison with Result values. Example: - * - * - * ResultWithValue result = openStream(); - * if (result == Result::ErrorNoMemory){ // tell user they're out of memory } - * - */ - operator Result() const { - return mError; - } - - /** - * Create a ResultWithValue from a number. If the number is positive the ResultWithValue will - * have a result of Result::OK and the value will contain the number. If the number is negative - * the result will be obtained from the negative number (numeric error codes can be found in - * AAudio.h) and the value will be null. - * - */ - static ResultWithValue createBasedOnSign(T numericResult){ - - // Ensure that the type is either an integer or float - static_assert(std::is_arithmetic::value, - "createBasedOnSign can only be called for numeric types (int or float)"); - - if (numericResult >= 0){ - return ResultWithValue(numericResult); - } else { - return ResultWithValue(static_cast(numericResult)); - } - } - -private: - const T mValue; - const oboe::Result mError; -}; - -/** - * If the result is `OK` then return the value, otherwise return a human-readable error message. - */ -template -std::ostream& operator<<(std::ostream &strm, const ResultWithValue &result) { - if (!result) { - strm << convertToText(result.error()); - } else { - strm << result.value(); - } - return strm; -} - -} // namespace oboe - - -#endif //OBOE_RESULT_WITH_VALUE_H diff --git a/app/src/main/cpp/oboe/include/oboe/StabilizedCallback.h b/app/src/main/cpp/oboe/include/oboe/StabilizedCallback.h deleted file mode 100644 index 3f1a6896..00000000 --- a/app/src/main/cpp/oboe/include/oboe/StabilizedCallback.h +++ /dev/null @@ -1,75 +0,0 @@ -/* - * Copyright 2018 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_STABILIZEDCALLBACK_H -#define OBOE_STABILIZEDCALLBACK_H - -#include -#include "oboe/AudioStream.h" - -namespace oboe { - -class StabilizedCallback : public AudioStreamCallback { - -public: - explicit StabilizedCallback(AudioStreamCallback *callback); - - DataCallbackResult - onAudioReady(AudioStream *oboeStream, void *audioData, int32_t numFrames) override; - - void onErrorBeforeClose(AudioStream *oboeStream, Result error) override { - return mCallback->onErrorBeforeClose(oboeStream, error); - } - - void onErrorAfterClose(AudioStream *oboeStream, Result error) override { - - // Reset all fields now that the stream has been closed - mFrameCount = 0; - mEpochTimeNanos = 0; - mOpsPerNano = 1; - return mCallback->onErrorAfterClose(oboeStream, error); - } - -private: - - AudioStreamCallback *mCallback = nullptr; - int64_t mFrameCount = 0; - int64_t mEpochTimeNanos = 0; - double mOpsPerNano = 1; - - void generateLoad(int64_t durationNanos); -}; - -/** - * cpu_relax is an architecture specific method of telling the CPU that you don't want it to - * do much work. asm volatile keeps the compiler from optimising these instructions out. - */ -#if defined(__i386__) || defined(__x86_64__) -#define cpu_relax() asm volatile("rep; nop" ::: "memory"); - -#elif defined(__arm__) || defined(__mips__) - #define cpu_relax() asm volatile("":::"memory") - -#elif defined(__aarch64__) -#define cpu_relax() asm volatile("yield" ::: "memory") - -#else -#error "cpu_relax is not defined for this architecture" -#endif - -} - -#endif //OBOE_STABILIZEDCALLBACK_H diff --git a/app/src/main/cpp/oboe/include/oboe/Utilities.h b/app/src/main/cpp/oboe/include/oboe/Utilities.h deleted file mode 100644 index 2c270881..00000000 --- a/app/src/main/cpp/oboe/include/oboe/Utilities.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - * Copyright 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_UTILITIES_H -#define OBOE_UTILITIES_H - -#include -#include -#include -#include "oboe/Definitions.h" - -namespace oboe { - -/** - * Convert an array of floats to an array of 16-bit integers. - * - * @param source the input array. - * @param destination the output array. - * @param numSamples the number of values to convert. - */ -void convertFloatToPcm16(const float *source, int16_t *destination, int32_t numSamples); - -/** - * Convert an array of 16-bit integers to an array of floats. - * - * @param source the input array. - * @param destination the output array. - * @param numSamples the number of values to convert. - */ -void convertPcm16ToFloat(const int16_t *source, float *destination, int32_t numSamples); - -/** - * @return the size of a sample of the given format in bytes or 0 if format is invalid - */ -int32_t convertFormatToSizeInBytes(AudioFormat format); - -/** - * The text is the ASCII symbol corresponding to the supplied Oboe enum value, - * or an English message saying the value is unrecognized. - * This is intended for developers to use when debugging. - * It is not for displaying to users. - * - * @param input object to convert from. @see common/Utilities.cpp for concrete implementations - * @return text representation of an Oboe enum value. There is no need to call free on this. - */ -template -const char * convertToText(FromType input); - -/** - * @param name - * @return the value of a named system property in a string or empty string - */ -std::string getPropertyString(const char * name); - -/** - * @param name - * @param defaultValue - * @return integer value associated with a property or the default value - */ -int getPropertyInteger(const char * name, int defaultValue); - -/** - * Return the version of the SDK that is currently running. - * - * For example, on Android, this would return 27 for Oreo 8.1. - * If the version number cannot be determined then this will return -1. - * - * @return version number or -1 - */ -int getSdkVersion(); - -} // namespace oboe - -#endif //OBOE_UTILITIES_H diff --git a/app/src/main/cpp/oboe/include/oboe/Version.h b/app/src/main/cpp/oboe/include/oboe/Version.h deleted file mode 100644 index 56530305..00000000 --- a/app/src/main/cpp/oboe/include/oboe/Version.h +++ /dev/null @@ -1,92 +0,0 @@ -/* - * Copyright 2017 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef OBOE_VERSIONINFO_H -#define OBOE_VERSIONINFO_H - -#include - -/** - * A note on use of preprocessor defines: - * - * This is one of the few times when it's suitable to use preprocessor defines rather than constexpr - * Why? Because C++11 requires a lot of boilerplate code to convert integers into compile-time - * string literals. The preprocessor, despite it's lack of type checking, is more suited to the task - * - * See: https://stackoverflow.com/questions/6713420/c-convert-integer-to-string-at-compile-time/26824971#26824971 - * - */ - -// Type: 8-bit unsigned int. Min value: 0 Max value: 255. See below for description. -#define OBOE_VERSION_MAJOR 1 - -// Type: 8-bit unsigned int. Min value: 0 Max value: 255. See below for description. -#define OBOE_VERSION_MINOR 6 - -// Type: 16-bit unsigned int. Min value: 0 Max value: 65535. See below for description. -#define OBOE_VERSION_PATCH 1 - -#define OBOE_STRINGIFY(x) #x -#define OBOE_TOSTRING(x) OBOE_STRINGIFY(x) - -// Type: String literal. See below for description. -#define OBOE_VERSION_TEXT \ - OBOE_TOSTRING(OBOE_VERSION_MAJOR) "." \ - OBOE_TOSTRING(OBOE_VERSION_MINOR) "." \ - OBOE_TOSTRING(OBOE_VERSION_PATCH) - -// Type: 32-bit unsigned int. See below for description. -#define OBOE_VERSION_NUMBER ((OBOE_VERSION_MAJOR << 24) | (OBOE_VERSION_MINOR << 16) | OBOE_VERSION_PATCH) - -namespace oboe { - -const char * getVersionText(); - -/** - * Oboe versioning object - */ -struct Version { - /** - * This is incremented when we make breaking API changes. Based loosely on https://semver.org/. - */ - static constexpr uint8_t Major = OBOE_VERSION_MAJOR; - - /** - * This is incremented when we add backwards compatible functionality. Or set to zero when MAJOR is - * incremented. - */ - static constexpr uint8_t Minor = OBOE_VERSION_MINOR; - - /** - * This is incremented when we make backwards compatible bug fixes. Or set to zero when MINOR is - * incremented. - */ - static constexpr uint16_t Patch = OBOE_VERSION_PATCH; - - /** - * Version string in the form MAJOR.MINOR.PATCH. - */ - static constexpr const char * Text = OBOE_VERSION_TEXT; - - /** - * Integer representation of the current Oboe library version. This will always increase when the - * version number changes so can be compared using integer comparison. - */ - static constexpr uint32_t Number = OBOE_VERSION_NUMBER; -}; - -} // namespace oboe -#endif //OBOE_VERSIONINFO_H diff --git a/app/src/main/cpp/oboe/libs/android.arm64-v8a/abi.json b/app/src/main/cpp/oboe/libs/android.arm64-v8a/abi.json deleted file mode 100644 index d1818e36..00000000 --- a/app/src/main/cpp/oboe/libs/android.arm64-v8a/abi.json +++ /dev/null @@ -1 +0,0 @@ -{"abi":"arm64-v8a","api":21,"ndk":21,"stl":"c++_shared"} \ No newline at end of file diff --git a/app/src/main/cpp/oboe/libs/android.arm64-v8a/liboboe.so b/app/src/main/cpp/oboe/libs/android.arm64-v8a/liboboe.so deleted file mode 100644 index bc0e1fac..00000000 Binary files a/app/src/main/cpp/oboe/libs/android.arm64-v8a/liboboe.so and /dev/null differ diff --git a/app/src/main/cpp/oboe/libs/android.armeabi-v7a/abi.json b/app/src/main/cpp/oboe/libs/android.armeabi-v7a/abi.json deleted file mode 100644 index 2a7b1a02..00000000 --- a/app/src/main/cpp/oboe/libs/android.armeabi-v7a/abi.json +++ /dev/null @@ -1 +0,0 @@ -{"abi":"armeabi-v7a","api":16,"ndk":21,"stl":"c++_shared"} \ No newline at end of file diff --git a/app/src/main/cpp/oboe/libs/android.armeabi-v7a/liboboe.so b/app/src/main/cpp/oboe/libs/android.armeabi-v7a/liboboe.so deleted file mode 100644 index 82609af0..00000000 Binary files a/app/src/main/cpp/oboe/libs/android.armeabi-v7a/liboboe.so and /dev/null differ diff --git a/app/src/main/cpp/oboe/libs/android.x86/abi.json b/app/src/main/cpp/oboe/libs/android.x86/abi.json deleted file mode 100644 index edd3d748..00000000 --- a/app/src/main/cpp/oboe/libs/android.x86/abi.json +++ /dev/null @@ -1 +0,0 @@ -{"abi":"x86","api":16,"ndk":21,"stl":"c++_shared"} \ No newline at end of file diff --git a/app/src/main/cpp/oboe/libs/android.x86/liboboe.so b/app/src/main/cpp/oboe/libs/android.x86/liboboe.so deleted file mode 100644 index 14ddd880..00000000 Binary files a/app/src/main/cpp/oboe/libs/android.x86/liboboe.so and /dev/null differ diff --git a/app/src/main/cpp/oboe/libs/android.x86_64/abi.json b/app/src/main/cpp/oboe/libs/android.x86_64/abi.json deleted file mode 100644 index 61b61c8f..00000000 --- a/app/src/main/cpp/oboe/libs/android.x86_64/abi.json +++ /dev/null @@ -1 +0,0 @@ -{"abi":"x86_64","api":21,"ndk":21,"stl":"c++_shared"} \ No newline at end of file diff --git a/app/src/main/cpp/oboe/libs/android.x86_64/liboboe.so b/app/src/main/cpp/oboe/libs/android.x86_64/liboboe.so deleted file mode 100644 index dde908c0..00000000 Binary files a/app/src/main/cpp/oboe/libs/android.x86_64/liboboe.so and /dev/null differ diff --git a/app/src/main/cpp/oboe/module.json b/app/src/main/cpp/oboe/module.json deleted file mode 100644 index c81458f9..00000000 --- a/app/src/main/cpp/oboe/module.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "export_libraries": [], - "library_name": null, - "android": { - "export_libraries": [], - "library_name": null - } -} \ No newline at end of file diff --git a/app/src/main/cpp/oboe/oboeConfig.cmake b/app/src/main/cpp/oboe/oboeConfig.cmake deleted file mode 100644 index 6ab7e177..00000000 --- a/app/src/main/cpp/oboe/oboeConfig.cmake +++ /dev/null @@ -1,13 +0,0 @@ -if(ANDROID AND NOT TARGET oboe::oboe) - #set(OBOE_LIBRARY "${CMAKE_CURRENT_SOURCE_DIR}/libs/android.${CMAKE_ANDROID_ARCH_ABI}/liboboe.so") - #set(OBOE_INCLUDE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/include") - add_library(oboe::oboe SHARED IMPORTED) - set_target_properties(oboe::oboe PROPERTIES - IMPORTED_LOCATION "${CMAKE_CURRENT_LIST_DIR}/libs/android.${CMAKE_ANDROID_ARCH_ABI}/liboboe.so" - INTERFACE_INCLUDE_DIRECTORIES "${CMAKE_CURRENT_LIST_DIR}/include" - ) - #mark_as_advanced(OBOE_LIBRARY OBOE_INCLUDE_DIR) -endif() - -#include(FindPackageHandleStandardArgs) -#find_package_handle_standard_args(Oboe REQUIRED_VARS OBOE_LIBRARY OBOE_INCLUDE_DIR) diff --git a/app/src/main/cpp/oboe/oboeConfigVersion.cmake b/app/src/main/cpp/oboe/oboeConfigVersion.cmake deleted file mode 100644 index 73a0aac9..00000000 --- a/app/src/main/cpp/oboe/oboeConfigVersion.cmake +++ /dev/null @@ -1,14 +0,0 @@ -set(PACKAGE_FIND_VERSION_MAJOR 1) -set(PACKAGE_FIND_VERSION_MINOR 6) -set(PACKAGE_FIND_VERSION_PATCH 1) -set(PACKAGE_FIND_VERSION_COUNT 3) -set(PACKAGE_VERSION "${PACKAGE_FIND_VERSION_MAJOR}.${PACKAGE_FIND_VERSION_MINOR}.${PACKAGE_FIND_VERSION_PATCH}") - -if("${PACKAGE_VERSION}" VERSION_LESS "${PACKAGE_FIND_VERSION}") - set(PACKAGE_VERSION_COMPATIBLE FALSE) -else() - set(PACKAGE_VERSION_COMPATIBLE TRUE) - if("${PACKAGE_VERSION}" VERSION_EQUAL "${PACKAGE_FIND_VERSION}") - set(PACKAGE_VERSION_EXACT TRUE) - endif() -endif()