cannam@140: #include "portaudiocpp/CppFunCallbackStream.hxx" cannam@140: cannam@140: #include "portaudiocpp/StreamParameters.hxx" cannam@140: #include "portaudiocpp/Exception.hxx" cannam@140: cannam@140: namespace portaudio cannam@140: { cannam@140: namespace impl cannam@140: { cannam@140: ////// cannam@140: /// Adapts any a C++ callback to a C-callable function (ie this function). A cannam@140: /// pointer to a struct with the C++ function pointer and the actual user data should be cannam@140: /// passed as the ``userData'' parameter when setting up the callback. cannam@140: ////// cannam@140: int cppCallbackToPaCallbackAdapter(const void *inputBuffer, void *outputBuffer, unsigned long numFrames, cannam@140: const PaStreamCallbackTimeInfo *timeInfo, PaStreamCallbackFlags statusFlags, void *userData) cannam@140: { cannam@140: FunCallbackStream::CppToCCallbackData *data = static_cast(userData); cannam@140: return data->funPtr(inputBuffer, outputBuffer, numFrames, timeInfo, statusFlags, data->userData); cannam@140: } cannam@140: } cannam@140: cannam@140: // ----------------------------------------------------------------------------------- cannam@140: cannam@140: FunCallbackStream::CppToCCallbackData::CppToCCallbackData() cannam@140: { cannam@140: } cannam@140: cannam@140: FunCallbackStream::CppToCCallbackData::CppToCCallbackData(CallbackFunPtr funPtr, void *userData) : funPtr(funPtr), userData(userData) cannam@140: { cannam@140: } cannam@140: cannam@140: void FunCallbackStream::CppToCCallbackData::init(CallbackFunPtr funPtr, void *userData) cannam@140: { cannam@140: this->funPtr = funPtr; cannam@140: this->userData = userData; cannam@140: } cannam@140: cannam@140: // ----------------------------------------------------------------------------------- cannam@140: cannam@140: FunCallbackStream::FunCallbackStream() cannam@140: { cannam@140: } cannam@140: cannam@140: FunCallbackStream::FunCallbackStream(const StreamParameters ¶meters, CallbackFunPtr funPtr, void *userData) : adapterData_(funPtr, userData) cannam@140: { cannam@140: open(parameters); cannam@140: } cannam@140: cannam@140: FunCallbackStream::~FunCallbackStream() cannam@140: { cannam@140: try cannam@140: { cannam@140: close(); cannam@140: } cannam@140: catch (...) cannam@140: { cannam@140: // ignore all errors cannam@140: } cannam@140: } cannam@140: cannam@140: void FunCallbackStream::open(const StreamParameters ¶meters, CallbackFunPtr funPtr, void *userData) cannam@140: { cannam@140: adapterData_.init(funPtr, userData); cannam@140: open(parameters); cannam@140: } cannam@140: cannam@140: void FunCallbackStream::open(const StreamParameters ¶meters) cannam@140: { cannam@140: PaError err = Pa_OpenStream(&stream_, parameters.inputParameters().paStreamParameters(), parameters.outputParameters().paStreamParameters(), cannam@140: parameters.sampleRate(), parameters.framesPerBuffer(), parameters.flags(), &impl::cppCallbackToPaCallbackAdapter, cannam@140: static_cast(&adapterData_)); cannam@140: cannam@140: if (err != paNoError) cannam@140: { cannam@140: throw PaException(err); cannam@140: } cannam@140: } cannam@140: cannam@140: // ----------------------------------------------------------------------------------- cannam@140: }