#include "creeper-qt/utility/theme/theme.hh" using namespace creeper::theme; using Handler = ThemeManager::Handler; struct ThemeManager::Impl { using Key = const QObject*; std::unordered_map handlers; std::vector begin_callbacks; std::vector final_callbacks; ThemePack theme_pack; ColorMode color_mode; auto apply_theme(const ThemeManager& manager) const { for (auto const& callback : begin_callbacks) callback(manager); for (auto& [_, callback] : handlers) callback(manager); for (auto const& callback : final_callbacks) callback(manager); } auto append_handler(Key key, const Handler& handler) { handlers[key] = handler; QObject::connect(key, &QObject::destroyed, [this, key] { remove_handler(key); }); } void remove_handler(Key key) { handlers.erase(key); } }; ThemeManager::ThemeManager() : pimpl(std::make_unique()) { } ThemeManager::ThemeManager(const ThemePack& pack, ColorMode mode) : pimpl(std::make_unique()) { pimpl->theme_pack = pack; pimpl->color_mode = mode; } ThemeManager::~ThemeManager() = default; void ThemeManager::apply_theme() const { pimpl->apply_theme(*this); } void ThemeManager::append_handler(const QObject* key, const Handler& handler) { pimpl->append_handler(key, handler); } auto ThemeManager::append_begin_callback(const Handler& callback) noexcept -> void { pimpl->begin_callbacks.push_back(callback); } auto ThemeManager::append_final_callback(const Handler& callback) noexcept -> void { pimpl->final_callbacks.push_back(callback); } void ThemeManager::remove_handler(const QObject* key) { pimpl->remove_handler(key); } void ThemeManager::set_theme_pack(const ThemePack& pack) { pimpl->theme_pack = pack; } void ThemeManager::set_color_mode(const ColorMode& mode) { pimpl->color_mode = mode; } void ThemeManager::toggle_color_mode() { pimpl->color_mode = (pimpl->color_mode == ColorMode::LIGHT) // ? ColorMode::DARK : ColorMode::LIGHT; } ThemePack ThemeManager::theme_pack() const { return pimpl->theme_pack; } ColorMode ThemeManager::color_mode() const { return pimpl->color_mode; } ColorScheme ThemeManager::color_scheme() const { return pimpl->theme_pack.color_scheme(pimpl->color_mode); }