158 lines
3.3 KiB
C++
158 lines
3.3 KiB
C++
#include "PluginHostList.h"
|
|
|
|
#include "Paths.h"
|
|
#include "PluginHost/PluginHost.h"
|
|
#include "PortAudioAPI.h"
|
|
#include "PluginHost/Sampler.h"
|
|
#include "PluginHost/VST2PluginHost.h"
|
|
#include "Thread/MainThreadEventList.h"
|
|
#include "AudioBuffer/ChannelNode.h"
|
|
#include "MixerList.h"
|
|
#include "Mixer/MixerTrack.h"
|
|
|
|
DEFINE_LOG_CATEGORY(LogPluginHostList);
|
|
|
|
DECLARE_THREAD_MESSAGE(FPortAudioAPI, RegisterInstrument,
|
|
FPluginHost* Host;
|
|
)
|
|
{
|
|
FPluginHostList::Get().RegisterInstrument_AudioThread(Args.Host);
|
|
}
|
|
|
|
DECLARE_THREAD_MESSAGE(FMainThreadEventList, OnPluginHostRemoved,
|
|
FPluginHost* Host;
|
|
)
|
|
{
|
|
FPluginHostList::Get().OnPluginHostRemoved.Broadcast(Args.Host);
|
|
}
|
|
|
|
DECLARE_THREAD_MESSAGE(FPortAudioAPI, RemovePluginHost,
|
|
FPluginHost* Host;
|
|
)
|
|
{
|
|
FPluginHostList::Get().Instruments.RemoveSingle(Args.Host);
|
|
FPluginHostList::Get().RemoveSingle(Args.Host);
|
|
delete Args.Host;
|
|
|
|
PUSH_THREAD_EVENT(OnPluginHostRemoved, Args.Host);
|
|
FMixerList::Get().BuildProcessNode();
|
|
}
|
|
|
|
DECLARE_THREAD_MESSAGE(FMainThreadEventList, OnInstrumentRegistered,
|
|
FPluginHost* Host;
|
|
)
|
|
{
|
|
FPluginHostList::Get().OnInstrumentHostCreated.Broadcast(Args.Host);
|
|
}
|
|
|
|
void FPluginHostList::Init()
|
|
{
|
|
}
|
|
|
|
void FPluginHostList::Release()
|
|
{
|
|
for (FPluginHost* Element : *this)
|
|
{
|
|
for (FMixerTrack* Track : Element->OwnerTracks)
|
|
{
|
|
Track->Effects.RemoveSingle(Element);
|
|
}
|
|
delete Element;
|
|
}
|
|
Reset();
|
|
}
|
|
|
|
FPluginHost* FPluginHostList::TryLoadPlugin(const FString& Path)
|
|
{
|
|
const FString& Extension = FPaths::GetExtension(Path);
|
|
FPluginHost* Host = nullptr;
|
|
if (Extension == "dll")
|
|
{
|
|
Host = new FVST2PluginHost();
|
|
}
|
|
|
|
if (!Host)
|
|
{
|
|
UE_LOG(LogPluginHostList, Error, TEXT("加载插件失败 %s: 未知的拓展名 %s"), *Path, *Extension);
|
|
return nullptr;
|
|
}
|
|
|
|
if (Host->Load(Path))
|
|
{
|
|
Add(Host);
|
|
}
|
|
else
|
|
{
|
|
delete Host;
|
|
Host = nullptr;
|
|
}
|
|
return Host;
|
|
}
|
|
|
|
FSampler* FPluginHostList::TryLoadSampler(const FString& SampleFilePath)
|
|
{
|
|
FSampler* Sampler = new FSampler();
|
|
|
|
if (Sampler->Load(SampleFilePath))
|
|
{
|
|
Add(Sampler);
|
|
RegisterInstrument(Sampler);
|
|
}
|
|
else
|
|
{
|
|
delete Sampler;
|
|
Sampler = nullptr;
|
|
}
|
|
return Sampler;
|
|
}
|
|
|
|
void FPluginHostList::RegisterInstrument(FPluginHost* Host)
|
|
{
|
|
if (Host)
|
|
PUSH_THREAD_EVENT(RegisterInstrument, Host);
|
|
}
|
|
|
|
void FPluginHostList::RemovePluginHost(FPluginHost* Host)
|
|
{
|
|
if (Host)
|
|
PUSH_THREAD_EVENT(RemovePluginHost, Host);
|
|
}
|
|
|
|
void FPluginHostList::RemoveInstrument(FPluginHost* Host)
|
|
{
|
|
if (!Host)
|
|
return;
|
|
for (FMixerTrack* OwnerTrack : Host->OwnerTracks)
|
|
{
|
|
FMixerList::Get().RemoveTrack(OwnerTrack);
|
|
}
|
|
Host->OwnerTracks.Reset();
|
|
PUSH_THREAD_EVENT(RemovePluginHost, Host);
|
|
}
|
|
|
|
void FPluginHostList::Process(int32 NumSamples)
|
|
{
|
|
for (FPluginHost* Instrument : Instruments)
|
|
{
|
|
Instrument->Process(NumSamples);
|
|
}
|
|
}
|
|
|
|
void FPluginHostList::StopAllMidiOn()
|
|
{
|
|
for (FPluginHost* Instrument : Instruments)
|
|
{
|
|
Instrument->IncomingMidi.addEvent(FMidiMessage::allNotesOff(1));
|
|
}
|
|
}
|
|
|
|
void FPluginHostList::RegisterInstrument_AudioThread(FPluginHost* Host)
|
|
{
|
|
FInstrumentMixerTrack* MixerTrack = FMixerList::Get().CreateInstrumentTrack(Host);
|
|
Host->ChannelInterface->SetInputChannel(MixerTrack->GetChannelInterface()->OutputChannelNodes);
|
|
Host->ChannelInterface->SetOutputChannel(MixerTrack->GetChannelInterface()->OutputChannelNodes);
|
|
Host->OwnerTracks.Add(MixerTrack);
|
|
Instruments.Add(Host);
|
|
PUSH_THREAD_EVENT(OnInstrumentRegistered, Host);
|
|
}
|