Tables: Fixed content size calculation creating feedback loops. Fixed handling of _DefaultSort with _PreferSortXXXflags (@parbo). Comments.

This commit is contained in:
omar 2020-02-06 18:34:37 +01:00 committed by ocornut
parent 787a309445
commit 104ec408a8
3 changed files with 13 additions and 6 deletions

View File

@ -1066,9 +1066,9 @@ enum ImGuiTableColumnFlags_
ImGuiTableColumnFlags_None = 0, ImGuiTableColumnFlags_None = 0,
ImGuiTableColumnFlags_DefaultHide = 1 << 0, // Default as a hidden column. ImGuiTableColumnFlags_DefaultHide = 1 << 0, // Default as a hidden column.
ImGuiTableColumnFlags_DefaultSort = 1 << 1, // Default as a sorting column. ImGuiTableColumnFlags_DefaultSort = 1 << 1, // Default as a sorting column.
ImGuiTableColumnFlags_WidthFixed = 1 << 2, // Column will keep a fixed size, preferable with horizontal scrolling enabled (default if table sizing policy is SizingPolicyFixedX). ImGuiTableColumnFlags_WidthFixed = 1 << 2, // Column will keep a fixed size, preferable with horizontal scrolling enabled (default if table sizing policy is SizingPolicyFixedX and table is resizable).
ImGuiTableColumnFlags_WidthStretch = 1 << 3, // Column will stretch, preferable with horizontal scrolling disabled (default if table sizing policy is SizingPolicyStretchX). ImGuiTableColumnFlags_WidthStretch = 1 << 3, // Column will stretch, preferable with horizontal scrolling disabled (default if table sizing policy is SizingPolicyStretchX).
ImGuiTableColumnFlags_WidthAlwaysAutoResize = 1 << 4, // Column will keep resizing based on submitted contents (with a one frame delay) == Fixed with auto resize ImGuiTableColumnFlags_WidthAlwaysAutoResize = 1 << 4, // Column will keep resizing based on submitted contents (with a one frame delay) == Fixed with auto resize (default if table sizing policy is SizingPolicyFixedX and table is not resizable).
ImGuiTableColumnFlags_NoResize = 1 << 5, // Disable manual resizing. ImGuiTableColumnFlags_NoResize = 1 << 5, // Disable manual resizing.
ImGuiTableColumnFlags_NoClipX = 1 << 6, // Disable clipping for this column (all NoClipX columns will render in a same draw command). ImGuiTableColumnFlags_NoClipX = 1 << 6, // Disable clipping for this column (all NoClipX columns will render in a same draw command).
ImGuiTableColumnFlags_NoSort = 1 << 7, // Disable ability to sort on this field (even if ImGuiTableFlags_Sortable is set on the table). ImGuiTableColumnFlags_NoSort = 1 << 7, // Disable ability to sort on this field (even if ImGuiTableFlags_Sortable is set on the table).

View File

@ -3795,7 +3795,7 @@ static void ShowDemoWindowTables()
case CT_LongText: ImGui::Text("Some longer text %d,%d\nOver two lines..", row, column); break; case CT_LongText: ImGui::Text("Some longer text %d,%d\nOver two lines..", row, column); break;
case CT_Button: ImGui::Button(label); break; case CT_Button: ImGui::Button(label); break;
case CT_StretchButton: ImGui::Button(label, ImVec2(-FLT_MIN, 0.0f)); break; case CT_StretchButton: ImGui::Button(label, ImVec2(-FLT_MIN, 0.0f)); break;
case CT_InputText: ImGui::SetNextItemWidth(-FLT_MIN); ImGui::InputText(label, text_buf, IM_ARRAYSIZE(text_buf)); break; case CT_InputText: ImGui::SetNextItemWidth(-FLT_MIN); ImGui::InputText("##", text_buf, IM_ARRAYSIZE(text_buf)); break;
} }
} }
} }

View File

