Nanako e65c44899a 1. 优化内存池
2. 延迟补偿功能完成
3. 优化内存布局
2024-07-12 07:55:12 +08:00

127 lines
3.5 KiB
C++

#include "mixer.h"
#include "channel_interface.h"
#include "channel_node.h"
#include "audio/device/audio_device_manager.h"
#include "audio/misc/audio_buffer_pool.h"
#include "misc/query_timer.h"
#include "thread_message/thread_message_hubs.h"
IMPL_SINGLETON_INSTANCE(mixer)
void mixer::init(singleton_initliazer& initliazer) {
singleton_t<mixer>::init(initliazer);
on_latency_offset_changed.add_raw(this, &mixer::on_mixer_latency_changed);
initliazer.require<audio_buffer_pool>();
initliazer.require<audio_device_manager>(); // 依赖音频设备管理器, 用于获取采样率和缓冲区大小
null_channel_node::init();
zero_track_ = new dummy_track();
zero_track_->rename("zero");
zero_track_->init();
master_ = new dummy_track();
master_->rename("master");
master_->init();
push_track(master_);
}
void mixer::begin_release(singleton_release_guard &release_guard) {
singleton::begin_release(release_guard);
on_latency_offset_changed.remove_object(this);
}
void mixer::release(singleton_release_guard& release_guard) {
singleton_t<mixer>::release(release_guard);
release_guard.require_release<audio_device_manager>();
null_channel_node::destroy();
for (auto track : tracks_) {
delete track;
}
delete zero_track_;
tracks_.clear();
}
dummy_track* mixer::create_dummy_track(const std::string& in_name) {
auto* track = new dummy_track();
track->init();
track->rename(in_name);
g_audio_thread_hub.push_message([track, this]() {
processor_.add_link(track, get_master(), 1.0f);
thread_register_track(track);
});
return track;
}
instrument_track* mixer::create_instrument_track(plugin_host* in_instrument) {
auto* track = new instrument_track(in_instrument);
track->init();
// register track
g_audio_thread_hub.push_message([track, this] {
processor_.add_link(track, get_master(), 1.0f);
thread_register_track(track);
});
return track;
}
void mixer::remove_track(mixer_track* track) {
g_audio_thread_hub.push_message([track, this] {
if (const auto it = std::ranges::find(tracks_, track); it != tracks_.end()) {
tracks_.erase(it);
}
processor_.remove_track(track);
on_remove_track.broadcast(track);
g_main_thread_hub.push_message([track, this]() {
on_remove_track_main_thread.broadcast(track);
if (track == selected_track)
selected_track = nullptr;
delete track;
});
});
}
void mixer::process(uint32_t in_frames, circular_buffer_vector_type& out_buffer) {
processor_.process(in_frames);
processor_.pop_master(in_frames, out_buffer);
}
void mixer::reset() {
if (process_node_dirty_) {
processor_.update_all();
process_node_dirty_ = false;
}
for (const auto track : tracks_) {
track->clear();
}
}
void mixer::request_build_process_node() {
g_audio_thread_hub.push_message([this] {
processor_.update_all();
});
}
void mixer::push_track(mixer_track* track) {
tracks_.push_back(track);
}
void mixer::thread_register_track(mixer_track* track) {
push_track(track);
processor_.update_all();
on_add_track.broadcast(track);
g_main_thread_hub.push_message([track, this] {
on_add_track_main_thread.broadcast(track);
});
}
void mixer::on_mixer_latency_changed() {
g_audio_thread_hub.push_message([this] {
processor_.update_latency();
});
}