Can now set output sample rate, demodulator sample rate doesn't adjust yet so I find it rather hilarious at the moment :)

This commit is contained in:
Charles J. Cliffe 2015-03-13 22:25:07 -04:00
parent fa54aab01f
commit b197a7ddb2
3 changed files with 51 additions and 11 deletions

View File

@ -392,7 +392,8 @@ void AppFrame::OnMenu(wxCommandEvent& event) {
if (evId == menu_id + j) { if (evId == menu_id + j) {
//audioSampleRateMenuItems[menu_id+j]; //audioSampleRateMenuItems[menu_id+j];
std::cout << "Would set audio sample rate on device " << mdevices_i->second.name << " (" << mdevices_i->first << ") to " << (*srate) << "Hz" << std::endl; //std::cout << "Would set audio sample rate on device " << mdevices_i->second.name << " (" << mdevices_i->first << ") to " << (*srate) << "Hz" << std::endl;
AudioThread::setDeviceSampleRate(mdevices_i->first, *srate);
} }
j++; j++;

View File

@ -6,11 +6,12 @@
#include <memory.h> #include <memory.h>
std::map<int, AudioThread *> AudioThread::deviceController; std::map<int, AudioThread *> AudioThread::deviceController;
std::map<int, int> AudioThread::deviceSampleRate;
std::map<int, std::thread *> AudioThread::deviceThread; std::map<int, std::thread *> AudioThread::deviceThread;
AudioThread::AudioThread(AudioThreadInputQueue *inputQueue, DemodulatorThreadCommandQueue* threadQueueNotify) : AudioThread::AudioThread(AudioThreadInputQueue *inputQueue, DemodulatorThreadCommandQueue* threadQueueNotify) :
currentInput(NULL), inputQueue(inputQueue), audioQueuePtr(0), underflowCount(0), terminated(false), active(false), outputDevice(-1), gain( currentInput(NULL), inputQueue(inputQueue), audioQueuePtr(0), underflowCount(0), terminated(false), active(false), outputDevice(-1), gain(
1.0), threadQueueNotify(threadQueueNotify) { 1.0), threadQueueNotify(threadQueueNotify), sampleRate(DEFAULT_AUDIO_SAMPLE_RATE), nBufferFrames(256) {
boundThreads = new std::vector<AudioThread *>; boundThreads = new std::vector<AudioThread *>;
} }
@ -217,18 +218,32 @@ void AudioThread::enumerateDevices(std::vector<RtAudio::DeviceInfo> &devs) {
} }
} }
void AudioThread::setDeviceSampleRate(int deviceId, int sampleRate) {
if (deviceController.find(deviceId) != deviceController.end()) {
AudioThreadCommand refreshDevice;
refreshDevice.cmd = AudioThreadCommand::AUDIO_THREAD_CMD_SET_SAMPLE_RATE;
refreshDevice.int_value = sampleRate;
deviceController[deviceId]->getCommandQueue()->push(refreshDevice);
}
}
void AudioThread::setSampleRate(int sampleRate) {
deviceSampleRate[outputDevice] = sampleRate;
this->sampleRate = sampleRate;
dac.stopStream();
dac.closeStream();
dac.openStream(&parameters, NULL, RTAUDIO_FLOAT32, sampleRate, &nBufferFrames, &audioCallback, (void *) this, &opts);
dac.startStream();
}
void AudioThread::setupDevice(int deviceId) { void AudioThread::setupDevice(int deviceId) {
parameters.deviceId = deviceId; parameters.deviceId = deviceId;
parameters.nChannels = 2; parameters.nChannels = 2;
parameters.firstChannel = 0; parameters.firstChannel = 0;
unsigned int sampleRate = DEFAULT_AUDIO_SAMPLE_RATE;
unsigned int bufferFrames = 256;
RtAudio::StreamOptions opts;
opts.streamName = "CubicSDR Audio Output"; opts.streamName = "CubicSDR Audio Output";
try { try {
if (deviceController.find(outputDevice.load()) != deviceController.end()) { if (deviceController.find(outputDevice.load()) != deviceController.end()) {
deviceController[outputDevice.load()]->removeThread(this); deviceController[outputDevice.load()]->removeThread(this);
} }
@ -240,11 +255,18 @@ void AudioThread::setupDevice(int deviceId) {
if (deviceController.find(parameters.deviceId) == deviceController.end()) { if (deviceController.find(parameters.deviceId) == deviceController.end()) {
deviceController[parameters.deviceId] = new AudioThread(NULL, NULL); deviceController[parameters.deviceId] = new AudioThread(NULL, NULL);
deviceController[parameters.deviceId]->setInitOutputDevice(parameters.deviceId); int srate = DEFAULT_AUDIO_SAMPLE_RATE;
if (deviceSampleRate.find(parameters.deviceId) != deviceSampleRate.end()) {
srate = deviceSampleRate[parameters.deviceId];
} else {
deviceSampleRate[parameters.deviceId] = srate;
}
deviceController[parameters.deviceId]->setInitOutputDevice(parameters.deviceId, srate);
deviceController[parameters.deviceId]->bindThread(this); deviceController[parameters.deviceId]->bindThread(this);
deviceThread[parameters.deviceId] = new std::thread(&AudioThread::threadMain, deviceController[parameters.deviceId]); deviceThread[parameters.deviceId] = new std::thread(&AudioThread::threadMain, deviceController[parameters.deviceId]);
} else if (deviceController[parameters.deviceId] == this) { } else if (deviceController[parameters.deviceId] == this) {
dac.openStream(&parameters, NULL, RTAUDIO_FLOAT32, sampleRate, &bufferFrames, &audioCallback, (void *) this, &opts); dac.openStream(&parameters, NULL, RTAUDIO_FLOAT32, sampleRate, &nBufferFrames, &audioCallback, (void *) this, &opts);
dac.startStream(); dac.startStream();
} else { } else {
deviceController[parameters.deviceId]->bindThread(this); deviceController[parameters.deviceId]->bindThread(this);
@ -267,8 +289,16 @@ int AudioThread::getOutputDevice() {
return outputDevice; return outputDevice;
} }
void AudioThread::setInitOutputDevice(int deviceId) { void AudioThread::setInitOutputDevice(int deviceId, int sampleRate) {
outputDevice = deviceId; outputDevice = deviceId;
if (sampleRate == -1) {
if (deviceSampleRate.find(parameters.deviceId) != deviceSampleRate.end()) {
sampleRate = deviceSampleRate[deviceId];
}
} else {
deviceSampleRate[deviceId] = sampleRate;
}
this->sampleRate = sampleRate;
} }
void AudioThread::threadMain() { void AudioThread::threadMain() {
@ -299,6 +329,9 @@ void AudioThread::threadMain() {
if (command.cmd == AudioThreadCommand::AUDIO_THREAD_CMD_SET_DEVICE) { if (command.cmd == AudioThreadCommand::AUDIO_THREAD_CMD_SET_DEVICE) {
setupDevice(command.int_value); setupDevice(command.int_value);
} }
if (command.cmd == AudioThreadCommand::AUDIO_THREAD_CMD_SET_SAMPLE_RATE) {
setSampleRate(command.int_value);
}
} }
if (deviceController[parameters.deviceId] != this) { if (deviceController[parameters.deviceId] != this) {

View File

@ -32,7 +32,7 @@ public:
class AudioThreadCommand { class AudioThreadCommand {
public: public:
enum AudioThreadCommandEnum { enum AudioThreadCommandEnum {
AUDIO_THREAD_CMD_NULL, AUDIO_THREAD_CMD_SET_DEVICE AUDIO_THREAD_CMD_NULL, AUDIO_THREAD_CMD_SET_DEVICE, AUDIO_THREAD_CMD_SET_SAMPLE_RATE
}; };
AudioThreadCommand() : AudioThreadCommand() :
@ -65,8 +65,9 @@ public:
static void enumerateDevices(std::vector<RtAudio::DeviceInfo> &devs); static void enumerateDevices(std::vector<RtAudio::DeviceInfo> &devs);
void setupDevice(int deviceId); void setupDevice(int deviceId);
void setInitOutputDevice(int deviceId); void setInitOutputDevice(int deviceId, int sampleRate=-1);
int getOutputDevice(); int getOutputDevice();
void setSampleRate(int sampleRate);
void threadMain(); void threadMain();
void terminate(); void terminate();
@ -80,17 +81,22 @@ public:
private: private:
RtAudio dac; RtAudio dac;
unsigned int nBufferFrames;
RtAudio::StreamOptions opts;
RtAudio::StreamParameters parameters; RtAudio::StreamParameters parameters;
AudioThreadCommandQueue cmdQueue; AudioThreadCommandQueue cmdQueue;
DemodulatorThreadCommandQueue* threadQueueNotify; DemodulatorThreadCommandQueue* threadQueueNotify;
int sampleRate;
public: public:
void bindThread(AudioThread *other); void bindThread(AudioThread *other);
void removeThread(AudioThread *other); void removeThread(AudioThread *other);
static std::map<int,AudioThread *> deviceController; static std::map<int,AudioThread *> deviceController;
static std::map<int,int> deviceSampleRate;
static std::map<int,std::thread *> deviceThread; static std::map<int,std::thread *> deviceThread;
static void deviceCleanup(); static void deviceCleanup();
static void setDeviceSampleRate(int deviceId, int sampleRate);
std::atomic<std::vector<AudioThread *> *> boundThreads; std::atomic<std::vector<AudioThread *> *> boundThreads;
}; };