Browse Source

Android: Added support for oboe input device without output

tags/2021-05-28
ed 5 years ago
parent
commit
cb8a40d47c
1 changed files with 43 additions and 40 deletions
  1. +43
    -40
      modules/juce_audio_devices/native/juce_android_Oboe.cpp

+ 43
- 40
modules/juce_audio_devices/native/juce_android_Oboe.cpp View File

@@ -91,33 +91,43 @@ struct OboeAudioIODeviceBufferHelpers<float>
static void convertFromOboe (const float* srcInterleaved, AudioBuffer<float>& audioBuffer, int numSamples)
{
// No need to convert, we instructed the buffer to point to the src data directly already
jassert (audioBuffer.getWritePointer (0) != srcInterleaved);
auto numChannels = audioBuffer.getNumChannels();
for (int i = 0; i < audioBuffer.getNumChannels(); ++i)
if (numChannels > 0)
{
using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::NonConst>;
using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved, AudioData::Const>;
// No need to convert, we instructed the buffer to point to the src data directly already
jassert (audioBuffer.getWritePointer (0) != srcInterleaved);
DstSampleType dstData (audioBuffer.getWritePointer (i));
SrcSampleType srcData (srcInterleaved + i, audioBuffer.getNumChannels());
dstData.convertSamples (srcData, numSamples);
for (int i = 0; i < numChannels; ++i)
{
using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::NonConst>;
using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved, AudioData::Const>;
DstSampleType dstData (audioBuffer.getWritePointer (i));
SrcSampleType srcData (srcInterleaved + i, audioBuffer.getNumChannels());
dstData.convertSamples (srcData, numSamples);
}
}
}
static void convertToOboe (const AudioBuffer<float>& audioBuffer, float* dstInterleaved, int numSamples)
{
// No need to convert, we instructed the buffer to point to the src data directly already
jassert (audioBuffer.getReadPointer (0) != dstInterleaved);
auto numChannels = audioBuffer.getNumChannels();
for (int i = 0; i < audioBuffer.getNumChannels(); ++i)
if (numChannels > 0)
{
using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved, AudioData::NonConst>;
using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::Const>;
// No need to convert, we instructed the buffer to point to the src data directly already
jassert (audioBuffer.getReadPointer (0) != dstInterleaved);
DstSampleType dstData (dstInterleaved + i, audioBuffer.getNumChannels());
SrcSampleType srcData (audioBuffer.getReadPointer (i));
dstData.convertSamples (srcData, numSamples);
for (int i = 0; i < numChannels; ++i)
{
using DstSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::Interleaved, AudioData::NonConst>;
using SrcSampleType = AudioData::Pointer<AudioData::Float32, AudioData::NativeEndian, AudioData::NonInterleaved, AudioData::Const>;
DstSampleType dstData (dstInterleaved + i, audioBuffer.getNumChannels());
SrcSampleType srcData (audioBuffer.getReadPointer (i));
dstData.convertSamples (srcData, numSamples);
}
}
}
};
@@ -148,8 +158,6 @@ public:
supportedOutputSampleRates (supportedOutputSampleRatesToUse),
maxNumOutputChannels (maxNumOutputChannelsToUse)
{
// At least an input or an output has to be supported by the device!
jassert (inputDeviceId != -1 || outputDeviceId != -1);
}
~OboeAudioIODevice() override
@@ -380,7 +388,7 @@ private:
// We initially try to open a stream with a buffer size returned from
// android.media.property.OUTPUT_FRAMES_PER_BUFFER property, but then we verify the actual
// size after the stream is open.
OboeAudioIODevice::OboeStream tempStream (-1,
OboeAudioIODevice::OboeStream tempStream (oboe::kUnspecified,
oboe::Direction::Output,
oboe::SharingMode::Exclusive,
2,
@@ -695,7 +703,7 @@ private:
ignoreUnused (deviceId, numChannels, sampleRate, expectedBufferSize);
ignoreUnused (streamFormat, bitDepth);
jassert (numChannels == nativeStream->getChannelCount());
jassert (numChannels == 0 || numChannels == nativeStream->getChannelCount());
jassert (expectedSampleRate == 0 || expectedSampleRate == nativeStream->getSampleRate());
jassert (format == nativeStream->getFormat());
}
@@ -951,7 +959,7 @@ private:
Thread::sleep (1);
outputStream = nullptr;
outputStream.reset (new OboeStream (-1,
outputStream.reset (new OboeStream (oboe::kUnspecified,
oboe::Direction::Output,
oboe::SharingMode::Exclusive,
numOutputChannels,
@@ -1058,9 +1066,6 @@ public:
StringArray getDeviceNames (bool wantInputNames) const override
{
if (inputDevices.isEmpty() && outputDevices.isEmpty())
return StringArray (OboeAudioIODevice::oboeTypeName);
StringArray names;
for (auto& device : wantInputNames ? inputDevices : outputDevices)
@@ -1099,12 +1104,8 @@ public:
auto outputDeviceInfo = getDeviceInfoForName (outputDeviceName, false);
auto inputDeviceInfo = getDeviceInfoForName (inputDeviceName, true);
if (outputDeviceInfo.name.isEmpty() && inputDeviceInfo.name.isEmpty())
{
// Invalid device name passed. It must be one of the names returned by getDeviceNames().
jassertfalse;
if (outputDeviceInfo.id < 0 && inputDeviceInfo.id < 0)
return nullptr;
}
auto& name = outputDeviceInfo.name.isNotEmpty() ? outputDeviceInfo.name
: inputDeviceInfo.name;
@@ -1130,8 +1131,8 @@ public:
{
auto sampleRates = OboeAudioIODevice::getDefaultSampleRates();
inputDevices .add ({ OboeAudioIODevice::oboeTypeName, -1, sampleRates, 1 });
outputDevices.add ({ OboeAudioIODevice::oboeTypeName, -1, sampleRates, 2 });
inputDevices .add ({ "System Default (Input)", oboe::kUnspecified, sampleRates, 1 });
outputDevices.add ({ "System Default (Output)", oboe::kUnspecified, sampleRates, 2 });
if (! supportsDevicesInfo())
return;
@@ -1279,19 +1280,21 @@ public:
struct DeviceInfo
{
String name;
int id;
int id = -1;
Array<int> sampleRates;
int numChannels;
};
DeviceInfo getDeviceInfoForName (const String& name, bool isInput)
{
if (name.isEmpty())
return {};
for (auto& device : isInput ? inputDevices : outputDevices)
if (device.name == name)
return device;
if (name.isNotEmpty())
{
for (auto& device : isInput ? inputDevices : outputDevices)
{
if (device.name == name)
return device;
}
}
return {};
}
@@ -1319,7 +1322,7 @@ class OboeRealtimeThread : private oboe::AudioStreamCallback
public:
OboeRealtimeThread()
: testStream (new OboeStream (-1,
: testStream (new OboeStream (oboe::kUnspecified,
oboe::Direction::Output,
oboe::SharingMode::Exclusive,
1,
@@ -1332,7 +1335,7 @@ public:
// Fallback to I16 stream format if Float has not worked
if (! testStream->openedOk())
{
testStream.reset (new OboeStream (-1,
testStream.reset (new OboeStream (oboe::kUnspecified,
oboe::Direction::Output,
oboe::SharingMode::Exclusive,
1,


Loading…
Cancel
Save