fix: Menu bar focus issues

This commit is contained in:
WerWolv
2026-03-03 13:45:54 +01:00
parent 04a8bd6798
commit 380b1dbce3
4 changed files with 50 additions and 41 deletions

View File

@@ -145,7 +145,6 @@ namespace hex {
* @brief A view that draws a regular window. This should be the default for most views * @brief A view that draws a regular window. This should be the default for most views
*/ */
class View::Window : public View { class View::Window : public View {
ImGuiWindow *m_focusedSubWindow;
public: public:
explicit Window(UnlocalizedString unlocalizedName, const char *icon) : View(std::move(unlocalizedName), icon), m_focusedSubWindow(nullptr) {} explicit Window(UnlocalizedString unlocalizedName, const char *icon) : View(std::move(unlocalizedName), icon), m_focusedSubWindow(nullptr) {}
@@ -159,6 +158,12 @@ namespace hex {
virtual bool allowScroll() const { virtual bool allowScroll() const {
return false; return false;
} }
private:
void handleFocusRestoration();
private:
ImGuiWindow *m_focusedSubWindow;
}; };
/** /**

View File

@@ -10,6 +10,7 @@
#include <imgui.h> #include <imgui.h>
#include <string> #include <string>
#include <GLFW/glfw3.h>
namespace hex { namespace hex {
@@ -117,44 +118,43 @@ namespace hex {
return s_lastFocusedView; return s_lastFocusedView;
} }
void View::Window::handleFocusRestoration() {
const auto title = fmt::format("{} {}", this->getIcon(), View::toWindowName(this->getUnlocalizedName()));
void View::Window::draw(ImGuiWindowFlags extraFlags) { const ImGuiContext& g = *ImGui::GetCurrentContext();
if (this->shouldDraw()) { bool foundTopFocused = false;
const auto title = fmt::format("{} {}", this->getIcon(), View::toWindowName(this->getUnlocalizedName())); ImGuiWindow *imguiFocusedWindow = nullptr;
ImGuiWindow *focusedSubWindow = nullptr;
const ImGuiContext& g = *ImGui::GetCurrentContext(); if (g.NavWindow != nullptr) {
bool foundTopFocused = false; imguiFocusedWindow = g.NavWindow;
ImGuiWindow *imguiFocusedWindow = nullptr; foundTopFocused = true;
ImGuiWindow *focusedSubWindow = nullptr; }
for (auto focusedWindow: g.WindowsFocusOrder | std::views::reverse) {
if (g.NavWindow != nullptr) { if (focusedWindow == nullptr || !focusedWindow->WasActive)
imguiFocusedWindow = g.NavWindow; continue;
std::string focusedWindowName = focusedWindow->Name;
if (!foundTopFocused) {
imguiFocusedWindow = focusedWindow;
foundTopFocused = true; foundTopFocused = true;
} }
for (auto focusedWindow: g.WindowsFocusOrder | std::views::reverse) { if (imguiFocusedWindow == nullptr || !focusedWindowName.contains("###hex.builtin.view."))
if (focusedWindow == nullptr || !focusedWindow->WasActive) continue;
continue; if (auto focusedChild = focusedWindow->NavLastChildNavWindow; focusedChild != nullptr)
std::string focusedWindowName = focusedWindow->Name; focusedSubWindow = focusedChild;
if (!foundTopFocused) { else if (focusedWindow == focusedWindow->RootWindow)
imguiFocusedWindow = focusedWindow; focusedSubWindow = focusedWindow;
foundTopFocused = true;
}
if (imguiFocusedWindow == nullptr || !focusedWindowName.contains("###hex.builtin.view."))
continue;
if (auto focusedChild = focusedWindow->NavLastChildNavWindow; focusedChild != nullptr)
focusedSubWindow = focusedChild;
else if (focusedWindow == focusedWindow->RootWindow)
focusedSubWindow = focusedWindow;
break; break;
} }
std::string imguiFocusedWindowName = "NULL"; std::string imguiFocusedWindowName = "NULL";
if (imguiFocusedWindow != nullptr) if (imguiFocusedWindow != nullptr)
imguiFocusedWindowName.assign(imguiFocusedWindow->Name); imguiFocusedWindowName.assign(imguiFocusedWindow->Name);
std::string focusedSubWindowName; std::string focusedSubWindowName;
if (focusedSubWindow != nullptr || m_focusedSubWindow != nullptr) { if (focusedSubWindow != nullptr || m_focusedSubWindow != nullptr) {
if (glfwGetWindowAttrib(ImHexApi::System::getMainWindowHandle(), GLFW_FOCUSED)) {
focusedSubWindowName = focusedSubWindow != nullptr ? focusedSubWindow->Name : m_focusedSubWindow->Name; focusedSubWindowName = focusedSubWindow != nullptr ? focusedSubWindow->Name : m_focusedSubWindow->Name;
if (focusedSubWindow != nullptr && m_focusedSubWindow != nullptr) { if (focusedSubWindow != nullptr && m_focusedSubWindow != nullptr) {
std::string_view windowName = m_focusedSubWindow->Name; std::string_view windowName = m_focusedSubWindow->Name;
@@ -182,6 +182,15 @@ namespace hex {
} }
} }
} }
}
}
void View::Window::draw(ImGuiWindowFlags extraFlags) {
if (this->shouldDraw()) {
const auto title = fmt::format("{} {}", this->getIcon(), View::toWindowName(this->getUnlocalizedName()));
handleFocusRestoration();
if (!allowScroll()) if (!allowScroll())
extraFlags |= ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse; extraFlags |= ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse;
@@ -239,4 +248,4 @@ namespace hex {
} }
} }

View File

@@ -420,7 +420,7 @@ namespace hex {
ImGui::PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0F); ImGui::PushStyleVar(ImGuiStyleVar_WindowBorderSize, 0.0F);
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0)); ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0));
ImGuiWindowFlags windowFlags = ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoNavFocus | ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse; ImGuiWindowFlags windowFlags = ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse;
if (!m_emergencyPopupOpen) if (!m_emergencyPopupOpen)
windowFlags |= ImGuiWindowFlags_MenuBar; windowFlags |= ImGuiWindowFlags_MenuBar;

View File

@@ -495,15 +495,10 @@ namespace hex::plugin::builtin {
ON_SCOPE_EXIT { ImGui::PopStyleVar(); }; ON_SCOPE_EXIT { ImGui::PopStyleVar(); };
#endif #endif
if (ImGui::BeginMainMenuBar()) {
drawTitleBarBackDrop();
ImGui::Dummy({});
ImGui::EndMainMenuBar();
}
auto window = ImHexApi::System::getMainWindowHandle(); auto window = ImHexApi::System::getMainWindowHandle();
menu::enableNativeMenuBar(s_useNativeMenuBar); menu::enableNativeMenuBar(s_useNativeMenuBar);
if (menu::beginMainMenuBar()) { if (menu::beginMainMenuBar()) {
drawTitleBarBackDrop();
if (ImHexApi::System::isBorderlessWindowModeEnabled()) { if (ImHexApi::System::isBorderlessWindowModeEnabled()) {
#if defined(OS_WINDOWS) #if defined(OS_WINDOWS)
ImGui::SetCursorPosX(5_scaled); ImGui::SetCursorPosX(5_scaled);
@@ -637,7 +632,7 @@ namespace hex::plugin::builtin {
s_logoTexture = ImGuiExt::Texture::fromImage(romfs::get("assets/common/icon.png").span(), ImGuiExt::Texture::Filter::Linear); s_logoTexture = ImGuiExt::Texture::fromImage(romfs::get("assets/common/icon.png").span(), ImGuiExt::Texture::Filter::Linear);
}; };
constexpr static ImGuiWindowFlags windowFlags = ImGuiWindowFlags_MenuBar | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoNavFocus | ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse; constexpr static ImGuiWindowFlags windowFlags = ImGuiWindowFlags_MenuBar | ImGuiWindowFlags_NoDocking | ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoBringToFrontOnFocus | ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse;
ImGuiViewport *viewport = ImGui::GetMainViewport(); ImGuiViewport *viewport = ImGui::GetMainViewport();
ImGui::SetNextWindowPos(viewport->WorkPos); ImGui::SetNextWindowPos(viewport->WorkPos);