@ -487,6 +487,7 @@ static ImGuiTableColumnFlags TableFixColumnFlags(ImGuiTable* table, ImGuiTableCo
// Sizing Policy // Sizing Policy
if ((flags & ImGuiTableColumnFlags_WidthMask_) == 0) if ((flags & ImGuiTableColumnFlags_WidthMask_) == 0)
{ {
// FIXME-TABLE: Inconsistent to promote columns to WidthAlwaysAutoResize
if (table->Flags & ImGuiTableFlags_SizingPolicyFixedX) if (table->Flags & ImGuiTableFlags_SizingPolicyFixedX)
flags |= ((table->Flags & ImGuiTableFlags_Resizable) && !(flags & ImGuiTableColumnFlags_NoResize)) ? ImGuiTableColumnFlags_WidthFixed : ImGuiTableColumnFlags_WidthAlwaysAutoResize; flags |= ((table->Flags & ImGuiTableFlags_Resizable) && !(flags & ImGuiTableColumnFlags_NoResize)) ? ImGuiTableColumnFlags_WidthFixed : ImGuiTableColumnFlags_WidthAlwaysAutoResize;
else else
@ -536,7 +537,7 @@ void ImGui::TableUpdateLayout(ImGuiTable* table)
// Compute offset, clip rect for the frame // Compute offset, clip rect for the frame
const ImRect work_rect = table->WorkRect; const ImRect work_rect = table->WorkRect;
const float padding_auto_x = table->CellPaddingX1; // Can't make auto padding larger than what WorkRect knows about so right-alignment matches. const float padding_auto_x = table->CellPaddingX2; // Can't make auto padding larger than what WorkRect knows about so right-alignment matches.
const float min_column_width = TableGetMinColumnWidth(); const float min_column_width = TableGetMinColumnWidth();
int count_fixed = 0; int count_fixed = 0;
@ -595,12 +596,13 @@ void ImGui::TableUpdateLayout(ImGuiTable* table)
} }
// Layout // Layout
// Remove -1.0f to cancel out the +1.0f we are doing in EndTable() to make last column line visible
const float width_spacings = table->CellSpacingX * (table->ColumnsActiveCount - 1); const float width_spacings = table->CellSpacingX * (table->ColumnsActiveCount - 1);
float width_avail; float width_avail;
if ((table->Flags & ImGuiTableFlags_ScrollX) && (table->InnerWidth == 0.0f)) if ((table->Flags & ImGuiTableFlags_ScrollX) && (table->InnerWidth == 0.0f))
width_avail = table->InnerClipRect.GetWidth() - width_spacings - 1.0f; width_avail = table->InnerClipRect.GetWidth() - width_spacings - 1.0f;
else else
width_avail = work_rect.GetWidth() - width_spacings - 1.0f; // Remove -1.0f to cancel out the +1.0f we are doing in EndTable() to make last column line visible width_avail = work_rect.GetWidth() - width_spacings - 1.0f;
const float width_avail_for_stretched_columns = width_avail - width_fixed; const float width_avail_for_stretched_columns = width_avail - width_fixed;
float width_remaining_for_stretched_columns = width_avail_for_stretched_columns; float width_remaining_for_stretched_columns = width_avail_for_stretched_columns;
@ -1406,7 +1408,10 @@ void ImGui::TableSetupColumn(const char* label, ImGuiTableColumnFlags flags,
if (flags & ImGuiTableColumnFlags_DefaultHide) if (flags & ImGuiTableColumnFlags_DefaultHide)
column->IsActive = column->NextIsActive = false; column->IsActive = column->NextIsActive = false;
if (flags & ImGuiTableColumnFlags_DefaultSort) if (flags & ImGuiTableColumnFlags_DefaultSort)
{
column->SortOrder = 0; // Multiple columns using _DefaultSort will be reordered when building the sort specs. column->SortOrder = 0; // Multiple columns using _DefaultSort will be reordered when building the sort specs.
column->SortDirection = (column->Flags & ImGuiTableColumnFlags_PreferSortDescending) ? (ImS8)ImGuiSortDirection_Descending : (ImU8)(ImGuiSortDirection_Ascending);
}
} }
// Store name (append with zero-terminator in contiguous buffer) // Store name (append with zero-terminator in contiguous buffer)
@ -2090,7 +2095,7 @@ void ImGui::TableSortSpecsClickColumn(ImGuiTable* table, ImGuiTableColumn* click
table->IsSortSpecsDirty = true; table->IsSortSpecsDirty = true;
} }
// Return NULL if no sort specs. // Return NULL if no sort specs (most often when ImGuiTableFlags_Sortable is not set)
// You can sort your data again when 'SpecsChanged == true'. It will be true with sorting specs have changed since last call, or the first time. // You can sort your data again when 'SpecsChanged == true'. It will be true with sorting specs have changed since last call, or the first time.
// Lifetime: don't hold on this pointer over multiple frames or past any subsequent call to BeginTable()! // Lifetime: don't hold on this pointer over multiple frames or past any subsequent call to BeginTable()!
const ImGuiTableSortSpecs* ImGui::TableGetSortSpecs() const ImGuiTableSortSpecs* ImGui::TableGetSortSpecs()
@ -2439,10 +2444,12 @@ void ImGui::DebugNodeTable(ImGuiTable* table)
BulletText("Column %d order %d name '%s': +%.1f to +%.1f\n" BulletText("Column %d order %d name '%s': +%.1f to +%.1f\n"
"Active: %d, Clipped: %d, DrawChannels: %d,%d\n" "Active: %d, Clipped: %d, DrawChannels: %d,%d\n"
"WidthGiven/Requested: %.1f/%.1f, Weight: %.2f\n" "WidthGiven/Requested: %.1f/%.1f, Weight: %.2f\n"
"ContentWidth: RowsFrozen %d, RowsUnfrozen %d, HeadersUsed/Desired %d/%d\n"
"UserID: 0x%08X, Flags: 0x%04X: %s%s%s%s..", "UserID: 0x%08X, Flags: 0x%04X: %s%s%s%s..",
n, column->IndexDisplayOrder, name ? name : "NULL", column->MinX - table->WorkRect.Min.x, column->MaxX - table->WorkRect.Min.x, n, column->IndexDisplayOrder, name ? name : "NULL", column->MinX - table->WorkRect.Min.x, column->MaxX - table->WorkRect.Min.x,
column->IsActive, column->IsClipped, column->DrawChannelRowsBeforeFreeze, column->DrawChannelRowsAfterFreeze, column->IsActive, column->IsClipped, column->DrawChannelRowsBeforeFreeze, column->DrawChannelRowsAfterFreeze,
column->WidthGiven, column->WidthRequested, column->ResizeWeight, column->WidthGiven, column->WidthRequested, column->ResizeWeight,
column->ContentWidthRowsFrozen, column->ContentWidthRowsUnfrozen, column->ContentWidthHeadersUsed, column->ContentWidthHeadersDesired,
column->UserID, column->Flags, column->UserID, column->Flags,
(column->Flags & ImGuiTableColumnFlags_WidthFixed) ? "WidthFixed " : "", (column->Flags & ImGuiTableColumnFlags_WidthFixed) ? "WidthFixed " : "",
(column->Flags & ImGuiTableColumnFlags_WidthStretch) ? "WidthStretch " : "", (column->Flags & ImGuiTableColumnFlags_WidthStretch) ? "WidthStretch " : "",