diff --git a/main/include/window.hpp b/main/include/window.hpp index 1c600c8f4..6c5d6eac9 100644 --- a/main/include/window.hpp +++ b/main/include/window.hpp @@ -29,6 +29,9 @@ namespace hex { void endNativeWindowFrame(); void drawTitleBar(); + void drawTitleBarBorderless(); + void drawTitleBarBorder(); + void frameBegin(); void frame(); void frameEnd(); diff --git a/main/source/window/linux_window.cpp b/main/source/window/linux_window.cpp index b51c61247..ea00c1ea1 100644 --- a/main/source/window/linux_window.cpp +++ b/main/source/window/linux_window.cpp @@ -72,9 +72,6 @@ namespace hex { void Window::endNativeWindowFrame() { } - void Window::drawTitleBar() { - } - } #endif \ No newline at end of file diff --git a/main/source/window/macos_window.cpp b/main/source/window/macos_window.cpp index 63760e98b..36feaa664 100644 --- a/main/source/window/macos_window.cpp +++ b/main/source/window/macos_window.cpp @@ -58,9 +58,6 @@ namespace hex { void Window::endNativeWindowFrame() { } - void Window::drawTitleBar() { - } - } #endif \ No newline at end of file diff --git a/main/source/window/win_window.cpp b/main/source/window/win_window.cpp index 1ed2043c2..70e50eaa1 100644 --- a/main/source/window/win_window.cpp +++ b/main/source/window/win_window.cpp @@ -380,58 +380,6 @@ namespace hex { return; } - void Window::drawTitleBar() { - // In borderless window mode, we draw our own title bar - - if (!ImHexApi::System::isBorderlessWindowModeEnabled()) return; - - auto startX = ImGui::GetCursorPosX(); - - auto buttonSize = ImVec2(g_titleBarHeight * 1.5F, g_titleBarHeight - 1); - - ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); - ImGui::PushStyleColor(ImGuiCol_Button, ImGui::GetColorU32(ImGuiCol_MenuBarBg)); - ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabActive)); - ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabHovered)); - - auto &titleBarButtons = ContentRegistry::Interface::impl::getTitleBarButtons(); - - // Draw custom title bar buttons - ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (4 + titleBarButtons.size())); - for (const auto &[icon, tooltip, callback] : titleBarButtons) { - if (ImGui::TitleBarButton(icon.c_str(), buttonSize)) { - callback(); - } - ImGui::InfoTooltip(LangEntry(tooltip)); - } - - // Draw minimize, restore and maximize buttons - ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * 3); - if (ImGui::TitleBarButton(ICON_VS_CHROME_MINIMIZE, buttonSize)) - glfwIconifyWindow(this->m_window); - if (glfwGetWindowAttrib(this->m_window, GLFW_MAXIMIZED)) { - if (ImGui::TitleBarButton(ICON_VS_CHROME_RESTORE, buttonSize)) - glfwRestoreWindow(this->m_window); - } else { - if (ImGui::TitleBarButton(ICON_VS_CHROME_MAXIMIZE, buttonSize)) - glfwMaximizeWindow(this->m_window); - } - - ImGui::PushStyleColor(ImGuiCol_ButtonActive, 0xFF7A70F1); - ImGui::PushStyleColor(ImGuiCol_ButtonHovered, 0xFF2311E8); - - // Draw close button - if (ImGui::TitleBarButton(ICON_VS_CHROME_CLOSE, buttonSize)) { - ImHexApi::System::closeImHex(); - } - - ImGui::PopStyleColor(5); - ImGui::PopStyleVar(); - - ImGui::SetCursorPosX(std::max(startX, (ImGui::GetWindowWidth() - ImGui::CalcTextSize(this->m_windowTitle.c_str()).x) / 2)); - ImGui::TextUnformatted(this->m_windowTitle.c_str()); - } - } #endif \ No newline at end of file diff --git a/main/source/window/window.cpp b/main/source/window/window.cpp index 6b68fd980..a14aa7d49 100644 --- a/main/source/window/window.cpp +++ b/main/source/window/window.cpp @@ -340,6 +340,88 @@ namespace hex { } } + void Window::drawTitleBarBorderless() { + auto startX = ImGui::GetCursorPosX(); + auto titleBarHeight = ImGui::GetCurrentWindow()->MenuBarHeight(); + auto buttonSize = ImVec2(titleBarHeight * 1.5F, titleBarHeight - 1); + + ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); + ImGui::PushStyleColor(ImGuiCol_Button, ImGui::GetColorU32(ImGuiCol_MenuBarBg)); + ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabActive)); + ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabHovered)); + + // custom titlebar buttons implementation for borderless window mode + auto &titleBarButtons = ContentRegistry::Interface::impl::getTitleBarButtons(); + + // Draw custom title bar buttons + ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (4 + titleBarButtons.size())); + for (const auto &[icon, tooltip, callback] : titleBarButtons) { + if (ImGui::TitleBarButton(icon.c_str(), buttonSize)) { + callback(); + } + ImGui::InfoTooltip(LangEntry(tooltip)); + } + + // Draw minimize, restore and maximize buttons + ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * 3); + if (ImGui::TitleBarButton(ICON_VS_CHROME_MINIMIZE, buttonSize)) + glfwIconifyWindow(this->m_window); + if (glfwGetWindowAttrib(this->m_window, GLFW_MAXIMIZED)) { + if (ImGui::TitleBarButton(ICON_VS_CHROME_RESTORE, buttonSize)) + glfwRestoreWindow(this->m_window); + } else { + if (ImGui::TitleBarButton(ICON_VS_CHROME_MAXIMIZE, buttonSize)) + glfwMaximizeWindow(this->m_window); + } + + + ImGui::PushStyleColor(ImGuiCol_ButtonActive, 0xFF7A70F1); + ImGui::PushStyleColor(ImGuiCol_ButtonHovered, 0xFF2311E8); + + // Draw close button + if (ImGui::TitleBarButton(ICON_VS_CHROME_CLOSE, buttonSize)) { + ImHexApi::System::closeImHex(); + } + + ImGui::PopStyleColor(5); + ImGui::PopStyleVar(); + + ImGui::SetCursorPosX(std::max(startX, (ImGui::GetWindowWidth() - ImGui::CalcTextSize(this->m_windowTitle.c_str()).x) / 2)); + ImGui::TextUnformatted(this->m_windowTitle.c_str()); + } + + void Window::drawTitleBarBorder() { + auto titleBarHeight = ImGui::GetCurrentWindow()->MenuBarHeight(); + auto buttonSize = ImVec2(titleBarHeight * 1.5F, titleBarHeight - 1); + + ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(0, 0)); + ImGui::PushStyleColor(ImGuiCol_Button, ImGui::GetColorU32(ImGuiCol_MenuBarBg)); + ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabActive)); + ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImGui::GetColorU32(ImGuiCol_ScrollbarGrabHovered)); + + auto &titleBarButtons = ContentRegistry::Interface::impl::getTitleBarButtons(); + + // Draw custom title bar buttons + ImGui::SetCursorPosX(ImGui::GetWindowWidth() - buttonSize.x * (titleBarButtons.size()+0.5)); + for (const auto &[icon, tooltip, callback] : titleBarButtons) { + if (ImGui::TitleBarButton(icon.c_str(), buttonSize)) { + callback(); + } + ImGui::InfoTooltip(LangEntry(tooltip)); + } + + ImGui::PopStyleColor(3); + ImGui::PopStyleVar(); + } + + void Window::drawTitleBar() { + if (ImHexApi::System::isBorderlessWindowModeEnabled()) { + drawTitleBarBorderless(); + } else { + drawTitleBarBorder(); + } + } + void Window::frameBegin() { // Start new ImGui Frame ImGui_ImplOpenGL3_NewFrame(); diff --git a/plugins/builtin/source/content/ui_items.cpp b/plugins/builtin/source/content/ui_items.cpp index e2d33e981..59b4c12ca 100644 --- a/plugins/builtin/source/content/ui_items.cpp +++ b/plugins/builtin/source/content/ui_items.cpp @@ -17,6 +17,31 @@ namespace hex::plugin::builtin { + void addTitleBarButtons() { +#if defined(DEBUG) + ContentRegistry::Interface::addTitleBarButton(ICON_VS_DEBUG, "hex.windows.title_bar_button.debug_build", []{ + if (ImGui::GetIO().KeyCtrl) { + // Explicitly trigger a segfault by writing to an invalid memory location + // Used for debugging crashes + *reinterpret_cast(0x10) = 0x10; + std::unreachable(); + } else if (ImGui::GetIO().KeyShift) { + // Explicitly trigger an abort by throwing an uncaught exception + // Used for debugging exception errors + throw std::runtime_error("Debug Error"); + std::unreachable(); + } else { + hex::openWebpage("https://imhex.werwolv.net/debug"); + } + }); +#endif + + ContentRegistry::Interface::addTitleBarButton(ICON_VS_SMILEY, "hex.windows.title_bar_button.feedback", []{ + hex::openWebpage("https://github.com/WerWolv/ImHex/discussions/categories/feedback"); + }); + + } + static void drawGlobalPopups() { // Task exception popup for (const auto &task : TaskManager::getRunningTasks()) { diff --git a/plugins/builtin/source/plugin_builtin.cpp b/plugins/builtin/source/plugin_builtin.cpp index a8c6acec1..d14119eb7 100644 --- a/plugins/builtin/source/plugin_builtin.cpp +++ b/plugins/builtin/source/plugin_builtin.cpp @@ -32,6 +32,7 @@ namespace hex::plugin::builtin { void registerNetworkEndpoints(); void addFooterItems(); + void addTitleBarButtons(); void addToolbarItems(); void addGlobalUIItems(); @@ -70,6 +71,7 @@ IMHEX_PLUGIN_SETUP("Built-in", "WerWolv", "Default ImHex functionality") { registerNetworkEndpoints(); addFooterItems(); + addTitleBarButtons(); addToolbarItems(); addGlobalUIItems(); diff --git a/plugins/windows/source/content/ui_items.cpp b/plugins/windows/source/content/ui_items.cpp index a821682e4..7117dcd2f 100644 --- a/plugins/windows/source/content/ui_items.cpp +++ b/plugins/windows/source/content/ui_items.cpp @@ -13,31 +13,6 @@ namespace hex::plugin::windows { - void addTitleBarButtons() { -#if defined(DEBUG) - ContentRegistry::Interface::addTitleBarButton(ICON_VS_DEBUG, "hex.windows.title_bar_button.debug_build", []{ - if (ImGui::GetIO().KeyCtrl) { - // Explicitly trigger a segfault by writing to an invalid memory location - // Used for debugging crashes - *reinterpret_cast(0x10) = 0x10; - std::unreachable(); - } else if (ImGui::GetIO().KeyShift) { - // Explicitly trigger an abort by throwing an uncaught exception - // Used for debugging exception errors - throw std::runtime_error("Debug Error"); - std::unreachable(); - } else { - hex::openWebpage("https://imhex.werwolv.net/debug"); - } - }); -#endif - - ContentRegistry::Interface::addTitleBarButton(ICON_VS_SMILEY, "hex.windows.title_bar_button.feedback", []{ - hex::openWebpage("https://github.com/WerWolv/ImHex/discussions/categories/feedback"); - }); - - } - void addFooterItems() { ContentRegistry::Interface::addFooterItem([] { diff --git a/plugins/windows/source/plugin_windows.cpp b/plugins/windows/source/plugin_windows.cpp index 84725a4a0..44c108859 100644 --- a/plugins/windows/source/plugin_windows.cpp +++ b/plugins/windows/source/plugin_windows.cpp @@ -67,7 +67,6 @@ IMHEX_PLUGIN_SETUP("Windows", "WerWolv", "Windows-only features") { hex::ContentRegistry::Views::add(); addFooterItems(); - addTitleBarButtons(); registerSettings(); registerProviders();