20 #include "JackPortAudioDevices.h" 21 #include "JackError.h" 26 PortAudioDevices::PortAudioDevices()
30 jack_log(
"Initializing PortAudio...");
35 for (
id = 0;
id < fNumDevice;
id++) {
38 fHostName =
new string[fNumHostApi];
39 for (
id = 0;
id < fNumHostApi;
id++) {
47 PortAudioDevices::~PortAudioDevices()
63 return fDeviceInfo[id];
68 return string(fDeviceInfo[
id]->name);
71 string PortAudioDevices::GetHostFromDevice(
PaDeviceInfo* device)
73 return fHostName[device->hostApi];
78 return fHostName[fDeviceInfo[id]->hostApi];
83 string hostname = GetHostFromDevice(
id);
84 string devicename = GetDeviceName(
id);
86 if (hostname.compare(
"Windows DirectSound") == 0) {
87 hostname = string(
"DirectSound");
89 return (hostname +
"::" + devicename);
92 string PortAudioDevices::GetFullName(std::string hostname, std::string devicename)
95 if (hostname.compare(
"Windows DirectSound") == 0) {
96 hostname = string(
"DirectSound");
98 return (hostname +
"::" + devicename);
105 if (fullname.size() == 0) {
109 string::size_type separator = fullname.find(
"::", 0);
111 if (separator == string::npos) {
115 char* hostname = (
char*)malloc(separator + 9);
116 fill_n(hostname, separator + 9, 0);
117 fullname.copy(hostname, separator);
120 if (strcmp(hostname,
"DirectSound") == 0) {
121 strcpy(hostname,
"Windows DirectSound");
123 string devicename = fullname.substr(separator + 2);
125 for (
PaDeviceIndex dev_id = 0; dev_id < fNumDevice; dev_id++) {
126 bool flag = (isInput) ? (fDeviceInfo[dev_id]->maxInputChannels > 0) : (fDeviceInfo[dev_id]->maxOutputChannels > 0);
127 if ((GetHostFromDevice(dev_id).compare(hostname) == 0)
128 && (GetDeviceName(dev_id).compare(devicename) == 0)
131 ret = fDeviceInfo[dev_id];
140 static double standardSampleRates[] =
142 8000.0, 9600.0, 11025.0, 12000.0, 16000.0, 22050.0, 24000.0, 32000.0,
143 44100.0, 48000.0, 88200.0, 96000.0, 192000.0, -1
149 for (i = 0; standardSampleRates[i] > 0; i++) {
152 if (printCount == 0) {
153 jack_info(
"\t%8.2f", standardSampleRates[i]);
155 }
else if (printCount == 4) {
156 jack_info(
",\n\t%8.2f", standardSampleRates[i]);
159 jack_info(
", %8.2f", standardSampleRates[i]);
171 int PortAudioDevices::GetInputDeviceFromName(
const char* devicename,
PaDeviceIndex&
id,
int& max_input)
173 string fullname = string(devicename);
174 PaDeviceInfo* device = GetDeviceFromFullName(fullname,
id,
true);
176 max_input = device->maxInputChannels;
179 if (fullname.size()) {
180 jack_error(
"Can't open %s, PortAudio will use default input device.", devicename);
185 max_input = GetDeviceInfo(
id)->maxInputChannels;
190 int PortAudioDevices::GetOutputDeviceFromName(
const char* devicename,
PaDeviceIndex&
id,
int& max_output)
192 string fullname = string(devicename);
193 PaDeviceInfo* device = GetDeviceFromFullName(fullname,
id,
false);
195 max_output = device->maxOutputChannels;
198 if (fullname.size()) {
199 jack_error(
"Can't open %s, PortAudio will use default output device.", devicename);
204 max_output = GetDeviceInfo(
id)->maxOutputChannels;
209 int PortAudioDevices::GetPreferredBufferSize(
PaDeviceIndex id)
211 #if defined(WIN32) && defined(HAVE_ASIO) 214 long minLatency, maxLatency, preferredLatency, granularity;
218 jack_info(
"ASIO minimum buffer size = %ld", minLatency);
219 jack_info(
"ASIO maximum buffer size = %ld", maxLatency);
220 jack_info(
"ASIO preferred buffer size = %ld", preferredLatency);
222 if (granularity == -1) {
223 jack_info(
"ASIO buffer granularity = power of 2");
225 jack_info(
"ASIO buffer granularity = %ld", granularity);
228 return preferredLatency;
236 void PortAudioDevices::DisplayDevicesNames()
240 jack_info(
"********************** Devices list, %d detected **********************", fNumDevice);
242 for (
id = 0;
id < fNumDevice;
id++) {
243 jack_info(
"-------- device #%d ------------------------------------------------",
id);
247 }
else if (
id ==
Pa_GetHostApiInfo(fDeviceInfo[
id]->hostApi)->defaultInputDevice) {
254 }
else if (
id ==
Pa_GetHostApiInfo(fDeviceInfo[
id]->hostApi)->defaultOutputDevice) {
260 jack_info(
"Name = %s", GetFullName(
id).c_str());
261 jack_info(
"Max inputs = %d", fDeviceInfo[
id]->maxInputChannels);
262 jack_info(
"Max outputs = %d", fDeviceInfo[
id]->maxOutputChannels);
264 #if defined(WIN32) && defined(HAVE_ASIO) 267 long minLatency, maxLatency, preferredLatency, granularity;
271 jack_info(
"ASIO minimum buffer size = %ld", minLatency);
272 jack_info(
"ASIO maximum buffer size = %ld", maxLatency);
273 jack_info(
"ASIO preferred buffer size = %ld", preferredLatency);
275 if (granularity == -1) {
276 jack_info(
"ASIO buffer granularity = power of 2");
278 jack_info(
"ASIO buffer granularity = %ld", granularity);
282 jack_info(
"Default sample rate = %8.2f", fDeviceInfo[
id]->defaultSampleRate);
285 inputParameters.
device = id;
286 inputParameters.
channelCount = fDeviceInfo[id]->maxInputChannels;
291 outputParameters.
device = id;
292 outputParameters.
channelCount = fDeviceInfo[id]->maxOutputChannels;
297 jack_info(
"**************************** End of list ****************************");
303 if (fDeviceInfo[
id]->maxInputChannels && fDeviceInfo[
id]->maxOutputChannels) {
308 if ((i !=
id) && (GetDeviceName(i) == GetDeviceName(
id))) {
309 if ((fDeviceInfo[i]->maxInputChannels && fDeviceInfo[
id]->maxOutputChannels)
310 || (fDeviceInfo[i]->maxOutputChannels && fDeviceInfo[
id]->maxInputChannels)) {
PaError Pa_Initialize(void)
PaDeviceIndex Pa_GetDefaultInputDevice(void)
PaDeviceIndex Pa_GetDeviceCount(void)
SERVER_EXPORT void jack_error(const char *fmt,...)
SERVER_EXPORT void jack_info(const char *fmt,...)
PaError Pa_IsFormatSupported(const PaStreamParameters *inputParameters, const PaStreamParameters *outputParameters, double sampleRate)
void * hostApiSpecificStreamInfo
PaError PaAsio_GetAvailableBufferSizes(PaDeviceIndex device, long *minBufferSizeFrames, long *maxBufferSizeFrames, long *preferredBufferSizeFrames, long *granularity)
PaSampleFormat sampleFormat
const PaHostApiInfo * Pa_GetHostApiInfo(PaHostApiIndex hostApi)
PaHostApiIndex Pa_GetHostApiCount(void)
const PaDeviceInfo * Pa_GetDeviceInfo(PaDeviceIndex device)
PaDeviceIndex Pa_GetDefaultOutputDevice(void)
#define paFormatIsSupported
const char * Pa_GetErrorText(PaError errorCode)
SERVER_EXPORT void jack_log(const char *fmt,...)
PaError Pa_Terminate(void)