86 lines
1.8 KiB
C++
86 lines
1.8 KiB
C++
#include "RenderThread.h"
|
|
|
|
#include "HAL/PlatformProcess.h"
|
|
#include "Singleton/MidiSequencer.h"
|
|
#include "Singleton/MixerList.h"
|
|
#include "Mixer/MixerTrack.h"
|
|
#include "PluginHost/PluginHost.h"
|
|
#include "Singleton/PluginHostList.h"
|
|
|
|
void FInstrumentRenderThread::DoThreadedWork()
|
|
{
|
|
PluginHost->Process(FrameNum);
|
|
--Counter;
|
|
}
|
|
|
|
FAudioRenderThread::FAudioRenderThread()
|
|
{
|
|
BlockSize = 512;
|
|
Size = BlockSize * 16;
|
|
IsRunning = true;
|
|
}
|
|
|
|
bool FAudioRenderThread::Init()
|
|
{
|
|
ThreadPool = FQueuedThreadPool::Allocate();
|
|
ThreadPool->Create(FPlatformMisc::NumberOfIOWorkerThreadsToSpawn() * 2, 128 * 1024);
|
|
Buffer.SetCapacity(Size);
|
|
return true;
|
|
}
|
|
|
|
uint32 FAudioRenderThread::Run()
|
|
{
|
|
FPortAudioAPI& AudioAPI = FPortAudioAPI::Get();
|
|
FMixerList& MixerList = FMixerList::Get();
|
|
FPluginHostList& PluginHostList = FPluginHostList::Get();
|
|
FMidiSequencer& MidiSequencer = FMidiSequencer::Get();
|
|
|
|
FMixerTrack* MasterTrack = MixerList.GetMaster();
|
|
|
|
while (IsRunning.load())
|
|
{
|
|
const float Seconds = 1.f / (SampleRate / (BlockSize / 4));
|
|
|
|
AudioAPI.ProcessMessage();
|
|
if (Buffer.Num() >= Size)
|
|
{
|
|
FPlatformProcess::Sleep(Seconds);
|
|
continue;
|
|
}
|
|
MixerList.ResetAllTracks();
|
|
|
|
MidiSequencer.Process(SampleRate, BlockSize);
|
|
TAtomic<int32> LeftTask = PluginHostList.Instruments.Num();
|
|
|
|
for (FPluginHost* PluginHost : PluginHostList.Instruments)
|
|
{
|
|
ThreadPool->AddQueuedWork(new FInstrumentRenderThread(PluginHost, BlockSize, LeftTask));
|
|
}
|
|
|
|
while (LeftTask.Load() > 0)
|
|
{
|
|
FPlatformProcess::Sleep(Seconds);
|
|
}
|
|
|
|
MixerList.Process(BlockSize);
|
|
|
|
float** Headers = MasterTrack->Buffer.GetHeaders();
|
|
|
|
for (int i = 0; i < 2; ++i)
|
|
Buffer.Push(Headers[i], BlockSize);
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
void FAudioRenderThread::Stop()
|
|
{
|
|
IsRunning.store(false);
|
|
}
|
|
|
|
void FAudioRenderThread::Exit()
|
|
{
|
|
ThreadPool->Destroy();
|
|
delete ThreadPool;
|
|
ThreadPool = nullptr;
|
|
}
|