mirror of
https://github.com/Drezil/imgui.git
synced 2024-12-23 16:16:36 +00:00
Docking: Another attempt at tidying the inconsistent focus / tab bar reordering issues, and toward generalizing single window dock nodes. (#2109)
This commit is contained in:
parent
2da200fc16
commit
8bac6d428d
33
imgui.cpp
33
imgui.cpp
@ -10337,7 +10337,7 @@ void ImGui::DockContextProcessDock(ImGuiContext* ctx, ImGuiDockRequest* req)
|
|||||||
|
|
||||||
// Update selection immediately
|
// Update selection immediately
|
||||||
if (ImGuiTabBar* tab_bar = target_node->TabBar)
|
if (ImGuiTabBar* tab_bar = target_node->TabBar)
|
||||||
tab_bar->NextSelectedTabId = tab_bar->WantFocusTabId = next_selected_id;
|
tab_bar->NextSelectedTabId = next_selected_id;
|
||||||
MarkIniSettingsDirty();
|
MarkIniSettingsDirty();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -10461,6 +10461,10 @@ static void ImGui::DockNodeAddWindow(ImGuiDockNode* node, ImGuiWindow* window, b
|
|||||||
{
|
{
|
||||||
node->TabBar = IM_NEW(ImGuiTabBar)();
|
node->TabBar = IM_NEW(ImGuiTabBar)();
|
||||||
node->TabBar->SelectedTabId = node->TabBar->NextSelectedTabId = node->SelectedTabID;
|
node->TabBar->SelectedTabId = node->TabBar->NextSelectedTabId = node->SelectedTabID;
|
||||||
|
|
||||||
|
// Add existing windows
|
||||||
|
for (int n = 0; n < node->Windows.Size - 1; n++)
|
||||||
|
TabBarAddTab(node->TabBar, node->Windows[n], ImGuiTabItemFlags_None);
|
||||||
}
|
}
|
||||||
TabBarAddTab(node->TabBar, window, ImGuiTabItemFlags_Unsorted);
|
TabBarAddTab(node->TabBar, window, ImGuiTabItemFlags_Unsorted);
|
||||||
}
|
}
|
||||||
@ -10835,7 +10839,7 @@ static void ImGui::DockNodeUpdate(ImGuiDockNode* node)
|
|||||||
char window_label[20];
|
char window_label[20];
|
||||||
DockNodeGetHostWindowTitle(node, window_label, IM_ARRAYSIZE(window_label));
|
DockNodeGetHostWindowTitle(node, window_label, IM_ARRAYSIZE(window_label));
|
||||||
ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_DockNodeHost;
|
ImGuiWindowFlags window_flags = ImGuiWindowFlags_NoScrollbar | ImGuiWindowFlags_NoScrollWithMouse | ImGuiWindowFlags_DockNodeHost;
|
||||||
//window_flags |= ImGuiWindowFlags_NoFocusOnAppearing;
|
window_flags |= ImGuiWindowFlags_NoFocusOnAppearing;
|
||||||
window_flags |= ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoNavFocus;
|
window_flags |= ImGuiWindowFlags_NoSavedSettings | ImGuiWindowFlags_NoNavFocus;
|
||||||
window_flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse;
|
window_flags |= ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoCollapse;
|
||||||
|
|
||||||
@ -11018,6 +11022,8 @@ static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_w
|
|||||||
if (tab_bar == NULL)
|
if (tab_bar == NULL)
|
||||||
tab_bar = node->TabBar = IM_NEW(ImGuiTabBar)();
|
tab_bar = node->TabBar = IM_NEW(ImGuiTabBar)();
|
||||||
|
|
||||||
|
ImGuiID focus_tab_id = 0;
|
||||||
|
|
||||||
// Collapse button changes shape and display a list
|
// Collapse button changes shape and display a list
|
||||||
if (IsPopupOpen("#TabListMenu"))
|
if (IsPopupOpen("#TabListMenu"))
|
||||||
{
|
{
|
||||||
@ -11037,7 +11043,7 @@ static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_w
|
|||||||
ImGuiTabItem* tab = &tab_bar->Tabs[tab_n];
|
ImGuiTabItem* tab = &tab_bar->Tabs[tab_n];
|
||||||
IM_ASSERT(tab->Window != NULL);
|
IM_ASSERT(tab->Window != NULL);
|
||||||
if (Selectable(tab->Window->Name, tab->ID == tab_bar->SelectedTabId))
|
if (Selectable(tab->Window->Name, tab->ID == tab_bar->SelectedTabId))
|
||||||
tab_bar->NextSelectedTabId = tab_bar->WantFocusTabId = tab->ID;
|
focus_tab_id = tab_bar->NextSelectedTabId = tab->ID;
|
||||||
SameLine();
|
SameLine();
|
||||||
Text(" ");
|
Text(" ");
|
||||||
}
|
}
|
||||||
@ -11046,8 +11052,6 @@ static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_w
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ImGuiID focus_tab_id = 0;
|
|
||||||
|
|
||||||
// Title bar
|
// Title bar
|
||||||
node->IsFocused = is_focused;
|
node->IsFocused = is_focused;
|
||||||
if (is_focused)
|
if (is_focused)
|
||||||
@ -11063,11 +11067,16 @@ static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_w
|
|||||||
if (IsItemActive())
|
if (IsItemActive())
|
||||||
focus_tab_id = tab_bar->SelectedTabId;
|
focus_tab_id = tab_bar->SelectedTabId;
|
||||||
|
|
||||||
// Submit new tabs
|
// Submit new tabs and apply NavWindow focus back to the tab bar. They will be added as Unsorted and sorted below based on relative DockOrder value.
|
||||||
const int tabs_count_old = tab_bar->Tabs.Size;
|
const int tabs_count_old = tab_bar->Tabs.Size;
|
||||||
for (int window_n = 0; window_n < node->Windows.Size; window_n++)
|
for (int window_n = 0; window_n < node->Windows.Size; window_n++)
|
||||||
if (TabBarFindTabByID(tab_bar, node->Windows[window_n]->ID) == NULL)
|
{
|
||||||
TabBarAddTab(tab_bar, node->Windows[window_n], ImGuiTabItemFlags_Unsorted);
|
ImGuiWindow* window = node->Windows[window_n];
|
||||||
|
if (g.NavWindow && g.NavWindow->RootWindowDockStop == window)
|
||||||
|
tab_bar->SelectedTabId = window->ID;
|
||||||
|
if (TabBarFindTabByID(tab_bar, window->ID) == NULL)
|
||||||
|
TabBarAddTab(tab_bar, window, ImGuiTabItemFlags_Unsorted);
|
||||||
|
}
|
||||||
|
|
||||||
// If multiple tabs are appearing on the same frame, sort them based on their persistent DockOrder value
|
// If multiple tabs are appearing on the same frame, sort them based on their persistent DockOrder value
|
||||||
int tabs_unsorted_start = tab_bar->Tabs.Size;
|
int tabs_unsorted_start = tab_bar->Tabs.Size;
|
||||||
@ -11170,13 +11179,13 @@ static void ImGui::DockNodeUpdateTabBar(ImGuiDockNode* node, ImGuiWindow* host_w
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Forward focus from host node to selected window
|
// Forward focus from host node to selected window
|
||||||
if (is_focused && g.NavWindow == host_window && !g.NavWindowingTarget)
|
//if (is_focused && g.NavWindow == host_window && !g.NavWindowingTarget)
|
||||||
focus_tab_id = tab_bar->SelectedTabId;
|
// focus_tab_id = tab_bar->SelectedTabId;
|
||||||
|
|
||||||
// When clicked on a tab we requested focus to the docked child
|
// When clicked on a tab we requested focus to the docked child
|
||||||
// This overrides the value set by "forward focus from host node to selected window".
|
// This overrides the value set by "forward focus from host node to selected window".
|
||||||
if (tab_bar->WantFocusTabId)
|
if (tab_bar->NextSelectedTabId)
|
||||||
focus_tab_id = tab_bar->WantFocusTabId;
|
focus_tab_id = tab_bar->NextSelectedTabId;
|
||||||
|
|
||||||
// Apply navigation focus
|
// Apply navigation focus
|
||||||
if (focus_tab_id != 0)
|
if (focus_tab_id != 0)
|
||||||
|
@ -1355,7 +1355,6 @@ struct ImGuiTabBar
|
|||||||
ImGuiID SelectedTabId; // Selected tab
|
ImGuiID SelectedTabId; // Selected tab
|
||||||
ImGuiID NextSelectedTabId;
|
ImGuiID NextSelectedTabId;
|
||||||
ImGuiID VisibleTabId; // Can occasionally be != SelectedTabId (e.g. when previewing contents for CTRL+TAB preview)
|
ImGuiID VisibleTabId; // Can occasionally be != SelectedTabId (e.g. when previewing contents for CTRL+TAB preview)
|
||||||
ImGuiID WantFocusTabId; // Request focus for the window associated to this tab. Used and only honored by DockNode (meaningless for standalone tab bars)
|
|
||||||
int CurrFrameVisible;
|
int CurrFrameVisible;
|
||||||
int PrevFrameVisible;
|
int PrevFrameVisible;
|
||||||
ImRect BarRect;
|
ImRect BarRect;
|
||||||
|
@ -5813,7 +5813,7 @@ namespace ImGui
|
|||||||
ImGuiTabBar::ImGuiTabBar()
|
ImGuiTabBar::ImGuiTabBar()
|
||||||
{
|
{
|
||||||
ID = 0;
|
ID = 0;
|
||||||
SelectedTabId = NextSelectedTabId = VisibleTabId = WantFocusTabId = 0;
|
SelectedTabId = NextSelectedTabId = VisibleTabId = 0;
|
||||||
CurrFrameVisible = PrevFrameVisible = -1;
|
CurrFrameVisible = PrevFrameVisible = -1;
|
||||||
OffsetMax = OffsetNextTab = 0.0f;
|
OffsetMax = OffsetNextTab = 0.0f;
|
||||||
ScrollingAnim = ScrollingTarget = 0.0f;
|
ScrollingAnim = ScrollingTarget = 0.0f;
|
||||||
@ -5960,7 +5960,6 @@ static void ImGui::TabBarLayout(ImGuiTabBar* tab_bar)
|
|||||||
|
|
||||||
// Setup next selected tab
|
// Setup next selected tab
|
||||||
ImGuiID scroll_track_selected_tab_id = 0;
|
ImGuiID scroll_track_selected_tab_id = 0;
|
||||||
tab_bar->WantFocusTabId = 0;
|
|
||||||
if (tab_bar->NextSelectedTabId)
|
if (tab_bar->NextSelectedTabId)
|
||||||
{
|
{
|
||||||
tab_bar->SelectedTabId = tab_bar->NextSelectedTabId;
|
tab_bar->SelectedTabId = tab_bar->NextSelectedTabId;
|
||||||
@ -6157,7 +6156,6 @@ void ImGui::TabBarRemoveTab(ImGuiTabBar* tab_bar, ImGuiID tab_id)
|
|||||||
if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_id))
|
if (ImGuiTabItem* tab = TabBarFindTabByID(tab_bar, tab_id))
|
||||||
tab_bar->Tabs.erase(tab);
|
tab_bar->Tabs.erase(tab);
|
||||||
if (tab_bar->VisibleTabId == tab_id) { tab_bar->VisibleTabId = 0; }
|
if (tab_bar->VisibleTabId == tab_id) { tab_bar->VisibleTabId = 0; }
|
||||||
if (tab_bar->WantFocusTabId == tab_id) { tab_bar->WantFocusTabId = 0; }
|
|
||||||
if (tab_bar->SelectedTabId == tab_id) { tab_bar->SelectedTabId = 0; }
|
if (tab_bar->SelectedTabId == tab_id) { tab_bar->SelectedTabId = 0; }
|
||||||
if (tab_bar->NextSelectedTabId == tab_id) { tab_bar->NextSelectedTabId = 0; }
|
if (tab_bar->NextSelectedTabId == tab_id) { tab_bar->NextSelectedTabId = 0; }
|
||||||
}
|
}
|
||||||
@ -6447,8 +6445,8 @@ bool ImGui::TabItemEx(ImGuiTabBar* tab_bar, const char* label, bool* p_open,
|
|||||||
bool hovered, held;
|
bool hovered, held;
|
||||||
bool pressed = ButtonBehavior(bb, id, &hovered, &held, button_flags);
|
bool pressed = ButtonBehavior(bb, id, &hovered, &held, button_flags);
|
||||||
hovered |= (g.HoveredId == id);
|
hovered |= (g.HoveredId == id);
|
||||||
if (pressed || ((flags & ImGuiTabItemFlags_SetSelected) && !tab_contents_visible)) // SetSelected can only be passed on explicit tab bar, so we don't need to set WantFocusTabId
|
if (pressed || ((flags & ImGuiTabItemFlags_SetSelected) && !tab_contents_visible)) // SetSelected can only be passed on explicit tab bar
|
||||||
tab_bar->NextSelectedTabId = tab_bar->WantFocusTabId = id;
|
tab_bar->NextSelectedTabId = id;
|
||||||
|
|
||||||
// Allow the close button to overlap unless we are dragging (in which case we don't want any overlapping tabs to be hovered)
|
// Allow the close button to overlap unless we are dragging (in which case we don't want any overlapping tabs to be hovered)
|
||||||
if (!held)
|
if (!held)
|
||||||
@ -6531,7 +6529,7 @@ bool ImGui::TabItemEx(ImGuiTabBar* tab_bar, const char* label, bool* p_open,
|
|||||||
// Select with right mouse button. This is so the common idiom for context menu automatically highlight the current widget.
|
// Select with right mouse button. This is so the common idiom for context menu automatically highlight the current widget.
|
||||||
const bool hovered_unblocked = IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup);
|
const bool hovered_unblocked = IsItemHovered(ImGuiHoveredFlags_AllowWhenBlockedByPopup);
|
||||||
if (hovered_unblocked && (IsMouseClicked(1) || IsMouseReleased(1)))
|
if (hovered_unblocked && (IsMouseClicked(1) || IsMouseReleased(1)))
|
||||||
tab_bar->NextSelectedTabId = tab_bar->WantFocusTabId = id;
|
tab_bar->NextSelectedTabId = id;
|
||||||
|
|
||||||
if (tab_bar->Flags & ImGuiTabBarFlags_NoCloseWithMiddleMouseButton)
|
if (tab_bar->Flags & ImGuiTabBarFlags_NoCloseWithMiddleMouseButton)
|
||||||
flags |= ImGuiTabItemFlags_NoCloseWithMiddleMouseButton;
|
flags |= ImGuiTabItemFlags_NoCloseWithMiddleMouseButton;
|
||||||
|
Loading…
Reference in New Issue
Block a user