#include "window_manager.h" #include "audio/plugin_host/plugin_host.h" #include "audio/plugin_host/plugin_host_manager.h" #include "GLFW/glfw3.h" #include "GLFW/glfw3native.h" void window_manager::init(singleton_initliazer& initliazer) { singleton_t::init(initliazer); auto plugin_host = initliazer.require(); plugin_host->on_instrument_removed.add_raw(this, &window_manager::destroy_plugin_window); if (!glfwInit()) return; glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); } void window_manager::release(singleton_release_guard& release_guard) { singleton_t::release(release_guard); release_guard.require_release(); windows_.clear(); host_infos_.clear(); glfwTerminate(); } std::shared_ptr window_manager::create_window(int width, int height, const char* title) { auto* window = glfwCreateWindow(width, height, title, nullptr, nullptr); std::shared_ptr w = std::shared_ptr(window, [](GLFWwindow* w) { glfwDestroyWindow(w); }); windows_.push_back(w); return w; } void* window_manager::create_plugin_window(plugin_host* host) { uint32_t width, height; host->get_editor_size(width, height); if (width == 0 || height == 0) return nullptr; auto w = create_window(width, height, host->name.c_str()); host_info info; host_info& window_info = host_infos_[host]; window_info.window = w; glfwSetWindowCloseCallback(w.get(), [](GLFWwindow* window) { get_window_manager()->on_host_window_close(window); }); #if PLATFORM_WINDOWS HWND hwnd = glfwGetWin32Window(w.get()); return hwnd; #elif PLATFORM_LINUX return glfwGetX11Window(w.get()); #elif PLATFORM_MACOS return glfwGetCocoaWindow(w.get()); #endif return nullptr; } void window_manager::destroy_plugin_window(plugin_host* host) { const auto& find = host_infos_.find(host); if (find == host_infos_.end()) { return; } auto window = find->second.window; if (!window) return; auto f = std::ranges::find_if(windows_, [window](const std::weak_ptr& w) { return w.lock() == window; }); windows_.erase(f); on_host_window_close(window.get()); } void window_manager::update() { glfwPollEvents(); for (auto& info : host_infos_) { if (!info.second.window) { continue; } info.first->idle_editor(); } } void window_manager::on_host_window_close(GLFWwindow* window) { auto f = std::ranges::find_if(host_infos_, [window](const std::pair& info) { return info.second.window.get() == window; }); if (f != host_infos_.end()) { f->first->close_editor(); int x, y; glfwGetWindowPos(window, &x, &y); f->second.x = x; f->second.y = y; f->second.window.reset(); } }