#include "Audio_Null.h" #include "helper/HL_Log.h" #include #include #define LOG_SUBSYSTEM "NULL audio" using namespace Audio; NullTimer::NullTimer(int interval, Delegate *delegate, const char* name) :mShutdown(false), mDelegate(delegate), mInterval(interval), mThreadName(name) { start(); } NullTimer::~NullTimer() { stop(); } void NullTimer::start() { mShutdown = false; mWorkerThread = std::thread(&NullTimer::run, this); } void NullTimer::stop() { mShutdown = true; if (mWorkerThread.joinable()) mWorkerThread.join(); } void NullTimer::run() { mTail = 0; while (!mShutdown) { // Get current timestamp std::chrono::system_clock::time_point timestamp = std::chrono::system_clock::now(); while (mTail >= mInterval * 1000) { if (mDelegate) mDelegate->onTimerSignal(*this); mTail -= mInterval * 1000; } // Sleep for mInterval - mTail milliseconds std::this_thread::sleep_for(std::chrono::microseconds(mInterval * 1000 - mTail)); mTail += (int)std::chrono::duration_cast(std::chrono::system_clock::now() - timestamp).count(); } } // --------------------- NullInputDevice ------------------------- NullInputDevice::NullInputDevice() :mBuffer(nullptr) { } NullInputDevice::~NullInputDevice() { internalClose(); } bool NullInputDevice::open() { mBuffer = malloc(AUDIO_MIC_BUFFER_SIZE); memset(mBuffer, 0, AUDIO_MIC_BUFFER_SIZE); mTimeCounter = 0; mDataCounter = 0; // Creation of timer starts it also. So first onTimerSignal can come even before open() returns. mTimer = std::make_shared(AUDIO_MIC_BUFFER_LENGTH, this, "NullMicrophoneThread"); return true; } void NullInputDevice::internalClose() { mTimer.reset(); if (mBuffer) { free(mBuffer); mBuffer = nullptr; } ICELogInfo(<<"Pseudocaptured " << mTimeCounter << " milliseconds , " << mDataCounter << " bytes."); } void NullInputDevice::close() { internalClose(); } Format NullInputDevice::getFormat() { assert (Format().sizeFromTime(AUDIO_MIC_BUFFER_LENGTH) == AUDIO_MIC_BUFFER_SIZE); return Format(); } void NullInputDevice::onTimerSignal(NullTimer& timer) { mTimeCounter += AUDIO_MIC_BUFFER_LENGTH; mDataCounter += AUDIO_MIC_BUFFER_SIZE; if (mConnection) mConnection->onMicData(getFormat(), mBuffer, AUDIO_MIC_BUFFER_SIZE); } // --------------------- NullOutputDevice -------------------------- NullOutputDevice::NullOutputDevice() :mBuffer(nullptr) { } NullOutputDevice::~NullOutputDevice() { internalClose(); } bool NullOutputDevice::open() { mTimeCounter = 0; mDataCounter = 0; mBuffer = malloc(AUDIO_SPK_BUFFER_SIZE); // Creation of timer starts it also. So first onSpkData() can come before open() returns even. mTimer = std::make_shared(AUDIO_SPK_BUFFER_LENGTH, this, "NullSpeakerThread"); return true; } void NullOutputDevice::internalClose() { mTimer.reset(); free(mBuffer); mBuffer = nullptr; ICELogInfo(<< "Pseudoplayed " << mTimeCounter << " milliseconds, " << mDataCounter << " bytes."); } void NullOutputDevice::close() { internalClose(); } Format NullOutputDevice::getFormat() { assert (Format().sizeFromTime(AUDIO_SPK_BUFFER_LENGTH) == AUDIO_SPK_BUFFER_SIZE); return Format(); } void NullOutputDevice::onTimerSignal(NullTimer &timer) { mTimeCounter += AUDIO_SPK_BUFFER_LENGTH; mDataCounter += AUDIO_SPK_BUFFER_SIZE; if (mConnection) mConnection->onSpkData(getFormat(), mBuffer, AUDIO_SPK_BUFFER_SIZE); } // ---------------------- NullEnumerator -------------------------- NullEnumerator::NullEnumerator() {} NullEnumerator::~NullEnumerator() {} void NullEnumerator::open(int direction) {} void NullEnumerator::close() {} int NullEnumerator::count() { return 1; } std::tstring NullEnumerator::nameAt(int index) { #if defined(TARGET_WIN) return L"null"; #else return "null"; #endif } int NullEnumerator::idAt(int index) { return 0; } int NullEnumerator::indexOfDefaultDevice() { return 0; }