upgrade imgui to 1.91.1, sokol to sept 10 2024
This commit is contained in:
parent
640c8389f3
commit
a3f68316ca
13
source/engine/thirdparty/imgui/imconfig.h
vendored
13
source/engine/thirdparty/imgui/imconfig.h
vendored
|
@ -21,10 +21,11 @@
|
|||
|
||||
//---- Define attributes of all API symbols declarations, e.g. for DLL under Windows
|
||||
// Using Dear ImGui via a shared library is not recommended, because of function call overhead and because we don't guarantee backward nor forward ABI compatibility.
|
||||
// DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions()
|
||||
// for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for more details.
|
||||
//#define IMGUI_API __declspec( dllexport )
|
||||
//#define IMGUI_API __declspec( dllimport )
|
||||
// - Windows DLL users: heaps and globals are not shared across DLL boundaries! You will need to call SetCurrentContext() + SetAllocatorFunctions()
|
||||
// for each static/DLL boundary you are calling from. Read "Context and Memory Allocators" section of imgui.cpp for more details.
|
||||
//#define IMGUI_API __declspec(dllexport) // MSVC Windows: DLL export
|
||||
//#define IMGUI_API __declspec(dllimport) // MSVC Windows: DLL import
|
||||
//#define IMGUI_API __attribute__((visibility("default"))) // GCC/Clang: override visibility when set is hidden
|
||||
|
||||
//---- Don't define obsolete functions/enums/behaviors. Consider enabling from time to time after updating to clean your code of obsolete function/names.
|
||||
//#define IMGUI_DISABLE_OBSOLETE_FUNCTIONS
|
||||
|
@ -42,6 +43,7 @@
|
|||
//#define IMGUI_DISABLE_WIN32_DEFAULT_IME_FUNCTIONS // [Win32] [Default with non-Visual Studio compilers] Don't implement default IME handler (won't require imm32.lib/.a)
|
||||
//#define IMGUI_DISABLE_WIN32_FUNCTIONS // [Win32] Won't use and link with any Win32 function (clipboard, IME).
|
||||
//#define IMGUI_ENABLE_OSX_DEFAULT_CLIPBOARD_FUNCTIONS // [OSX] Implement default OSX clipboard handler (need to link with '-framework ApplicationServices', this is why this is not the default).
|
||||
//#define IMGUI_DISABLE_DEFAULT_SHELL_FUNCTIONS // Don't implement default platform_io.Platform_OpenInShellFn() handler (Win32: ShellExecute(), require shell32.lib/.a, Mac/Linux: use system("")).
|
||||
//#define IMGUI_DISABLE_DEFAULT_FORMAT_FUNCTIONS // Don't implement ImFormatString/ImFormatStringV so you can implement them yourself (e.g. if you don't want to link with vsnprintf)
|
||||
//#define IMGUI_DISABLE_DEFAULT_MATH_FUNCTIONS // Don't implement ImFabs/ImSqrt/ImPow/ImFmod/ImCos/ImSin/ImAcos/ImAtan2 so you can implement them yourself.
|
||||
//#define IMGUI_DISABLE_FILE_FUNCTIONS // Don't implement ImFileOpen/ImFileClose/ImFileRead/ImFileWrite and ImFileHandle at all (replace them with dummies)
|
||||
|
@ -49,6 +51,9 @@
|
|||
//#define IMGUI_DISABLE_DEFAULT_ALLOCATORS // Don't implement default allocators calling malloc()/free() to avoid linking with them. You will need to call ImGui::SetAllocatorFunctions().
|
||||
//#define IMGUI_DISABLE_SSE // Disable use of SSE intrinsics even if available
|
||||
|
||||
//---- Enable Test Engine / Automation features.
|
||||
//#define IMGUI_ENABLE_TEST_ENGINE // Enable imgui_test_engine hooks. Generally set automatically by include "imgui_te_config.h", see Test Engine for details.
|
||||
|
||||
//---- Include imgui_user.h at the end of imgui.h as a convenience
|
||||
// May be convenient for some users to only explicitly include vanilla imgui.h and have extra stuff included.
|
||||
//#define IMGUI_INCLUDE_IMGUI_USER_H
|
||||
|
|
929
source/engine/thirdparty/imgui/imgui.cpp
vendored
929
source/engine/thirdparty/imgui/imgui.cpp
vendored
File diff suppressed because it is too large
Load diff
574
source/engine/thirdparty/imgui/imgui.h
vendored
574
source/engine/thirdparty/imgui/imgui.h
vendored
File diff suppressed because it is too large
Load diff
51
source/engine/thirdparty/imgui/imgui_draw.cpp
vendored
51
source/engine/thirdparty/imgui/imgui_draw.cpp
vendored
|
@ -1,4 +1,4 @@
|
|||
// dear imgui, v1.90.8 WIP
|
||||
// dear imgui, v1.91.1
|
||||
// (drawing and font code)
|
||||
|
||||
/*
|
||||
|
@ -211,11 +211,13 @@ void ImGui::StyleColorsDark(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_ResizeGrip] = ImVec4(0.26f, 0.59f, 0.98f, 0.20f);
|
||||
colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f);
|
||||
colors[ImGuiCol_ResizeGripActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f);
|
||||
colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered];
|
||||
colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f);
|
||||
colors[ImGuiCol_TabSelected] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabSelectedOverline] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TabDimmed] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabDimmedSelected] = ImLerp(colors[ImGuiCol_TabSelected], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_TabDimmedSelectedOverline] = ImVec4(0.50f, 0.50f, 0.50f, 1.00f);
|
||||
colors[ImGuiCol_PlotLines] = ImVec4(0.61f, 0.61f, 0.61f, 1.00f);
|
||||
colors[ImGuiCol_PlotLinesHovered] = ImVec4(1.00f, 0.43f, 0.35f, 1.00f);
|
||||
colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f);
|
||||
|
@ -225,6 +227,7 @@ void ImGui::StyleColorsDark(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_TableBorderLight] = ImVec4(0.23f, 0.23f, 0.25f, 1.00f); // Prefer using Alpha=1.0 here
|
||||
colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f);
|
||||
colors[ImGuiCol_TableRowBgAlt] = ImVec4(1.00f, 1.00f, 1.00f, 0.06f);
|
||||
colors[ImGuiCol_TextLink] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TextSelectedBg] = ImVec4(0.26f, 0.59f, 0.98f, 0.35f);
|
||||
colors[ImGuiCol_DragDropTarget] = ImVec4(1.00f, 1.00f, 0.00f, 0.90f);
|
||||
colors[ImGuiCol_NavHighlight] = ImVec4(0.26f, 0.59f, 0.98f, 1.00f);
|
||||
|
@ -271,11 +274,13 @@ void ImGui::StyleColorsClassic(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_ResizeGrip] = ImVec4(1.00f, 1.00f, 1.00f, 0.10f);
|
||||
colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.78f, 0.82f, 1.00f, 0.60f);
|
||||
colors[ImGuiCol_ResizeGripActive] = ImVec4(0.78f, 0.82f, 1.00f, 0.90f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f);
|
||||
colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered];
|
||||
colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.80f);
|
||||
colors[ImGuiCol_TabSelected] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabSelectedOverline] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TabDimmed] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabDimmedSelected] = ImLerp(colors[ImGuiCol_TabSelected], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_TabDimmedSelectedOverline] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_PlotLines] = ImVec4(1.00f, 1.00f, 1.00f, 1.00f);
|
||||
colors[ImGuiCol_PlotLinesHovered] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f);
|
||||
colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f);
|
||||
|
@ -285,6 +290,7 @@ void ImGui::StyleColorsClassic(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_TableBorderLight] = ImVec4(0.26f, 0.26f, 0.28f, 1.00f); // Prefer using Alpha=1.0 here
|
||||
colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f);
|
||||
colors[ImGuiCol_TableRowBgAlt] = ImVec4(1.00f, 1.00f, 1.00f, 0.07f);
|
||||
colors[ImGuiCol_TextLink] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TextSelectedBg] = ImVec4(0.00f, 0.00f, 1.00f, 0.35f);
|
||||
colors[ImGuiCol_DragDropTarget] = ImVec4(1.00f, 1.00f, 0.00f, 0.90f);
|
||||
colors[ImGuiCol_NavHighlight] = colors[ImGuiCol_HeaderHovered];
|
||||
|
@ -332,11 +338,13 @@ void ImGui::StyleColorsLight(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_ResizeGrip] = ImVec4(0.35f, 0.35f, 0.35f, 0.17f);
|
||||
colors[ImGuiCol_ResizeGripHovered] = ImVec4(0.26f, 0.59f, 0.98f, 0.67f);
|
||||
colors[ImGuiCol_ResizeGripActive] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.90f);
|
||||
colors[ImGuiCol_TabHovered] = colors[ImGuiCol_HeaderHovered];
|
||||
colors[ImGuiCol_TabActive] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabUnfocused] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabUnfocusedActive] = ImLerp(colors[ImGuiCol_TabActive], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_Tab] = ImLerp(colors[ImGuiCol_Header], colors[ImGuiCol_TitleBgActive], 0.90f);
|
||||
colors[ImGuiCol_TabSelected] = ImLerp(colors[ImGuiCol_HeaderActive], colors[ImGuiCol_TitleBgActive], 0.60f);
|
||||
colors[ImGuiCol_TabSelectedOverline] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TabDimmed] = ImLerp(colors[ImGuiCol_Tab], colors[ImGuiCol_TitleBg], 0.80f);
|
||||
colors[ImGuiCol_TabDimmedSelected] = ImLerp(colors[ImGuiCol_TabSelected], colors[ImGuiCol_TitleBg], 0.40f);
|
||||
colors[ImGuiCol_TabDimmedSelectedOverline] = ImVec4(0.26f, 0.59f, 1.00f, 1.00f);
|
||||
colors[ImGuiCol_PlotLines] = ImVec4(0.39f, 0.39f, 0.39f, 1.00f);
|
||||
colors[ImGuiCol_PlotLinesHovered] = ImVec4(1.00f, 0.43f, 0.35f, 1.00f);
|
||||
colors[ImGuiCol_PlotHistogram] = ImVec4(0.90f, 0.70f, 0.00f, 1.00f);
|
||||
|
@ -346,6 +354,7 @@ void ImGui::StyleColorsLight(ImGuiStyle* dst)
|
|||
colors[ImGuiCol_TableBorderLight] = ImVec4(0.68f, 0.68f, 0.74f, 1.00f); // Prefer using Alpha=1.0 here
|
||||
colors[ImGuiCol_TableRowBg] = ImVec4(0.00f, 0.00f, 0.00f, 0.00f);
|
||||
colors[ImGuiCol_TableRowBgAlt] = ImVec4(0.30f, 0.30f, 0.30f, 0.09f);
|
||||
colors[ImGuiCol_TextLink] = colors[ImGuiCol_HeaderActive];
|
||||
colors[ImGuiCol_TextSelectedBg] = ImVec4(0.26f, 0.59f, 0.98f, 0.35f);
|
||||
colors[ImGuiCol_DragDropTarget] = ImVec4(0.26f, 0.59f, 0.98f, 0.95f);
|
||||
colors[ImGuiCol_NavHighlight] = colors[ImGuiCol_HeaderHovered];
|
||||
|
@ -517,7 +526,6 @@ void ImDrawList::_OnChangedClipRect()
|
|||
CmdBuffer.pop_back();
|
||||
return;
|
||||
}
|
||||
|
||||
curr_cmd->ClipRect = _CmdHeader.ClipRect;
|
||||
}
|
||||
|
||||
|
@ -540,7 +548,6 @@ void ImDrawList::_OnChangedTextureID()
|
|||
CmdBuffer.pop_back();
|
||||
return;
|
||||
}
|
||||
|
||||
curr_cmd->TextureId = _CmdHeader.TextureId;
|
||||
}
|
||||
|
||||
|
@ -616,6 +623,15 @@ void ImDrawList::PopTextureID()
|
|||
_OnChangedTextureID();
|
||||
}
|
||||
|
||||
// This is used by ImGui::PushFont()/PopFont(). It works because we never use _TextureIdStack[] elsewhere than in PushTextureID()/PopTextureID().
|
||||
void ImDrawList::_SetTextureID(ImTextureID texture_id)
|
||||
{
|
||||
if (_CmdHeader.TextureId == texture_id)
|
||||
return;
|
||||
_CmdHeader.TextureId = texture_id;
|
||||
_OnChangedTextureID();
|
||||
}
|
||||
|
||||
// Reserve space for a number of vertices and indices.
|
||||
// You must finish filling your reserved data before calling PrimReserve() again, as it may reallocate or
|
||||
// submit the intermediate results. PrimUnreserve() can be used to release unused allocations.
|
||||
|
@ -2806,8 +2822,9 @@ static bool ImFontAtlasBuildWithStbTruetype(ImFontAtlas* atlas)
|
|||
for (const ImWchar* src_range = src_tmp.SrcRanges; src_range[0] && src_range[1]; src_range += 2)
|
||||
{
|
||||
// Check for valid range. This may also help detect *some* dangling pointers, because a common
|
||||
// user error is to setup ImFontConfig::GlyphRanges with a pointer to data that isn't persistent.
|
||||
IM_ASSERT(src_range[0] <= src_range[1]);
|
||||
// user error is to setup ImFontConfig::GlyphRanges with a pointer to data that isn't persistent,
|
||||
// or to forget to zero-terminate the glyph range array.
|
||||
IM_ASSERT(src_range[0] <= src_range[1] && "Invalid range: is your glyph range array persistent? it is zero-terminated?");
|
||||
src_tmp.GlyphsHighest = ImMax(src_tmp.GlyphsHighest, (int)src_range[1]);
|
||||
}
|
||||
dst_tmp.SrcCount++;
|
||||
|
|
378
source/engine/thirdparty/imgui/imgui_internal.h
vendored
378
source/engine/thirdparty/imgui/imgui_internal.h
vendored
|
@ -1,4 +1,4 @@
|
|||
// dear imgui, v1.90.8 WIP
|
||||
// dear imgui, v1.91.1
|
||||
// (internal structures/api)
|
||||
|
||||
// You may use this file to debug, understand or extend Dear ImGui features but we don't provide any guarantee of forward compatibility.
|
||||
|
@ -14,14 +14,15 @@ Index of this file:
|
|||
// [SECTION] Macros
|
||||
// [SECTION] Generic helpers
|
||||
// [SECTION] ImDrawList support
|
||||
// [SECTION] Widgets support: flags, enums, data structures
|
||||
// [SECTION] Data types support
|
||||
// [SECTION] Widgets support: flags, enums, data structures
|
||||
// [SECTION] Popup support
|
||||
// [SECTION] Inputs support
|
||||
// [SECTION] Clipper support
|
||||
// [SECTION] Navigation support
|
||||
// [SECTION] Typing-select support
|
||||
// [SECTION] Columns support
|
||||
// [SECTION] Box-select support
|
||||
// [SECTION] Multi-select support
|
||||
// [SECTION] Docking support
|
||||
// [SECTION] Viewport support
|
||||
|
@ -93,6 +94,7 @@ Index of this file:
|
|||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wpragmas" // warning: unknown option after '#pragma GCC diagnostic' kind
|
||||
#pragma GCC diagnostic ignored "-Wclass-memaccess" // [__GNUC__ >= 8] warning: 'memset/memcpy' clearing/writing an object of type 'xxxx' with no trivial copy-assignment; use assignment or value-initialization instead
|
||||
#pragma GCC diagnostic ignored "-Wdeprecated-enum-enum-conversion" // warning: bitwise operation between different enumeration types ('XXXFlags_' and 'XXXFlagsPrivate_') is deprecated
|
||||
#endif
|
||||
|
||||
// In 1.89.4, we moved the implementation of "courtesy maths operators" from imgui_internal.h in imgui.h
|
||||
|
@ -123,6 +125,7 @@ struct ImBitVector; // Store 1-bit per value
|
|||
struct ImRect; // An axis-aligned rectangle (2 points)
|
||||
struct ImDrawDataBuilder; // Helper to build a ImDrawData instance
|
||||
struct ImDrawListSharedData; // Data shared between all ImDrawList instances
|
||||
struct ImGuiBoxSelectState; // Box-selection state (currently used by multi-selection, could potentially be used by others)
|
||||
struct ImGuiColorMod; // Stacked color modifier, backup of modified data so we can restore it
|
||||
struct ImGuiContext; // Main Dear ImGui context
|
||||
struct ImGuiContextHook; // Hook for extensions like ImGuiTestEngine
|
||||
|
@ -134,8 +137,9 @@ struct ImGuiInputTextDeactivateData;// Short term storage to backup text of a de
|
|||
struct ImGuiLastItemData; // Status storage for last submitted items
|
||||
struct ImGuiLocEntry; // A localization entry.
|
||||
struct ImGuiMenuColumns; // Simple column measurement, currently used for MenuItem() only
|
||||
struct ImGuiMultiSelectState; // Multi-selection persistent state (for focused selection).
|
||||
struct ImGuiMultiSelectTempData; // Multi-selection temporary state (while traversing).
|
||||
struct ImGuiNavItemData; // Result of a gamepad/keyboard directional navigation move query result
|
||||
struct ImGuiNavTreeNodeData; // Temporary storage for last TreeNode() being a Left arrow landing candidate.
|
||||
struct ImGuiMetricsConfig; // Storage for ShowMetricsWindow() and DebugNodeXXX() functions
|
||||
struct ImGuiNextWindowData; // Storage for SetNextWindow** functions
|
||||
struct ImGuiNextItemData; // Storage for SetNextItem** functions
|
||||
|
@ -154,6 +158,7 @@ struct ImGuiTableInstanceData; // Storage for one instance of a same table
|
|||
struct ImGuiTableTempData; // Temporary storage for one table (one per table in the stack), shared between tables.
|
||||
struct ImGuiTableSettings; // Storage for a table .ini settings
|
||||
struct ImGuiTableColumnsSettings; // Storage for a column .ini settings
|
||||
struct ImGuiTreeNodeStackData; // Temporary storage for TreeNode().
|
||||
struct ImGuiTypingSelectState; // Storage for GetTypingSelectRequest()
|
||||
struct ImGuiTypingSelectRequest; // Storage for GetTypingSelectRequest() (aimed to be public)
|
||||
struct ImGuiWindow; // Storage for one window
|
||||
|
@ -169,7 +174,6 @@ typedef int ImGuiLayoutType; // -> enum ImGuiLayoutType_ // E
|
|||
typedef int ImGuiActivateFlags; // -> enum ImGuiActivateFlags_ // Flags: for navigation/focus function (will be for ActivateItem() later)
|
||||
typedef int ImGuiDebugLogFlags; // -> enum ImGuiDebugLogFlags_ // Flags: for ShowDebugLogWindow(), g.DebugLogFlags
|
||||
typedef int ImGuiFocusRequestFlags; // -> enum ImGuiFocusRequestFlags_ // Flags: for FocusWindow();
|
||||
typedef int ImGuiItemFlags; // -> enum ImGuiItemFlags_ // Flags: for PushItemFlag(), g.LastItemData.InFlags
|
||||
typedef int ImGuiItemStatusFlags; // -> enum ImGuiItemStatusFlags_ // Flags: for g.LastItemData.StatusFlags
|
||||
typedef int ImGuiOldColumnFlags; // -> enum ImGuiOldColumnFlags_ // Flags: for BeginColumns()
|
||||
typedef int ImGuiNavHighlightFlags; // -> enum ImGuiNavHighlightFlags_ // Flags: for RenderNavHighlight()
|
||||
|
@ -348,6 +352,7 @@ namespace ImStb
|
|||
// - Helper: ImPool<>
|
||||
// - Helper: ImChunkStream<>
|
||||
// - Helper: ImGuiTextIndex
|
||||
// - Helper: ImGuiStorage
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
// Helpers: Hashing
|
||||
|
@ -384,6 +389,7 @@ IM_MSVC_RUNTIME_CHECKS_OFF
|
|||
static inline char ImToUpper(char c) { return (c >= 'a' && c <= 'z') ? c &= ~32 : c; }
|
||||
static inline bool ImCharIsBlankA(char c) { return c == ' ' || c == '\t'; }
|
||||
static inline bool ImCharIsBlankW(unsigned int c) { return c == ' ' || c == '\t' || c == 0x3000; }
|
||||
static inline bool ImCharIsXdigitA(char c) { return (c >= '0' && c <= '9') || (c >= 'A' && c <= 'F') || (c >= 'a' && c <= 'f'); }
|
||||
IM_MSVC_RUNTIME_CHECKS_RESTORE
|
||||
|
||||
// Helpers: Formatting
|
||||
|
@ -488,6 +494,7 @@ static inline int ImModPositive(int a, int b)
|
|||
static inline float ImDot(const ImVec2& a, const ImVec2& b) { return a.x * b.x + a.y * b.y; }
|
||||
static inline ImVec2 ImRotate(const ImVec2& v, float cos_a, float sin_a) { return ImVec2(v.x * cos_a - v.y * sin_a, v.x * sin_a + v.y * cos_a); }
|
||||
static inline float ImLinearSweep(float current, float target, float speed) { if (current < target) return ImMin(current + speed, target); if (current > target) return ImMax(current - speed, target); return current; }
|
||||
static inline float ImLinearRemapClamp(float s0, float s1, float d0, float d1, float x) { return ImSaturate((x - s0) / (s1 - s0)) * (d1 - d0) + d0; }
|
||||
static inline ImVec2 ImMul(const ImVec2& lhs, const ImVec2& rhs) { return ImVec2(lhs.x * rhs.x, lhs.y * rhs.y); }
|
||||
static inline bool ImIsFloatAboveGuaranteedIntegerPrecision(float f) { return f <= -16777216 || f >= 16777216; }
|
||||
static inline float ImExponentialMovingAverage(float avg, float sample, int n) { avg -= avg / n; avg += sample / n; return avg; }
|
||||
|
@ -722,7 +729,7 @@ struct ImChunkStream
|
|||
void swap(ImChunkStream<T>& rhs) { rhs.Buf.swap(Buf); }
|
||||
};
|
||||
|
||||
// Helper: ImGuiTextIndex<>
|
||||
// Helper: ImGuiTextIndex
|
||||
// Maintain a line index for a text buffer. This is a strong candidate to be moved into the public API.
|
||||
struct ImGuiTextIndex
|
||||
{
|
||||
|
@ -736,6 +743,8 @@ struct ImGuiTextIndex
|
|||
void append(const char* base, int old_size, int new_size);
|
||||
};
|
||||
|
||||
// Helper: ImGuiStorage
|
||||
IMGUI_API ImGuiStoragePair* ImLowerBound(ImGuiStoragePair* in_begin, ImGuiStoragePair* in_end, ImGuiID key);
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] ImDrawList support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -772,6 +781,7 @@ struct IMGUI_API ImDrawListSharedData
|
|||
ImVec2 TexUvWhitePixel; // UV of white pixel in the atlas
|
||||
ImFont* Font; // Current/default font (optional, for simplified AddText overload)
|
||||
float FontSize; // Current/default font size (optional, for simplified AddText overload)
|
||||
float FontScale; // Current/default font scale (== FontSize / Font->FontSize)
|
||||
float CurveTessellationTol; // Tessellation tolerance when using PathBezierCurveTo()
|
||||
float CircleSegmentMaxError; // Number of circle segments to use per pixel of radius for AddCircle() etc
|
||||
ImVec4 ClipRectFullscreen; // Value for PushClipRectFullscreen()
|
||||
|
@ -798,33 +808,65 @@ struct ImDrawDataBuilder
|
|||
ImDrawDataBuilder() { memset(this, 0, sizeof(*this)); }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Data types support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
struct ImGuiDataVarInfo
|
||||
{
|
||||
ImGuiDataType Type;
|
||||
ImU32 Count; // 1+
|
||||
ImU32 Offset; // Offset in parent structure
|
||||
void* GetVarPtr(void* parent) const { return (void*)((unsigned char*)parent + Offset); }
|
||||
};
|
||||
|
||||
struct ImGuiDataTypeStorage
|
||||
{
|
||||
ImU8 Data[8]; // Opaque storage to fit any data up to ImGuiDataType_COUNT
|
||||
};
|
||||
|
||||
// Type information associated to one ImGuiDataType. Retrieve with DataTypeGetInfo().
|
||||
struct ImGuiDataTypeInfo
|
||||
{
|
||||
size_t Size; // Size in bytes
|
||||
const char* Name; // Short descriptive name for the type, for debugging
|
||||
const char* PrintFmt; // Default printf format for the type
|
||||
const char* ScanFmt; // Default scanf format for the type
|
||||
};
|
||||
|
||||
// Extend ImGuiDataType_
|
||||
enum ImGuiDataTypePrivate_
|
||||
{
|
||||
ImGuiDataType_String = ImGuiDataType_COUNT + 1,
|
||||
ImGuiDataType_Pointer,
|
||||
ImGuiDataType_ID,
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Widgets support: flags, enums, data structures
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
// Flags used by upcoming items
|
||||
// Extend ImGuiItemFlags
|
||||
// - input: PushItemFlag() manipulates g.CurrentItemFlags, ItemAdd() calls may add extra flags.
|
||||
// - output: stored in g.LastItemData.InFlags
|
||||
// Current window shared by all windows.
|
||||
// This is going to be exposed in imgui.h when stabilized enough.
|
||||
enum ImGuiItemFlags_
|
||||
enum ImGuiItemFlagsPrivate_
|
||||
{
|
||||
// Controlled by user
|
||||
ImGuiItemFlags_None = 0,
|
||||
ImGuiItemFlags_NoTabStop = 1 << 0, // false // Disable keyboard tabbing. This is a "lighter" version of ImGuiItemFlags_NoNav.
|
||||
ImGuiItemFlags_ButtonRepeat = 1 << 1, // false // Button() will return true multiple times based on io.KeyRepeatDelay and io.KeyRepeatRate settings.
|
||||
ImGuiItemFlags_Disabled = 1 << 2, // false // Disable interactions but doesn't affect visuals. See BeginDisabled()/EndDisabled(). See github.com/ocornut/imgui/issues/211
|
||||
ImGuiItemFlags_NoNav = 1 << 3, // false // Disable any form of focusing (keyboard/gamepad directional navigation and SetKeyboardFocusHere() calls)
|
||||
ImGuiItemFlags_NoNavDefaultFocus = 1 << 4, // false // Disable item being a candidate for default focus (e.g. used by title bar items)
|
||||
ImGuiItemFlags_SelectableDontClosePopup = 1 << 5, // false // Disable MenuItem/Selectable() automatically closing their popup window
|
||||
ImGuiItemFlags_MixedValue = 1 << 6, // false // [BETA] Represent a mixed/indeterminate value, generally multi-selection where values differ. Currently only supported by Checkbox() (later should support all sorts of widgets)
|
||||
ImGuiItemFlags_ReadOnly = 1 << 7, // false // [ALPHA] Allow hovering interactions but underlying value is not changed.
|
||||
ImGuiItemFlags_NoWindowHoverableCheck = 1 << 8, // false // Disable hoverable check in ItemHoverable()
|
||||
ImGuiItemFlags_AllowOverlap = 1 << 9, // false // Allow being overlapped by another widget. Not-hovered to Hovered transition deferred by a frame.
|
||||
ImGuiItemFlags_Disabled = 1 << 10, // false // Disable interactions (DOES NOT affect visuals, see BeginDisabled()/EndDisabled() for full disable feature, and github #211).
|
||||
ImGuiItemFlags_ReadOnly = 1 << 11, // false // [ALPHA] Allow hovering interactions but underlying value is not changed.
|
||||
ImGuiItemFlags_MixedValue = 1 << 12, // false // [BETA] Represent a mixed/indeterminate value, generally multi-selection where values differ. Currently only supported by Checkbox() (later should support all sorts of widgets)
|
||||
ImGuiItemFlags_NoWindowHoverableCheck = 1 << 13, // false // Disable hoverable check in ItemHoverable()
|
||||
ImGuiItemFlags_AllowOverlap = 1 << 14, // false // Allow being overlapped by another widget. Not-hovered to Hovered transition deferred by a frame.
|
||||
|
||||
// Controlled by widget code
|
||||
ImGuiItemFlags_Inputable = 1 << 10, // false // [WIP] Auto-activate input mode when tab focused. Currently only used and supported by a few items before it becomes a generic feature.
|
||||
ImGuiItemFlags_HasSelectionUserData = 1 << 11, // false // Set by SetNextItemSelectionUserData()
|
||||
ImGuiItemFlags_Inputable = 1 << 20, // false // [WIP] Auto-activate input mode when tab focused. Currently only used and supported by a few items before it becomes a generic feature.
|
||||
ImGuiItemFlags_HasSelectionUserData = 1 << 21, // false // Set by SetNextItemSelectionUserData()
|
||||
ImGuiItemFlags_IsMultiSelect = 1 << 22, // false // Set by SetNextItemSelectionUserData()
|
||||
|
||||
ImGuiItemFlags_Default_ = ImGuiItemFlags_AutoClosePopups, // Please don't change, use PushItemFlag() instead.
|
||||
|
||||
// Obsolete
|
||||
//ImGuiItemFlags_SelectableDontClosePopup = !ImGuiItemFlags_AutoClosePopups, // Can't have a redirect as we inverted the behavior
|
||||
};
|
||||
|
||||
// Status flags for an already submitted item
|
||||
|
@ -927,8 +969,9 @@ enum ImGuiSelectableFlagsPrivate_
|
|||
// Extend ImGuiTreeNodeFlags_
|
||||
enum ImGuiTreeNodeFlagsPrivate_
|
||||
{
|
||||
ImGuiTreeNodeFlags_ClipLabelForTrailingButton = 1 << 20,
|
||||
ImGuiTreeNodeFlags_UpsideDownArrow = 1 << 21,// (FIXME-WIP) Turn Down arrow into an Up arrow, but reversed trees (#6517)
|
||||
ImGuiTreeNodeFlags_ClipLabelForTrailingButton = 1 << 28,// FIXME-WIP: Hard-coded for CollapsingHeader()
|
||||
ImGuiTreeNodeFlags_UpsideDownArrow = 1 << 29,// FIXME-WIP: Turn Down arrow into an Up arrow, but reversed trees (#6517)
|
||||
ImGuiTreeNodeFlags_OpenOnMask_ = ImGuiTreeNodeFlags_OpenOnDoubleClick | ImGuiTreeNodeFlags_OpenOnArrow,
|
||||
};
|
||||
|
||||
enum ImGuiSeparatorFlags_
|
||||
|
@ -1079,7 +1122,7 @@ struct IMGUI_API ImGuiInputTextState
|
|||
ImVector<char> InitialTextA; // value to revert to when pressing Escape = backup of end-user buffer at the time of focus (in UTF-8, unaltered)
|
||||
bool TextAIsValid; // temporary UTF8 buffer is not initially valid before we make the widget active (until then we pull the data from user argument)
|
||||
int BufCapacityA; // end-user buffer capacity
|
||||
float ScrollX; // horizontal scrolling/offset
|
||||
ImVec2 Scroll; // horizontal offset (managed manually) + vertical scrolling (pulled from child window's own Scroll.y)
|
||||
ImStb::STB_TexteditState Stb; // state for stb_textedit.h
|
||||
float CursorAnim; // timer for cursor blink, reset on every user action so the cursor reappears immediately
|
||||
bool CursorFollow; // set when we want scrolling to follow the current cursor position (not always!)
|
||||
|
@ -1167,29 +1210,30 @@ struct ImGuiNextWindowData
|
|||
inline void ClearFlags() { Flags = ImGuiNextWindowDataFlags_None; }
|
||||
};
|
||||
|
||||
// Multi-Selection item index or identifier when using SetNextItemSelectionUserData()/BeginMultiSelect()
|
||||
// (Most users are likely to use this store an item INDEX but this may be used to store a POINTER as well.)
|
||||
typedef ImS64 ImGuiSelectionUserData;
|
||||
|
||||
enum ImGuiNextItemDataFlags_
|
||||
{
|
||||
ImGuiNextItemDataFlags_None = 0,
|
||||
ImGuiNextItemDataFlags_HasWidth = 1 << 0,
|
||||
ImGuiNextItemDataFlags_HasOpen = 1 << 1,
|
||||
ImGuiNextItemDataFlags_HasShortcut = 1 << 2,
|
||||
ImGuiNextItemDataFlags_HasRefVal = 1 << 3,
|
||||
ImGuiNextItemDataFlags_HasStorageID = 1 << 4,
|
||||
};
|
||||
|
||||
struct ImGuiNextItemData
|
||||
{
|
||||
ImGuiNextItemDataFlags Flags;
|
||||
ImGuiItemFlags ItemFlags; // Currently only tested/used for ImGuiItemFlags_AllowOverlap.
|
||||
ImGuiItemFlags ItemFlags; // Currently only tested/used for ImGuiItemFlags_AllowOverlap and ImGuiItemFlags_HasSelectionUserData.
|
||||
// Non-flags members are NOT cleared by ItemAdd() meaning they are still valid during NavProcessItem()
|
||||
ImGuiID FocusScopeId; // Set by SetNextItemSelectionUserData()
|
||||
ImGuiSelectionUserData SelectionUserData; // Set by SetNextItemSelectionUserData() (note that NULL/0 is a valid value, we use -1 == ImGuiSelectionUserData_Invalid to mark invalid values)
|
||||
float Width; // Set by SetNextItemWidth()
|
||||
ImGuiKeyChord Shortcut; // Set by SetNextItemShortcut()
|
||||
ImGuiInputFlags ShortcutFlags; // Set by SetNextItemShortcut()
|
||||
bool OpenVal; // Set by SetNextItemOpen()
|
||||
ImGuiCond OpenCond : 8;
|
||||
ImU8 OpenCond; // Set by SetNextItemOpen()
|
||||
ImGuiDataTypeStorage RefVal; // Not exposed yet, for ImGuiInputTextFlags_ParseEmptyAsRefVal
|
||||
ImGuiID StorageId; // Set by SetNextItemStorageID()
|
||||
|
||||
ImGuiNextItemData() { memset(this, 0, sizeof(*this)); SelectionUserData = -1; }
|
||||
inline void ClearFlags() { Flags = ImGuiNextItemDataFlags_None; ItemFlags = ImGuiItemFlags_None; } // Also cleared manually by ItemAdd()!
|
||||
|
@ -1211,14 +1255,16 @@ struct ImGuiLastItemData
|
|||
ImGuiLastItemData() { memset(this, 0, sizeof(*this)); }
|
||||
};
|
||||
|
||||
// Store data emitted by TreeNode() for usage by TreePop() to implement ImGuiTreeNodeFlags_NavLeftJumpsBackHere.
|
||||
// This is the minimum amount of data that we need to perform the equivalent of NavApplyItemToResult() and which we can't infer in TreePop()
|
||||
// Only stored when the node is a potential candidate for landing on a Left arrow jump.
|
||||
struct ImGuiNavTreeNodeData
|
||||
// Store data emitted by TreeNode() for usage by TreePop()
|
||||
// - To implement ImGuiTreeNodeFlags_NavLeftJumpsBackHere: store the minimum amount of data
|
||||
// which we can't infer in TreePop(), to perform the equivalent of NavApplyItemToResult().
|
||||
// Only stored when the node is a potential candidate for landing on a Left arrow jump.
|
||||
struct ImGuiTreeNodeStackData
|
||||
{
|
||||
ImGuiID ID;
|
||||
ImGuiItemFlags InFlags;
|
||||
ImRect NavRect;
|
||||
ImGuiTreeNodeFlags TreeFlags;
|
||||
ImGuiItemFlags InFlags; // Used for nav landing
|
||||
ImRect NavRect; // Used for nav landing
|
||||
};
|
||||
|
||||
struct IMGUI_API ImGuiStackSizes
|
||||
|
@ -1263,40 +1309,6 @@ struct ImGuiPtrOrIndex
|
|||
ImGuiPtrOrIndex(int index) { Ptr = NULL; Index = index; }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Data types support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
struct ImGuiDataVarInfo
|
||||
{
|
||||
ImGuiDataType Type;
|
||||
ImU32 Count; // 1+
|
||||
ImU32 Offset; // Offset in parent structure
|
||||
void* GetVarPtr(void* parent) const { return (void*)((unsigned char*)parent + Offset); }
|
||||
};
|
||||
|
||||
struct ImGuiDataTypeTempStorage
|
||||
{
|
||||
ImU8 Data[8]; // Can fit any data up to ImGuiDataType_COUNT
|
||||
};
|
||||
|
||||
// Type information associated to one ImGuiDataType. Retrieve with DataTypeGetInfo().
|
||||
struct ImGuiDataTypeInfo
|
||||
{
|
||||
size_t Size; // Size in bytes
|
||||
const char* Name; // Short descriptive name for the type, for debugging
|
||||
const char* PrintFmt; // Default printf format for the type
|
||||
const char* ScanFmt; // Default scanf format for the type
|
||||
};
|
||||
|
||||
// Extend ImGuiDataType_
|
||||
enum ImGuiDataTypePrivate_
|
||||
{
|
||||
ImGuiDataType_String = ImGuiDataType_COUNT + 1,
|
||||
ImGuiDataType_Pointer,
|
||||
ImGuiDataType_ID,
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Popup support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -1347,8 +1359,8 @@ typedef ImBitArray<ImGuiKey_NamedKey_COUNT, -ImGuiKey_NamedKey_BEGIN> ImBitAr
|
|||
#define ImGuiKey_NavKeyboardTweakFast ImGuiMod_Shift
|
||||
#define ImGuiKey_NavGamepadTweakSlow ImGuiKey_GamepadL1
|
||||
#define ImGuiKey_NavGamepadTweakFast ImGuiKey_GamepadR1
|
||||
#define ImGuiKey_NavGamepadActivate ImGuiKey_GamepadFaceDown
|
||||
#define ImGuiKey_NavGamepadCancel ImGuiKey_GamepadFaceRight
|
||||
#define ImGuiKey_NavGamepadActivate (g.IO.ConfigNavSwapGamepadButtons ? ImGuiKey_GamepadFaceRight : ImGuiKey_GamepadFaceDown)
|
||||
#define ImGuiKey_NavGamepadCancel (g.IO.ConfigNavSwapGamepadButtons ? ImGuiKey_GamepadFaceDown : ImGuiKey_GamepadFaceRight)
|
||||
#define ImGuiKey_NavGamepadMenu ImGuiKey_GamepadFaceLeft
|
||||
#define ImGuiKey_NavGamepadInput ImGuiKey_GamepadFaceUp
|
||||
|
||||
|
@ -1594,7 +1606,7 @@ struct ImGuiNavItemData
|
|||
float DistBox; // Move // Best candidate box distance to current NavId
|
||||
float DistCenter; // Move // Best candidate center distance to current NavId
|
||||
float DistAxial; // Move // Best candidate axial distance to current NavId
|
||||
ImGuiSelectionUserData SelectionUserData;//I+Mov // Best candidate SetNextItemSelectionData() value.
|
||||
ImGuiSelectionUserData SelectionUserData;//I+Mov // Best candidate SetNextItemSelectionUserData() value. Valid if (InFlags & ImGuiItemFlags_HasSelectionUserData)
|
||||
|
||||
ImGuiNavItemData() { Clear(); }
|
||||
void Clear() { Window = NULL; ID = FocusScopeId = 0; InFlags = 0; SelectionUserData = -1; DistBox = DistCenter = DistAxial = FLT_MAX; }
|
||||
|
@ -1700,6 +1712,34 @@ struct ImGuiOldColumns
|
|||
ImGuiOldColumns() { memset(this, 0, sizeof(*this)); }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Box-select support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
struct ImGuiBoxSelectState
|
||||
{
|
||||
// Active box-selection data (persistent, 1 active at a time)
|
||||
ImGuiID ID;
|
||||
bool IsActive;
|
||||
bool IsStarting;
|
||||
bool IsStartedFromVoid; // Starting click was not from an item.
|
||||
bool IsStartedSetNavIdOnce;
|
||||
bool RequestClear;
|
||||
ImGuiKeyChord KeyMods : 16; // Latched key-mods for box-select logic.
|
||||
ImVec2 StartPosRel; // Start position in window-contents relative space (to support scrolling)
|
||||
ImVec2 EndPosRel; // End position in window-contents relative space
|
||||
ImVec2 ScrollAccum; // Scrolling accumulator (to behave at high-frame spaces)
|
||||
ImGuiWindow* Window;
|
||||
|
||||
// Temporary/Transient data
|
||||
bool UnclipMode; // (Temp/Transient, here in hot area). Set/cleared by the BeginMultiSelect()/EndMultiSelect() owning active box-select.
|
||||
ImRect UnclipRect; // Rectangle where ItemAdd() clipping may be temporarily disabled. Need support by multi-select supporting widgets.
|
||||
ImRect BoxSelectRectPrev; // Selection rectangle in absolute coordinates (derived every frame from BoxSelectStartPosRel and MousePos)
|
||||
ImRect BoxSelectRectCurr;
|
||||
|
||||
ImGuiBoxSelectState() { memset(this, 0, sizeof(*this)); }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Multi-select support
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -1707,9 +1747,45 @@ struct ImGuiOldColumns
|
|||
// We always assume that -1 is an invalid value (which works for indices and pointers)
|
||||
#define ImGuiSelectionUserData_Invalid ((ImGuiSelectionUserData)-1)
|
||||
|
||||
#ifdef IMGUI_HAS_MULTI_SELECT
|
||||
// <this is filled in 'range_select' branch>
|
||||
#endif // #ifdef IMGUI_HAS_MULTI_SELECT
|
||||
// Temporary storage for multi-select
|
||||
struct IMGUI_API ImGuiMultiSelectTempData
|
||||
{
|
||||
ImGuiMultiSelectIO IO; // MUST BE FIRST FIELD. Requests are set and returned by BeginMultiSelect()/EndMultiSelect() + written to by user during the loop.
|
||||
ImGuiMultiSelectState* Storage;
|
||||
ImGuiID FocusScopeId; // Copied from g.CurrentFocusScopeId (unless another selection scope was pushed manually)
|
||||
ImGuiMultiSelectFlags Flags;
|
||||
ImVec2 ScopeRectMin;
|
||||
ImVec2 BackupCursorMaxPos;
|
||||
ImGuiSelectionUserData LastSubmittedItem; // Copy of last submitted item data, used to merge output ranges.
|
||||
ImGuiID BoxSelectId;
|
||||
ImGuiKeyChord KeyMods;
|
||||
ImS8 LoopRequestSetAll; // -1: no operation, 0: clear all, 1: select all.
|
||||
bool IsEndIO; // Set when switching IO from BeginMultiSelect() to EndMultiSelect() state.
|
||||
bool IsFocused; // Set if currently focusing the selection scope (any item of the selection). May be used if you have custom shortcut associated to selection.
|
||||
bool IsKeyboardSetRange; // Set by BeginMultiSelect() when using Shift+Navigation. Because scrolling may be affected we can't afford a frame of lag with Shift+Navigation.
|
||||
bool NavIdPassedBy;
|
||||
bool RangeSrcPassedBy; // Set by the item that matches RangeSrcItem.
|
||||
bool RangeDstPassedBy; // Set by the item that matches NavJustMovedToId when IsSetRange is set.
|
||||
|
||||
ImGuiMultiSelectTempData() { Clear(); }
|
||||
void Clear() { size_t io_sz = sizeof(IO); ClearIO(); memset((void*)(&IO + 1), 0, sizeof(*this) - io_sz); } // Zero-clear except IO as we preserve IO.Requests[] buffer allocation.
|
||||
void ClearIO() { IO.Requests.resize(0); IO.RangeSrcItem = IO.NavIdItem = ImGuiSelectionUserData_Invalid; IO.NavIdSelected = IO.RangeSrcReset = false; }
|
||||
};
|
||||
|
||||
// Persistent storage for multi-select (as long as selection is alive)
|
||||
struct IMGUI_API ImGuiMultiSelectState
|
||||
{
|
||||
ImGuiWindow* Window;
|
||||
ImGuiID ID;
|
||||
int LastFrameActive; // Last used frame-count, for GC.
|
||||
int LastSelectionSize; // Set by BeginMultiSelect() based on optional info provided by user. May be -1 if unknown.
|
||||
ImS8 RangeSelected; // -1 (don't have) or true/false
|
||||
ImS8 NavIdSelected; // -1 (don't have) or true/false
|
||||
ImGuiSelectionUserData RangeSrcItem; //
|
||||
ImGuiSelectionUserData NavIdItem; // SetNextItemSelectionUserData() value for NavId (if part of submitted items)
|
||||
|
||||
ImGuiMultiSelectState() { Window = NULL; ID = 0; LastFrameActive = LastSelectionSize = 0; RangeSelected = NavIdSelected = -1; RangeSrcItem = NavIdItem = ImGuiSelectionUserData_Invalid; }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// [SECTION] Docking support
|
||||
|
@ -1731,23 +1807,28 @@ struct ImGuiViewportP : public ImGuiViewport
|
|||
ImDrawList* BgFgDrawLists[2]; // Convenience background (0) and foreground (1) draw lists. We use them to draw software mouser cursor when io.MouseDrawCursor is set and to draw most debug overlays.
|
||||
ImDrawData DrawDataP;
|
||||
ImDrawDataBuilder DrawDataBuilder; // Temporary data while building final ImDrawData
|
||||
ImVec2 WorkOffsetMin; // Work Area: Offset from Pos to top-left corner of Work Area. Generally (0,0) or (0,+main_menu_bar_height). Work Area is Full Area but without menu-bars/status-bars (so WorkArea always fit inside Pos/Size!)
|
||||
ImVec2 WorkOffsetMax; // Work Area: Offset from Pos+Size to bottom-right corner of Work Area. Generally (0,0) or (0,-status_bar_height).
|
||||
ImVec2 BuildWorkOffsetMin; // Work Area: Offset being built during current frame. Generally >= 0.0f.
|
||||
ImVec2 BuildWorkOffsetMax; // Work Area: Offset being built during current frame. Generally <= 0.0f.
|
||||
|
||||
// Per-viewport work area
|
||||
// - Insets are >= 0.0f values, distance from viewport corners to work area.
|
||||
// - BeginMainMenuBar() and DockspaceOverViewport() tend to use work area to avoid stepping over existing contents.
|
||||
// - Generally 'safeAreaInsets' in iOS land, 'DisplayCutout' in Android land.
|
||||
ImVec2 WorkInsetMin; // Work Area inset locked for the frame. GetWorkRect() always fits within GetMainRect().
|
||||
ImVec2 WorkInsetMax; // "
|
||||
ImVec2 BuildWorkInsetMin; // Work Area inset accumulator for current frame, to become next frame's WorkInset
|
||||
ImVec2 BuildWorkInsetMax; // "
|
||||
|
||||
ImGuiViewportP() { BgFgDrawListsLastFrame[0] = BgFgDrawListsLastFrame[1] = -1; BgFgDrawLists[0] = BgFgDrawLists[1] = NULL; }
|
||||
~ImGuiViewportP() { if (BgFgDrawLists[0]) IM_DELETE(BgFgDrawLists[0]); if (BgFgDrawLists[1]) IM_DELETE(BgFgDrawLists[1]); }
|
||||
|
||||
// Calculate work rect pos/size given a set of offset (we have 1 pair of offset for rect locked from last frame data, and 1 pair for currently building rect)
|
||||
ImVec2 CalcWorkRectPos(const ImVec2& off_min) const { return ImVec2(Pos.x + off_min.x, Pos.y + off_min.y); }
|
||||
ImVec2 CalcWorkRectSize(const ImVec2& off_min, const ImVec2& off_max) const { return ImVec2(ImMax(0.0f, Size.x - off_min.x + off_max.x), ImMax(0.0f, Size.y - off_min.y + off_max.y)); }
|
||||
void UpdateWorkRect() { WorkPos = CalcWorkRectPos(WorkOffsetMin); WorkSize = CalcWorkRectSize(WorkOffsetMin, WorkOffsetMax); } // Update public fields
|
||||
ImVec2 CalcWorkRectPos(const ImVec2& inset_min) const { return ImVec2(Pos.x + inset_min.x, Pos.y + inset_min.y); }
|
||||
ImVec2 CalcWorkRectSize(const ImVec2& inset_min, const ImVec2& inset_max) const { return ImVec2(ImMax(0.0f, Size.x - inset_min.x - inset_max.x), ImMax(0.0f, Size.y - inset_min.y - inset_max.y)); }
|
||||
void UpdateWorkRect() { WorkPos = CalcWorkRectPos(WorkInsetMin); WorkSize = CalcWorkRectSize(WorkInsetMin, WorkInsetMax); } // Update public fields
|
||||
|
||||
// Helpers to retrieve ImRect (we don't need to store BuildWorkRect as every access tend to change it, hence the code asymmetry)
|
||||
ImRect GetMainRect() const { return ImRect(Pos.x, Pos.y, Pos.x + Size.x, Pos.y + Size.y); }
|
||||
ImRect GetWorkRect() const { return ImRect(WorkPos.x, WorkPos.y, WorkPos.x + WorkSize.x, WorkPos.y + WorkSize.y); }
|
||||
ImRect GetBuildWorkRect() const { ImVec2 pos = CalcWorkRectPos(BuildWorkOffsetMin); ImVec2 size = CalcWorkRectSize(BuildWorkOffsetMin, BuildWorkOffsetMax); return ImRect(pos.x, pos.y, pos.x + size.x, pos.y + size.y); }
|
||||
ImRect GetBuildWorkRect() const { ImVec2 pos = CalcWorkRectPos(BuildWorkInsetMin); ImVec2 size = CalcWorkRectSize(BuildWorkInsetMin, BuildWorkInsetMax); return ImRect(pos.x, pos.y, pos.x + size.x, pos.y + size.y); }
|
||||
};
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
@ -1801,6 +1882,7 @@ enum ImGuiLocKey : int
|
|||
ImGuiLocKey_WindowingMainMenuBar,
|
||||
ImGuiLocKey_WindowingPopup,
|
||||
ImGuiLocKey_WindowingUntitled,
|
||||
ImGuiLocKey_CopyLink,
|
||||
ImGuiLocKey_COUNT
|
||||
};
|
||||
|
||||
|
@ -1918,10 +2000,12 @@ struct ImGuiContext
|
|||
bool Initialized;
|
||||
bool FontAtlasOwnedByContext; // IO.Fonts-> is owned by the ImGuiContext and will be destructed along with it.
|
||||
ImGuiIO IO;
|
||||
ImGuiPlatformIO PlatformIO;
|
||||
ImGuiStyle Style;
|
||||
ImFont* Font; // (Shortcut) == FontStack.empty() ? IO.Font : FontStack.back()
|
||||
float FontSize; // (Shortcut) == FontBaseSize * g.CurrentWindow->FontWindowScale == window->FontSize(). Text height for current window.
|
||||
float FontBaseSize; // (Shortcut) == IO.FontGlobalScale * Font->Scale * Font->FontSize. Base text height.
|
||||
float FontScale; // == FontSize / Font->FontSize
|
||||
float CurrentDpiScale; // Current window/viewport DpiScale
|
||||
ImDrawListSharedData DrawListSharedData;
|
||||
double Time;
|
||||
|
@ -1934,6 +2018,7 @@ struct ImGuiContext
|
|||
bool GcCompactAll; // Request full GC
|
||||
bool TestEngineHookItems; // Will call test engine hooks: ImGuiTestEngineHook_ItemAdd(), ImGuiTestEngineHook_ItemInfo(), ImGuiTestEngineHook_Log()
|
||||
void* TestEngine; // Test engine user data
|
||||
char ContextName[16]; // Storage for a context name (to facilitate debugging multi-context setups)
|
||||
|
||||
// Inputs
|
||||
ImVector<ImGuiInputEvent> InputEventsQueue; // Input events which will be trickled/written into IO structure.
|
||||
|
@ -1953,6 +2038,7 @@ struct ImGuiContext
|
|||
ImGuiWindow* CurrentWindow; // Window being drawn into
|
||||
ImGuiWindow* HoveredWindow; // Window the mouse is hovering. Will typically catch mouse inputs.
|
||||
ImGuiWindow* HoveredWindowUnderMovingWindow; // Hovered window ignoring MovingWindow. Only set if MovingWindow is set.
|
||||
ImGuiWindow* HoveredWindowBeforeClear; // Window the mouse is hovering. Filled even with _NoMouse. This is currently useful for multi-context compositors.
|
||||
ImGuiWindow* MovingWindow; // Track the window we clicked on (in order to preserve focus). The actual window that is moved is generally MovingWindow->RootWindow.
|
||||
ImGuiWindow* WheelingWindow; // Track the window we started mouse-wheeling on. Until a timer elapse or mouse has moved, generally keep scrolling the same window even if during the course of scrolling the mouse ends up hovering a child window.
|
||||
ImVec2 WheelingWindowRefMousePos;
|
||||
|
@ -1969,7 +2055,7 @@ struct ImGuiContext
|
|||
float HoveredIdTimer; // Measure contiguous hovering time
|
||||
float HoveredIdNotActiveTimer; // Measure contiguous hovering time where the item has not been active
|
||||
bool HoveredIdAllowOverlap;
|
||||
bool HoveredIdDisabled; // At least one widget passed the rect test, but has been discarded by disabled flag or popup inhibit. May be true even if HoveredId == 0.
|
||||
bool HoveredIdIsDisabled; // At least one widget passed the rect test, but has been discarded by disabled flag or popup inhibit. May be true even if HoveredId == 0.
|
||||
bool ItemUnclipByLog; // Disable ItemAdd() clipping, essentially a memory-locality friendly copy of LogEnabled
|
||||
ImGuiID ActiveId; // Active widget
|
||||
ImGuiID ActiveIdIsAlive; // Active widget has been seen this frame (we can't use a bool as the ActiveId may change within the frame)
|
||||
|
@ -2003,11 +2089,9 @@ struct ImGuiContext
|
|||
ImGuiKeyOwnerData KeysOwnerData[ImGuiKey_NamedKey_COUNT];
|
||||
ImGuiKeyRoutingTable KeysRoutingTable;
|
||||
ImU32 ActiveIdUsingNavDirMask; // Active widget will want to read those nav move requests (e.g. can activate a button and move away from it)
|
||||
bool ActiveIdUsingAllKeyboardKeys; // Active widget will want to read all keyboard keys inputs. (FIXME: This is a shortcut for not taking ownership of 100+ keys but perhaps best to not have the inconsistency)
|
||||
bool ActiveIdUsingAllKeyboardKeys; // Active widget will want to read all keyboard keys inputs. (this is a shortcut for not taking ownership of 100+ keys, frequently used by drag operations)
|
||||
ImGuiKeyChord DebugBreakInShortcutRouting; // Set to break in SetShortcutRouting()/Shortcut() calls.
|
||||
#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO
|
||||
ImU32 ActiveIdUsingNavInputMask; // If you used this. Since (IMGUI_VERSION_NUM >= 18804) : 'g.ActiveIdUsingNavInputMask |= (1 << ImGuiNavInput_Cancel);' becomes 'SetKeyOwner(ImGuiKey_Escape, g.ActiveId) and/or SetKeyOwner(ImGuiKey_NavGamepadCancel, g.ActiveId);'
|
||||
#endif
|
||||
//ImU32 ActiveIdUsingNavInputMask; // [OBSOLETE] Since (IMGUI_VERSION_NUM >= 18804) : 'g.ActiveIdUsingNavInputMask |= (1 << ImGuiNavInput_Cancel);' becomes --> 'SetKeyOwner(ImGuiKey_Escape, g.ActiveId) and/or SetKeyOwner(ImGuiKey_NavGamepadCancel, g.ActiveId);'
|
||||
|
||||
// Next window/item data
|
||||
ImGuiID CurrentFocusScopeId; // Value for currently appending items == g.FocusScopeStack.back(). Not to be mistaken with g.NavFocusScopeId.
|
||||
|
@ -2028,7 +2112,7 @@ struct ImGuiContext
|
|||
ImVector<ImGuiGroupData> GroupStack; // Stack for BeginGroup()/EndGroup() - not inherited by Begin()
|
||||
ImVector<ImGuiPopupData> OpenPopupStack; // Which popups are open (persistent)
|
||||
ImVector<ImGuiPopupData> BeginPopupStack; // Which level of BeginPopup() we are in (reset every frame)
|
||||
ImVector<ImGuiNavTreeNodeData> NavTreeNodeStack; // Stack for TreeNode() when a NavLeft requested is emitted.
|
||||
ImVector<ImGuiTreeNodeStackData>TreeNodeStack; // Stack for TreeNode()
|
||||
|
||||
// Viewports
|
||||
ImVector<ImGuiViewportP*> Viewports; // Active viewports (Size==1 in 'master' branch). Each viewports hold their copy of ImDrawData.
|
||||
|
@ -2037,6 +2121,7 @@ struct ImGuiContext
|
|||
ImGuiWindow* NavWindow; // Focused window for navigation. Could be called 'FocusedWindow'
|
||||
ImGuiID NavId; // Focused item for navigation
|
||||
ImGuiID NavFocusScopeId; // Focused focus scope (e.g. selection code often wants to "clear other items" when landing on an item of the same scope)
|
||||
ImGuiNavLayer NavLayer; // Focused layer (main scrolling layer, or menu/title bar layer)
|
||||
ImGuiID NavActivateId; // ~~ (g.ActiveId == 0) && (IsKeyPressed(ImGuiKey_Space) || IsKeyDown(ImGuiKey_Enter) || IsKeyPressed(ImGuiKey_NavGamepadActivate)) ? NavId : 0, also set when calling ActivateItem()
|
||||
ImGuiID NavActivateDownId; // ~~ IsKeyDown(ImGuiKey_Space) || IsKeyDown(ImGuiKey_Enter) || IsKeyDown(ImGuiKey_NavGamepadActivate) ? NavId : 0
|
||||
ImGuiID NavActivatePressedId; // ~~ IsKeyPressed(ImGuiKey_Space) || IsKeyPressed(ImGuiKey_Enter) || IsKeyPressed(ImGuiKey_NavGamepadActivate) ? NavId : 0 (no repeat)
|
||||
|
@ -2044,13 +2129,9 @@ struct ImGuiContext
|
|||
ImVector<ImGuiFocusScopeData> NavFocusRoute; // Reversed copy focus scope stack for NavId (should contains NavFocusScopeId). This essentially follow the window->ParentWindowForFocusRoute chain.
|
||||
ImGuiID NavHighlightActivatedId;
|
||||
float NavHighlightActivatedTimer;
|
||||
ImGuiID NavJustMovedToId; // Just navigated to this id (result of a successfully MoveRequest).
|
||||
ImGuiID NavJustMovedToFocusScopeId; // Just navigated to this focus scope id (result of a successfully MoveRequest).
|
||||
ImGuiKeyChord NavJustMovedToKeyMods;
|
||||
ImGuiID NavNextActivateId; // Set by ActivateItem(), queued until next frame.
|
||||
ImGuiActivateFlags NavNextActivateFlags;
|
||||
ImGuiInputSource NavInputSource; // Keyboard or Gamepad mode? THIS CAN ONLY BE ImGuiInputSource_Keyboard or ImGuiInputSource_Mouse
|
||||
ImGuiNavLayer NavLayer; // Layer we are navigating on. For now the system is hard-coded for 0=main contents and 1=menu/title bar, may expose layers later.
|
||||
ImGuiSelectionUserData NavLastValidSelectionUserData; // Last valid data passed to SetNextItemSelectionUser(), or -1. For current window. Not reset when focusing an item that doesn't have selection data.
|
||||
bool NavIdIsAlive; // Nav widget has been seen this frame ~~ NavRectRel is valid
|
||||
bool NavMousePosDirty; // When set we will update mouse position if (io.ConfigFlags & ImGuiConfigFlags_NavEnableSetMousePos) if set (NB: this not enabled by default)
|
||||
|
@ -2081,6 +2162,14 @@ struct ImGuiContext
|
|||
ImGuiNavItemData NavMoveResultOther; // Best move request candidate within NavWindow's flattened hierarchy (when using ImGuiWindowFlags_NavFlattened flag)
|
||||
ImGuiNavItemData NavTabbingResultFirst; // First tabbing request candidate within NavWindow and flattened hierarchy
|
||||
|
||||
// Navigation: record of last move request
|
||||
ImGuiID NavJustMovedFromFocusScopeId; // Just navigated from this focus scope id (result of a successfully MoveRequest).
|
||||
ImGuiID NavJustMovedToId; // Just navigated to this id (result of a successfully MoveRequest).
|
||||
ImGuiID NavJustMovedToFocusScopeId; // Just navigated to this focus scope id (result of a successfully MoveRequest).
|
||||
ImGuiKeyChord NavJustMovedToKeyMods;
|
||||
bool NavJustMovedToIsTabbing; // Copy of ImGuiNavMoveFlags_IsTabbing. Maybe we should store whole flags.
|
||||
bool NavJustMovedToHasSelectionData; // Copy of move result's InFlags & ImGuiItemFlags_HasSelectionUserData). Maybe we should just store ImGuiNavItemData.
|
||||
|
||||
// Navigation: Windowing (CTRL+TAB for list, or Menu button + keys or directional pads to move/resize)
|
||||
ImGuiKeyChord ConfigNavWindowingKeyNext; // = ImGuiMod_Ctrl | ImGuiKey_Tab (or ImGuiMod_Super | ImGuiKey_Tab on OS X). For reconfiguration (see #4828)
|
||||
ImGuiKeyChord ConfigNavWindowingKeyPrev; // = ImGuiMod_Ctrl | ImGuiMod_Shift | ImGuiKey_Tab (or ImGuiMod_Super | ImGuiMod_Shift | ImGuiKey_Tab on OS X)
|
||||
|
@ -2136,6 +2225,13 @@ struct ImGuiContext
|
|||
ImVector<ImGuiPtrOrIndex> CurrentTabBarStack;
|
||||
ImVector<ImGuiShrinkWidthItem> ShrinkWidthBuffer;
|
||||
|
||||
// Multi-Select state
|
||||
ImGuiBoxSelectState BoxSelectState;
|
||||
ImGuiMultiSelectTempData* CurrentMultiSelect;
|
||||
int MultiSelectTempDataStacked; // Temporary multi-select data size (because we leave previous instances undestructed, we generally don't use MultiSelectTempData.Size)
|
||||
ImVector<ImGuiMultiSelectTempData> MultiSelectTempData;
|
||||
ImPool<ImGuiMultiSelectState> MultiSelectStorage;
|
||||
|
||||
// Hover Delay system
|
||||
ImGuiID HoverItemDelayId;
|
||||
ImGuiID HoverItemDelayIdPreviousFrame;
|
||||
|
@ -2154,6 +2250,7 @@ struct ImGuiContext
|
|||
ImGuiInputTextDeactivatedState InputTextDeactivatedState;
|
||||
ImFont InputTextPasswordFont;
|
||||
ImGuiID TempInputId; // Temporary text input when CTRL+clicking on a slider, etc.
|
||||
ImGuiDataTypeStorage DataTypeZeroValue; // 0 for all data types
|
||||
int BeginMenuDepth;
|
||||
int BeginComboDepth;
|
||||
ImGuiColorEditFlags ColorEditOptions; // Store user options for color edit widgets
|
||||
|
@ -2184,7 +2281,7 @@ struct ImGuiContext
|
|||
|
||||
// Platform support
|
||||
ImGuiPlatformImeData PlatformImeData; // Data updated by current frame
|
||||
ImGuiPlatformImeData PlatformImeDataPrev; // Previous frame data (when changing we will call io.SetPlatformImeDataFn
|
||||
ImGuiPlatformImeData PlatformImeDataPrev; // Previous frame data. When changed we call the platform_io.Platform_SetImeDataFn() handler.
|
||||
|
||||
// Settings
|
||||
bool SettingsLoaded;
|
||||
|
@ -2251,7 +2348,7 @@ struct ImGuiContext
|
|||
Initialized = false;
|
||||
FontAtlasOwnedByContext = shared_font_atlas ? false : true;
|
||||
Font = NULL;
|
||||
FontSize = FontBaseSize = CurrentDpiScale = 0.0f;
|
||||
FontSize = FontBaseSize = FontScale = CurrentDpiScale = 0.0f;
|
||||
IO.Fonts = shared_font_atlas ? shared_font_atlas : IM_NEW(ImFontAtlas)();
|
||||
Time = 0.0f;
|
||||
FrameCount = 0;
|
||||
|
@ -2260,6 +2357,7 @@ struct ImGuiContext
|
|||
GcCompactAll = false;
|
||||
TestEngineHookItems = false;
|
||||
TestEngine = NULL;
|
||||
memset(ContextName, 0, sizeof(ContextName));
|
||||
|
||||
InputEventsNextMouseSource = ImGuiMouseSource_Mouse;
|
||||
InputEventsNextEventId = 1;
|
||||
|
@ -2268,6 +2366,7 @@ struct ImGuiContext
|
|||
CurrentWindow = NULL;
|
||||
HoveredWindow = NULL;
|
||||
HoveredWindowUnderMovingWindow = NULL;
|
||||
HoveredWindowBeforeClear = NULL;
|
||||
MovingWindow = NULL;
|
||||
WheelingWindow = NULL;
|
||||
WheelingWindowStartFrame = WheelingWindowScrolledFrame = -1;
|
||||
|
@ -2276,7 +2375,7 @@ struct ImGuiContext
|
|||
DebugHookIdInfo = 0;
|
||||
HoveredId = HoveredIdPreviousFrame = 0;
|
||||
HoveredIdAllowOverlap = false;
|
||||
HoveredIdDisabled = false;
|
||||
HoveredIdIsDisabled = false;
|
||||
HoveredIdTimer = HoveredIdNotActiveTimer = 0.0f;
|
||||
ItemUnclipByLog = false;
|
||||
ActiveId = 0;
|
||||
|
@ -2304,9 +2403,6 @@ struct ImGuiContext
|
|||
|
||||
ActiveIdUsingNavDirMask = 0x00;
|
||||
ActiveIdUsingAllKeyboardKeys = false;
|
||||
#ifndef IMGUI_DISABLE_OBSOLETE_KEYIO
|
||||
ActiveIdUsingNavInputMask = 0x00;
|
||||
#endif
|
||||
|
||||
CurrentFocusScopeId = 0;
|
||||
CurrentItemFlags = ImGuiItemFlags_None;
|
||||
|
@ -2314,18 +2410,18 @@ struct ImGuiContext
|
|||
|
||||
NavWindow = NULL;
|
||||
NavId = NavFocusScopeId = NavActivateId = NavActivateDownId = NavActivatePressedId = 0;
|
||||
NavJustMovedToId = NavJustMovedToFocusScopeId = NavNextActivateId = 0;
|
||||
NavLayer = ImGuiNavLayer_Main;
|
||||
NavNextActivateId = 0;
|
||||
NavActivateFlags = NavNextActivateFlags = ImGuiActivateFlags_None;
|
||||
NavHighlightActivatedId = 0;
|
||||
NavHighlightActivatedTimer = 0.0f;
|
||||
NavJustMovedToKeyMods = ImGuiMod_None;
|
||||
NavInputSource = ImGuiInputSource_Keyboard;
|
||||
NavLayer = ImGuiNavLayer_Main;
|
||||
NavLastValidSelectionUserData = ImGuiSelectionUserData_Invalid;
|
||||
NavIdIsAlive = false;
|
||||
NavMousePosDirty = false;
|
||||
NavDisableHighlight = true;
|
||||
NavDisableMouseHover = false;
|
||||
|
||||
NavAnyRequest = false;
|
||||
NavInitRequest = false;
|
||||
NavInitRequestFromMove = false;
|
||||
|
@ -2340,6 +2436,11 @@ struct ImGuiContext
|
|||
NavTabbingDir = 0;
|
||||
NavTabbingCounter = 0;
|
||||
|
||||
NavJustMovedFromFocusScopeId = NavJustMovedToId = NavJustMovedToFocusScopeId = 0;
|
||||
NavJustMovedToKeyMods = ImGuiMod_None;
|
||||
NavJustMovedToIsTabbing = false;
|
||||
NavJustMovedToHasSelectionData = false;
|
||||
|
||||
// All platforms use Ctrl+Tab but Ctrl<>Super are swapped on Mac...
|
||||
// FIXME: Because this value is stored, it annoyingly interfere with toggling io.ConfigMacOSXBehaviors updating this..
|
||||
ConfigNavWindowingKeyNext = IO.ConfigMacOSXBehaviors ? (ImGuiMod_Super | ImGuiKey_Tab) : (ImGuiMod_Ctrl | ImGuiKey_Tab);
|
||||
|
@ -2368,6 +2469,8 @@ struct ImGuiContext
|
|||
CurrentTable = NULL;
|
||||
TablesTempDataStacked = 0;
|
||||
CurrentTabBar = NULL;
|
||||
CurrentMultiSelect = NULL;
|
||||
MultiSelectTempDataStacked = 0;
|
||||
|
||||
HoverItemDelayId = HoverItemDelayIdPreviousFrame = HoverItemUnlockedStationaryId = HoverWindowUnlockedStationaryId = 0;
|
||||
HoverItemDelayTimer = HoverItemDelayClearTimer = 0.0f;
|
||||
|
@ -2376,6 +2479,7 @@ struct ImGuiContext
|
|||
MouseStationaryTimer = 0.0f;
|
||||
|
||||
TempInputId = 0;
|
||||
memset(&DataTypeZeroValue, 0, sizeof(DataTypeZeroValue));
|
||||
BeginMenuDepth = BeginComboDepth = 0;
|
||||
ColorEditOptions = ImGuiColorEditFlags_DefaultOptions_;
|
||||
ColorEditCurrentID = ColorEditSavedID = 0;
|
||||
|
@ -2479,7 +2583,7 @@ struct IMGUI_API ImGuiWindowTempData
|
|||
ImVec2 MenuBarOffset; // MenuBarOffset.x is sort of equivalent of a per-layer CursorPos.x, saved/restored as we switch to the menu bar. The only situation when MenuBarOffset.y is > 0 if when (SafeAreaPadding.y > FramePadding.y), often used on TVs.
|
||||
ImGuiMenuColumns MenuColumns; // Simplified columns storage for menu items measurement
|
||||
int TreeDepth; // Current tree depth.
|
||||
ImU32 TreeJumpToParentOnPopMask; // Store a copy of !g.NavIdIsAlive for TreeDepth 0..31.. Could be turned into a ImU64 if necessary.
|
||||
ImU32 TreeHasStackDataDepthMask; // Store whether given depth has ImGuiTreeNodeStackData data. Could be turned into a ImU64 if necessary.
|
||||
ImVector<ImGuiWindow*> ChildWindows;
|
||||
ImGuiStorage* StateStorage; // Current persistent per-window storage (store e.g. tree node open/close state)
|
||||
ImGuiOldColumns* CurrentColumns; // Current columns set
|
||||
|
@ -2514,7 +2618,7 @@ struct IMGUI_API ImGuiWindow
|
|||
ImVec2 WindowPadding; // Window padding at the time of Begin().
|
||||
float WindowRounding; // Window rounding at the time of Begin(). May be clamped lower to avoid rendering artifacts with title bar, menu bar etc.
|
||||
float WindowBorderSize; // Window border size at the time of Begin().
|
||||
float TitleBarHeight, MenuBarHeight;
|
||||
float TitleBarHeight, MenuBarHeight; // Note that those used to be function before 2024/05/28. If you have old code calling TitleBarHeight() you can change it to TitleBarHeight.
|
||||
float DecoOuterSizeX1, DecoOuterSizeY1; // Left/Up offsets. Sum of non-scrolling outer decorations (X1 generally == 0.0f. Y1 generally = TitleBarHeight + MenuBarHeight). Locked during Begin().
|
||||
float DecoOuterSizeX2, DecoOuterSizeY2; // Right/Down offsets (X2 generally == ScrollbarSize.x, Y2 == ScrollbarSizes.y).
|
||||
float DecoInnerSizeX1, DecoInnerSizeY1; // Applied AFTER/OVER InnerRect. Specialized for Tables as they use specialized form of clipping and frozen rows/columns are inside InnerRect (and not part of regular decoration sizes).
|
||||
|
@ -2611,6 +2715,7 @@ public:
|
|||
ImGuiID GetID(const char* str, const char* str_end = NULL);
|
||||
ImGuiID GetID(const void* ptr);
|
||||
ImGuiID GetID(int n);
|
||||
ImGuiID GetIDFromPos(const ImVec2& p_abs);
|
||||
ImGuiID GetIDFromRectangle(const ImRect& r_abs);
|
||||
|
||||
// We don't use g.FontSize because the window may be != g.CurrentWindow.
|
||||
|
@ -2722,6 +2827,7 @@ struct ImGuiTableColumn
|
|||
float MaxX;
|
||||
float WidthRequest; // Master width absolute value when !(Flags & _WidthStretch). When Stretch this is derived every frame from StretchWeight in TableUpdateLayout()
|
||||
float WidthAuto; // Automatic width
|
||||
float WidthMax; // Maximum width (FIXME: overwritten by each instance)
|
||||
float StretchWeight; // Master width weight when (Flags & _WidthStretch). Often around ~1.0f initially.
|
||||
float InitStretchWeightOrWidth; // Value passed to TableSetupColumn(). For Width it is a content width (_without padding_).
|
||||
ImRect ClipRect; // Clipping rectangle for the column
|
||||
|
@ -3020,6 +3126,7 @@ namespace ImGui
|
|||
inline void SetWindowParentWindowForFocusRoute(ImGuiWindow* window, ImGuiWindow* parent_window) { window->ParentWindowForFocusRoute = parent_window; }
|
||||
inline ImRect WindowRectAbsToRel(ImGuiWindow* window, const ImRect& r) { ImVec2 off = window->DC.CursorStartPos; return ImRect(r.Min.x - off.x, r.Min.y - off.y, r.Max.x - off.x, r.Max.y - off.y); }
|
||||
inline ImRect WindowRectRelToAbs(ImGuiWindow* window, const ImRect& r) { ImVec2 off = window->DC.CursorStartPos; return ImRect(r.Min.x + off.x, r.Min.y + off.y, r.Max.x + off.x, r.Max.y + off.y); }
|
||||
inline ImVec2 WindowPosAbsToRel(ImGuiWindow* window, const ImVec2& p) { ImVec2 off = window->DC.CursorStartPos; return ImVec2(p.x - off.x, p.y - off.y); }
|
||||
inline ImVec2 WindowPosRelToAbs(ImGuiWindow* window, const ImVec2& p) { ImVec2 off = window->DC.CursorStartPos; return ImVec2(p.x + off.x, p.y + off.y); }
|
||||
|
||||
// Windows: Display Order and Focus Order
|
||||
|
@ -3096,7 +3203,7 @@ namespace ImGui
|
|||
//#endif
|
||||
|
||||
// Basic Accessors
|
||||
inline ImGuiItemStatusFlags GetItemStatusFlags(){ ImGuiContext& g = *GImGui; return g.LastItemData.StatusFlags; }
|
||||
inline ImGuiItemStatusFlags GetItemStatusFlags() { ImGuiContext& g = *GImGui; return g.LastItemData.StatusFlags; }
|
||||
inline ImGuiItemFlags GetItemFlags() { ImGuiContext& g = *GImGui; return g.LastItemData.InFlags; }
|
||||
inline ImGuiID GetActiveID() { ImGuiContext& g = *GImGui; return g.ActiveId; }
|
||||
inline ImGuiID GetFocusID() { ImGuiContext& g = *GImGui; return g.NavId; }
|
||||
|
@ -3122,13 +3229,9 @@ namespace ImGui
|
|||
IMGUI_API ImVec2 CalcItemSize(ImVec2 size, float default_w, float default_h);
|
||||
IMGUI_API float CalcWrapWidthForPos(const ImVec2& pos, float wrap_pos_x);
|
||||
IMGUI_API void PushMultiItemsWidths(int components, float width_full);
|
||||
IMGUI_API bool IsItemToggledSelection(); // Was the last item selection toggled? (after Selectable(), TreeNode() etc. We only returns toggle _event_ in order to handle clipping correctly)
|
||||
IMGUI_API ImVec2 GetContentRegionMaxAbs();
|
||||
IMGUI_API void ShrinkWidths(ImGuiShrinkWidthItem* items, int count, float width_excess);
|
||||
|
||||
// Parameter stacks (shared)
|
||||
IMGUI_API void PushItemFlag(ImGuiItemFlags option, bool enabled);
|
||||
IMGUI_API void PopItemFlag();
|
||||
IMGUI_API const ImGuiDataVarInfo* GetStyleVarInfo(ImGuiStyleVar idx);
|
||||
IMGUI_API void BeginDisabledOverrideReenable();
|
||||
IMGUI_API void EndDisabledOverrideReenable();
|
||||
|
@ -3139,16 +3242,16 @@ namespace ImGui
|
|||
IMGUI_API void LogRenderedText(const ImVec2* ref_pos, const char* text, const char* text_end = NULL);
|
||||
IMGUI_API void LogSetNextTextDecoration(const char* prefix, const char* suffix);
|
||||
|
||||
// Popups, Modals, Tooltips
|
||||
// Childs
|
||||
IMGUI_API bool BeginChildEx(const char* name, ImGuiID id, const ImVec2& size_arg, ImGuiChildFlags child_flags, ImGuiWindowFlags window_flags);
|
||||
|
||||
// Popups, Modals
|
||||
IMGUI_API bool BeginPopupEx(ImGuiID id, ImGuiWindowFlags extra_window_flags);
|
||||
IMGUI_API void OpenPopupEx(ImGuiID id, ImGuiPopupFlags popup_flags = ImGuiPopupFlags_None);
|
||||
IMGUI_API void ClosePopupToLevel(int remaining, bool restore_focus_to_window_under_popup);
|
||||
IMGUI_API void ClosePopupsOverWindow(ImGuiWindow* ref_window, bool restore_focus_to_window_under_popup);
|
||||
IMGUI_API void ClosePopupsExceptModals();
|
||||
IMGUI_API bool IsPopupOpen(ImGuiID id, ImGuiPopupFlags popup_flags);
|
||||
IMGUI_API bool BeginPopupEx(ImGuiID id, ImGuiWindowFlags extra_flags);
|
||||
IMGUI_API bool BeginTooltipEx(ImGuiTooltipFlags tooltip_flags, ImGuiWindowFlags extra_window_flags);
|
||||
IMGUI_API bool BeginTooltipHidden();
|
||||
IMGUI_API ImRect GetPopupAllowedExtentRect(ImGuiWindow* window);
|
||||
IMGUI_API ImGuiWindow* GetTopMostPopupModal();
|
||||
IMGUI_API ImGuiWindow* GetTopMostAndVisiblePopupModal();
|
||||
|
@ -3156,6 +3259,10 @@ namespace ImGui
|
|||
IMGUI_API ImVec2 FindBestWindowPosForPopup(ImGuiWindow* window);
|
||||
IMGUI_API ImVec2 FindBestWindowPosForPopupEx(const ImVec2& ref_pos, const ImVec2& size, ImGuiDir* last_dir, const ImRect& r_outer, const ImRect& r_avoid, ImGuiPopupPositionPolicy policy);
|
||||
|
||||
// Tooltips
|
||||
IMGUI_API bool BeginTooltipEx(ImGuiTooltipFlags tooltip_flags, ImGuiWindowFlags extra_window_flags);
|
||||
IMGUI_API bool BeginTooltipHidden();
|
||||
|
||||
// Menus
|
||||
IMGUI_API bool BeginViewportSideBar(const char* name, ImGuiViewport* viewport, ImGuiDir dir, float size, ImGuiWindowFlags window_flags);
|
||||
IMGUI_API bool BeginMenuEx(const char* label, const char* icon, bool enabled = true);
|
||||
|
@ -3173,7 +3280,7 @@ namespace ImGui
|
|||
IMGUI_API void NavMoveRequestSubmit(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags);
|
||||
IMGUI_API void NavMoveRequestForward(ImGuiDir move_dir, ImGuiDir clip_dir, ImGuiNavMoveFlags move_flags, ImGuiScrollFlags scroll_flags);
|
||||
IMGUI_API void NavMoveRequestResolveWithLastItem(ImGuiNavItemData* result);
|
||||
IMGUI_API void NavMoveRequestResolveWithPastTreeNode(ImGuiNavItemData* result, ImGuiNavTreeNodeData* tree_node_data);
|
||||
IMGUI_API void NavMoveRequestResolveWithPastTreeNode(ImGuiNavItemData* result, ImGuiTreeNodeStackData* tree_node_data);
|
||||
IMGUI_API void NavMoveRequestCancel();
|
||||
IMGUI_API void NavMoveRequestApplyResult();
|
||||
IMGUI_API void NavMoveRequestTryWrapping(ImGuiWindow* window, ImGuiNavMoveFlags move_flags);
|
||||
|
@ -3200,7 +3307,7 @@ namespace ImGui
|
|||
inline bool IsGamepadKey(ImGuiKey key) { return key >= ImGuiKey_Gamepad_BEGIN && key < ImGuiKey_Gamepad_END; }
|
||||
inline bool IsMouseKey(ImGuiKey key) { return key >= ImGuiKey_Mouse_BEGIN && key < ImGuiKey_Mouse_END; }
|
||||
inline bool IsAliasKey(ImGuiKey key) { return key >= ImGuiKey_Aliases_BEGIN && key < ImGuiKey_Aliases_END; }
|
||||
inline bool IsModKey(ImGuiKey key) { return key >= ImGuiKey_LeftCtrl && key <= ImGuiKey_RightSuper; }
|
||||
inline bool IsLRModKey(ImGuiKey key) { return key >= ImGuiKey_LeftCtrl && key <= ImGuiKey_RightSuper; }
|
||||
ImGuiKeyChord FixupKeyChord(ImGuiKeyChord key_chord);
|
||||
inline ImGuiKey ConvertSingleModFlagToKey(ImGuiKey key)
|
||||
{
|
||||
|
@ -3238,7 +3345,7 @@ namespace ImGui
|
|||
IMGUI_API ImGuiID GetKeyOwner(ImGuiKey key);
|
||||
IMGUI_API void SetKeyOwner(ImGuiKey key, ImGuiID owner_id, ImGuiInputFlags flags = 0);
|
||||
IMGUI_API void SetKeyOwnersForKeyChord(ImGuiKeyChord key, ImGuiID owner_id, ImGuiInputFlags flags = 0);
|
||||
IMGUI_API void SetItemKeyOwner(ImGuiKey key, ImGuiInputFlags flags = 0); // Set key owner to last item if it is hovered or active. Equivalent to 'if (IsItemHovered() || IsItemActive()) { SetKeyOwner(key, GetItemID());'.
|
||||
IMGUI_API void SetItemKeyOwner(ImGuiKey key, ImGuiInputFlags flags); // Set key owner to last item if it is hovered or active. Equivalent to 'if (IsItemHovered() || IsItemActive()) { SetKeyOwner(key, GetItemID());'.
|
||||
IMGUI_API bool TestKeyOwner(ImGuiKey key, ImGuiID owner_id); // Test that key is either not owned, either owned by 'owner_id'
|
||||
inline ImGuiKeyOwnerData* GetKeyOwnerData(ImGuiContext* ctx, ImGuiKey key) { if (key & ImGuiMod_Mask_) key = ConvertSingleModFlagToKey(key); IM_ASSERT(IsNamedKey(key)); return &ctx->KeysOwnerData[key - ImGuiKey_NamedKey_BEGIN]; }
|
||||
|
||||
|
@ -3301,6 +3408,18 @@ namespace ImGui
|
|||
IMGUI_API int TypingSelectFindNextSingleCharMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data, int nav_item_idx);
|
||||
IMGUI_API int TypingSelectFindBestLeadingMatch(ImGuiTypingSelectRequest* req, int items_count, const char* (*get_item_name_func)(void*, int), void* user_data);
|
||||
|
||||
// Box-Select API
|
||||
IMGUI_API bool BeginBoxSelect(const ImRect& scope_rect, ImGuiWindow* window, ImGuiID box_select_id, ImGuiMultiSelectFlags ms_flags);
|
||||
IMGUI_API void EndBoxSelect(const ImRect& scope_rect, ImGuiMultiSelectFlags ms_flags);
|
||||
|
||||
// Multi-Select API
|
||||
IMGUI_API void MultiSelectItemHeader(ImGuiID id, bool* p_selected, ImGuiButtonFlags* p_button_flags);
|
||||
IMGUI_API void MultiSelectItemFooter(ImGuiID id, bool* p_selected, bool* p_pressed);
|
||||
IMGUI_API void MultiSelectAddSetAll(ImGuiMultiSelectTempData* ms, bool selected);
|
||||
IMGUI_API void MultiSelectAddSetRange(ImGuiMultiSelectTempData* ms, bool selected, int range_dir, ImGuiSelectionUserData first_item, ImGuiSelectionUserData last_item);
|
||||
inline ImGuiBoxSelectState* GetBoxSelectState(ImGuiID id) { ImGuiContext& g = *GImGui; return (id != 0 && g.BoxSelectState.ID == id && g.BoxSelectState.IsActive) ? &g.BoxSelectState : NULL; }
|
||||
inline ImGuiMultiSelectState* GetMultiSelectState(ImGuiID id) { ImGuiContext& g = *GImGui; return g.MultiSelectStorage.GetByKey(id); }
|
||||
|
||||
// Internal Columns API (this is not exposed because we will encourage transitioning to the Tables API)
|
||||
IMGUI_API void SetWindowClipRectBeforeSetChannel(ImGuiWindow* window, const ImRect& clip_rect);
|
||||
IMGUI_API void BeginColumns(const char* str_id, int count, ImGuiOldColumnFlags flags = 0); // setup number of columns. use an identifier to distinguish multiple column sets. close with EndColumns().
|
||||
|
@ -3317,7 +3436,6 @@ namespace ImGui
|
|||
IMGUI_API void TableOpenContextMenu(int column_n = -1);
|
||||
IMGUI_API void TableSetColumnWidth(int column_n, float width);
|
||||
IMGUI_API void TableSetColumnSortDirection(int column_n, ImGuiSortDirection sort_direction, bool append_to_sort_specs);
|
||||
IMGUI_API int TableGetHoveredColumn(); // May use (TableGetColumnFlags() & ImGuiTableColumnFlags_IsHovered) instead. Return hovered column. return -1 when table is not hovered. return columns_count if the unused space at the right of visible columns is hovered.
|
||||
IMGUI_API int TableGetHoveredRow(); // Retrieve *PREVIOUS FRAME* hovered row. This difference with TableGetHoveredColumn() is the reason why this is not public yet.
|
||||
IMGUI_API float TableGetHeaderRowHeight();
|
||||
IMGUI_API float TableGetHeaderAngledMaxLabelWidth();
|
||||
|
@ -3353,7 +3471,7 @@ namespace ImGui
|
|||
IMGUI_API ImRect TableGetCellBgRect(const ImGuiTable* table, int column_n);
|
||||
IMGUI_API const char* TableGetColumnName(const ImGuiTable* table, int column_n);
|
||||
IMGUI_API ImGuiID TableGetColumnResizeID(ImGuiTable* table, int column_n, int instance_no = 0);
|
||||
IMGUI_API float TableGetMaxColumnWidth(const ImGuiTable* table, int column_n);
|
||||
IMGUI_API float TableCalcMaxColumnWidth(const ImGuiTable* table, int column_n);
|
||||
IMGUI_API void TableSetColumnWidthAutoSingle(ImGuiTable* table, int column_n);
|
||||
IMGUI_API void TableSetColumnWidthAutoAll(ImGuiTable* table);
|
||||
IMGUI_API void TableRemove(ImGuiTable* table);
|
||||
|
@ -3398,7 +3516,7 @@ namespace ImGui
|
|||
IMGUI_API void RenderTextClipped(const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_end, const ImVec2* text_size_if_known, const ImVec2& align = ImVec2(0, 0), const ImRect* clip_rect = NULL);
|
||||
IMGUI_API void RenderTextClippedEx(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, const char* text, const char* text_end, const ImVec2* text_size_if_known, const ImVec2& align = ImVec2(0, 0), const ImRect* clip_rect = NULL);
|
||||
IMGUI_API void RenderTextEllipsis(ImDrawList* draw_list, const ImVec2& pos_min, const ImVec2& pos_max, float clip_max_x, float ellipsis_max_x, const char* text, const char* text_end, const ImVec2* text_size_if_known);
|
||||
IMGUI_API void RenderFrame(ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, bool border = true, float rounding = 0.0f);
|
||||
IMGUI_API void RenderFrame(ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, bool borders = true, float rounding = 0.0f);
|
||||
IMGUI_API void RenderFrameBorder(ImVec2 p_min, ImVec2 p_max, float rounding = 0.0f);
|
||||
IMGUI_API void RenderColorRectWithAlphaCheckerboard(ImDrawList* draw_list, ImVec2 p_min, ImVec2 p_max, ImU32 fill_col, float grid_step, ImVec2 grid_off, float rounding = 0.0f, ImDrawFlags flags = 0);
|
||||
IMGUI_API void RenderNavHighlight(const ImRect& bb, ImGuiID id, ImGuiNavHighlightFlags flags = ImGuiNavHighlightFlags_None); // Navigation highlight
|
||||
|
@ -3438,11 +3556,13 @@ namespace ImGui
|
|||
IMGUI_API bool DragBehavior(ImGuiID id, ImGuiDataType data_type, void* p_v, float v_speed, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags);
|
||||
IMGUI_API bool SliderBehavior(const ImRect& bb, ImGuiID id, ImGuiDataType data_type, void* p_v, const void* p_min, const void* p_max, const char* format, ImGuiSliderFlags flags, ImRect* out_grab_bb);
|
||||
IMGUI_API bool SplitterBehavior(const ImRect& bb, ImGuiID id, ImGuiAxis axis, float* size1, float* size2, float min_size1, float min_size2, float hover_extend = 0.0f, float hover_visibility_delay = 0.0f, ImU32 bg_col = 0);
|
||||
|
||||
// Widgets: Tree Nodes
|
||||
IMGUI_API bool TreeNodeBehavior(ImGuiID id, ImGuiTreeNodeFlags flags, const char* label, const char* label_end = NULL);
|
||||
IMGUI_API void TreePushOverrideID(ImGuiID id);
|
||||
IMGUI_API void TreeNodeSetOpen(ImGuiID id, bool open);
|
||||
IMGUI_API bool TreeNodeUpdateNextOpen(ImGuiID id, ImGuiTreeNodeFlags flags); // Return open state. Consume previous SetNextItemOpen() data, if any. May return true when logging.
|
||||
IMGUI_API void SetNextItemSelectionUserData(ImGuiSelectionUserData selection_user_data);
|
||||
IMGUI_API bool TreeNodeGetOpen(ImGuiID storage_id);
|
||||
IMGUI_API void TreeNodeSetOpen(ImGuiID storage_id, bool open);
|
||||
IMGUI_API bool TreeNodeUpdateNextOpen(ImGuiID storage_id, ImGuiTreeNodeFlags flags); // Return open state. Consume previous SetNextItemOpen() data, if any. May return true when logging.
|
||||
|
||||
// Template functions are instantiated in imgui_widgets.cpp for a finite number of types.
|
||||
// To use them externally (for custom widget) you may need an "extern template" statement in your code in order to link to existing instances and silence Clang warnings (see #2036).
|
||||
|
@ -3458,7 +3578,7 @@ namespace ImGui
|
|||
IMGUI_API const ImGuiDataTypeInfo* DataTypeGetInfo(ImGuiDataType data_type);
|
||||
IMGUI_API int DataTypeFormatString(char* buf, int buf_size, ImGuiDataType data_type, const void* p_data, const char* format);
|
||||
IMGUI_API void DataTypeApplyOp(ImGuiDataType data_type, int op, void* output, const void* arg_1, const void* arg_2);
|
||||
IMGUI_API bool DataTypeApplyFromText(const char* buf, ImGuiDataType data_type, void* p_data, const char* format);
|
||||
IMGUI_API bool DataTypeApplyFromText(const char* buf, ImGuiDataType data_type, void* p_data, const char* format, void* p_data_when_empty = NULL);
|
||||
IMGUI_API int DataTypeCompare(ImGuiDataType data_type, const void* arg_1, const void* arg_2);
|
||||
IMGUI_API bool DataTypeClamp(ImGuiDataType data_type, void* p_data, const void* p_min, const void* p_max);
|
||||
|
||||
|
@ -3469,6 +3589,7 @@ namespace ImGui
|
|||
IMGUI_API bool TempInputScalar(const ImRect& bb, ImGuiID id, const char* label, ImGuiDataType data_type, void* p_data, const char* format, const void* p_clamp_min = NULL, const void* p_clamp_max = NULL);
|
||||
inline bool TempInputIsActive(ImGuiID id) { ImGuiContext& g = *GImGui; return (g.ActiveId == id && g.TempInputId == id); }
|
||||
inline ImGuiInputTextState* GetInputTextState(ImGuiID id) { ImGuiContext& g = *GImGui; return (id != 0 && g.InputTextState.ID == id) ? &g.InputTextState : NULL; } // Get input text state if active
|
||||
IMGUI_API void SetNextItemRefVal(ImGuiDataType data_type, void* p_data);
|
||||
|
||||
// Color
|
||||
IMGUI_API void ColorTooltip(const char* text, const float* col, ImGuiColorEditFlags flags);
|
||||
|
@ -3488,12 +3609,8 @@ namespace ImGui
|
|||
IMGUI_API void GcCompactTransientWindowBuffers(ImGuiWindow* window);
|
||||
IMGUI_API void GcAwakeTransientWindowBuffers(ImGuiWindow* window);
|
||||
|
||||
// Debug Log
|
||||
IMGUI_API void DebugLog(const char* fmt, ...) IM_FMTARGS(1);
|
||||
IMGUI_API void DebugLogV(const char* fmt, va_list args) IM_FMTLIST(1);
|
||||
IMGUI_API void DebugAllocHook(ImGuiDebugAllocInfo* info, int frame_count, void* ptr, size_t size); // size >= 0 : alloc, size = -1 : free
|
||||
|
||||
// Debug Tools
|
||||
IMGUI_API void DebugAllocHook(ImGuiDebugAllocInfo* info, int frame_count, void* ptr, size_t size); // size >= 0 : alloc, size = -1 : free
|
||||
IMGUI_API void ErrorCheckEndFrameRecover(ImGuiErrorLogCallback log_callback, void* user_data = NULL);
|
||||
IMGUI_API void ErrorCheckEndWindowRecover(ImGuiErrorLogCallback log_callback, void* user_data = NULL);
|
||||
IMGUI_API void ErrorCheckUsingSetCursorPosToExtendParentBoundaries();
|
||||
|
@ -3520,6 +3637,7 @@ namespace ImGui
|
|||
IMGUI_API void DebugNodeTableSettings(ImGuiTableSettings* settings);
|
||||
IMGUI_API void DebugNodeInputTextState(ImGuiInputTextState* state);
|
||||
IMGUI_API void DebugNodeTypingSelectState(ImGuiTypingSelectState* state);
|
||||
IMGUI_API void DebugNodeMultiSelectState(ImGuiMultiSelectState* state);
|
||||
IMGUI_API void DebugNodeWindow(ImGuiWindow* window, const char* label);
|
||||
IMGUI_API void DebugNodeWindowSettings(ImGuiWindowSettings* settings);
|
||||
IMGUI_API void DebugNodeWindowsList(ImVector<ImGuiWindow*>* windows, const char* label);
|
||||
|
|
108
source/engine/thirdparty/imgui/imgui_tables.cpp
vendored
108
source/engine/thirdparty/imgui/imgui_tables.cpp
vendored
|
@ -1,4 +1,4 @@
|
|||
// dear imgui, v1.90.8 WIP
|
||||
// dear imgui, v1.91.1
|
||||
// (tables and columns code)
|
||||
|
||||
/*
|
||||
|
@ -412,8 +412,8 @@ bool ImGui::BeginTableEx(const char* name, ImGuiID id, int columns_count, ImG
|
|||
SetNextWindowScroll(ImVec2(0.0f, 0.0f));
|
||||
|
||||
// Create scrolling region (without border and zero window padding)
|
||||
ImGuiWindowFlags child_flags = (flags & ImGuiTableFlags_ScrollX) ? ImGuiWindowFlags_HorizontalScrollbar : ImGuiWindowFlags_None;
|
||||
BeginChildEx(name, instance_id, outer_rect.GetSize(), false, child_flags);
|
||||
ImGuiWindowFlags child_window_flags = (flags & ImGuiTableFlags_ScrollX) ? ImGuiWindowFlags_HorizontalScrollbar : ImGuiWindowFlags_None;
|
||||
BeginChildEx(name, instance_id, outer_rect.GetSize(), ImGuiChildFlags_None, child_window_flags);
|
||||
table->InnerWindow = g.CurrentWindow;
|
||||
table->WorkRect = table->InnerWindow->WorkRect;
|
||||
table->OuterRect = table->InnerWindow->Rect();
|
||||
|
@ -460,16 +460,27 @@ bool ImGui::BeginTableEx(const char* name, ImGuiID id, int columns_count, ImG
|
|||
temp_data->HostBackupItemWidthStackSize = outer_window->DC.ItemWidthStack.Size;
|
||||
inner_window->DC.PrevLineSize = inner_window->DC.CurrLineSize = ImVec2(0.0f, 0.0f);
|
||||
|
||||
// Make left and top borders not overlap our contents by offsetting HostClipRect (#6765)
|
||||
// Make borders not overlap our contents by offsetting HostClipRect (#6765, #7428, #3752)
|
||||
// (we normally shouldn't alter HostClipRect as we rely on TableMergeDrawChannels() expanding non-clipped column toward the
|
||||
// limits of that rectangle, in order for ImDrawListSplitter::Merge() to merge the draw commands. However since the overlap
|
||||
// problem only affect scrolling tables in this case we can get away with doing it without extra cost).
|
||||
if (inner_window != outer_window)
|
||||
{
|
||||
// FIXME: Because inner_window's Scrollbar doesn't know about border size, since it's not encoded in window->WindowBorderSize,
|
||||
// it already overlaps it and doesn't need an extra offset. Ideally we should be able to pass custom border size with
|
||||
// different x/y values to BeginChild().
|
||||
if (flags & ImGuiTableFlags_BordersOuterV)
|
||||
{
|
||||
table->HostClipRect.Min.x = ImMin(table->HostClipRect.Min.x + TABLE_BORDER_SIZE, table->HostClipRect.Max.x);
|
||||
if (inner_window->DecoOuterSizeX2 == 0.0f)
|
||||
table->HostClipRect.Max.x = ImMax(table->HostClipRect.Max.x - TABLE_BORDER_SIZE, table->HostClipRect.Min.x);
|
||||
}
|
||||
if (flags & ImGuiTableFlags_BordersOuterH)
|
||||
{
|
||||
table->HostClipRect.Min.y = ImMin(table->HostClipRect.Min.y + TABLE_BORDER_SIZE, table->HostClipRect.Max.y);
|
||||
if (inner_window->DecoOuterSizeY2 == 0.0f)
|
||||
table->HostClipRect.Max.y = ImMax(table->HostClipRect.Max.y - TABLE_BORDER_SIZE, table->HostClipRect.Min.y);
|
||||
}
|
||||
}
|
||||
|
||||
// Padding and Spacing
|
||||
|
@ -497,7 +508,7 @@ bool ImGui::BeginTableEx(const char* name, ImGuiID id, int columns_count, ImG
|
|||
table->InnerClipRect = (inner_window == outer_window) ? table->WorkRect : inner_window->ClipRect;
|
||||
table->InnerClipRect.ClipWith(table->WorkRect); // We need this to honor inner_width
|
||||
table->InnerClipRect.ClipWithFull(table->HostClipRect);
|
||||
table->InnerClipRect.Max.y = (flags & ImGuiTableFlags_NoHostExtendY) ? ImMin(table->InnerClipRect.Max.y, inner_window->WorkRect.Max.y) : inner_window->ClipRect.Max.y;
|
||||
table->InnerClipRect.Max.y = (flags & ImGuiTableFlags_NoHostExtendY) ? ImMin(table->InnerClipRect.Max.y, inner_window->WorkRect.Max.y) : table->HostClipRect.Max.y;
|
||||
|
||||
table->RowPosY1 = table->RowPosY2 = table->WorkRect.Min.y; // This is needed somehow
|
||||
table->RowTextBaseline = 0.0f; // This will be cleared again by TableBeginRow()
|
||||
|
@ -1059,16 +1070,12 @@ void ImGui::TableUpdateLayout(ImGuiTable* table)
|
|||
continue;
|
||||
}
|
||||
|
||||
// Detect hovered column
|
||||
if (is_hovering_table && mouse_skewed_x >= column->ClipRect.Min.x && mouse_skewed_x < column->ClipRect.Max.x)
|
||||
table->HoveredColumnBody = (ImGuiTableColumnIdx)column_n;
|
||||
|
||||
// Lock start position
|
||||
column->MinX = offset_x;
|
||||
|
||||
// Lock width based on start position and minimum/maximum width for this position
|
||||
float max_width = TableGetMaxColumnWidth(table, column_n);
|
||||
column->WidthGiven = ImMin(column->WidthGiven, max_width);
|
||||
column->WidthMax = TableCalcMaxColumnWidth(table, column_n);
|
||||
column->WidthGiven = ImMin(column->WidthGiven, column->WidthMax);
|
||||
column->WidthGiven = ImMax(column->WidthGiven, ImMin(column->WidthRequest, table->MinColumnWidth));
|
||||
column->MaxX = offset_x + column->WidthGiven + table->CellSpacingX1 + table->CellSpacingX2 + table->CellPaddingX * 2.0f;
|
||||
|
||||
|
@ -1117,8 +1124,13 @@ void ImGui::TableUpdateLayout(ImGuiTable* table)
|
|||
column->Flags |= ImGuiTableColumnFlags_IsVisible;
|
||||
if (column->SortOrder != -1)
|
||||
column->Flags |= ImGuiTableColumnFlags_IsSorted;
|
||||
if (table->HoveredColumnBody == column_n)
|
||||
|
||||
// Detect hovered column
|
||||
if (is_hovering_table && mouse_skewed_x >= column->ClipRect.Min.x && mouse_skewed_x < column->ClipRect.Max.x)
|
||||
{
|
||||
column->Flags |= ImGuiTableColumnFlags_IsHovered;
|
||||
table->HoveredColumnBody = (ImGuiTableColumnIdx)column_n;
|
||||
}
|
||||
|
||||
// Alignment
|
||||
// FIXME-TABLE: This align based on the whole column width, not per-cell, and therefore isn't useful in
|
||||
|
@ -1249,7 +1261,7 @@ void ImGui::TableUpdateLayout(ImGuiTable* table)
|
|||
if (table->Flags & ImGuiTableFlags_NoClip)
|
||||
table->DrawSplitter->SetCurrentChannel(inner_window->DrawList, TABLE_DRAW_CHANNEL_NOCLIP);
|
||||
else
|
||||
inner_window->DrawList->PushClipRect(inner_window->ClipRect.Min, inner_window->ClipRect.Max, false);
|
||||
inner_window->DrawList->PushClipRect(inner_window->InnerClipRect.Min, inner_window->InnerClipRect.Max, false);
|
||||
}
|
||||
|
||||
// Process hit-testing on resizing borders. Actual size change will be applied in EndTable()
|
||||
|
@ -1996,34 +2008,37 @@ void ImGui::TableEndRow(ImGuiTable* table)
|
|||
// We need to do that in TableEndRow() instead of TableBeginRow() so the list clipper can mark end of row and
|
||||
// get the new cursor position.
|
||||
if (unfreeze_rows_request)
|
||||
{
|
||||
for (int column_n = 0; column_n < table->ColumnsCount; column_n++)
|
||||
table->Columns[column_n].NavLayerCurrent = ImGuiNavLayer_Main;
|
||||
if (unfreeze_rows_actual)
|
||||
{
|
||||
IM_ASSERT(table->IsUnfrozenRows == false);
|
||||
const float y0 = ImMax(table->RowPosY2 + 1, window->InnerClipRect.Min.y);
|
||||
table->IsUnfrozenRows = true;
|
||||
table_instance->LastFrozenHeight = y0 - table->OuterRect.Min.y;
|
||||
|
||||
// BgClipRect starts as table->InnerClipRect, reduce it now and make BgClipRectForDrawCmd == BgClipRect
|
||||
table->BgClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y = ImMin(y0, window->InnerClipRect.Max.y);
|
||||
table->BgClipRect.Max.y = table->Bg2ClipRectForDrawCmd.Max.y = window->InnerClipRect.Max.y;
|
||||
table->Bg2DrawChannelCurrent = table->Bg2DrawChannelUnfrozen;
|
||||
IM_ASSERT(table->Bg2ClipRectForDrawCmd.Min.y <= table->Bg2ClipRectForDrawCmd.Max.y);
|
||||
|
||||
float row_height = table->RowPosY2 - table->RowPosY1;
|
||||
table->RowPosY2 = window->DC.CursorPos.y = table->WorkRect.Min.y + table->RowPosY2 - table->OuterRect.Min.y;
|
||||
table->RowPosY1 = table->RowPosY2 - row_height;
|
||||
for (int column_n = 0; column_n < table->ColumnsCount; column_n++)
|
||||
if (unfreeze_rows_actual)
|
||||
{
|
||||
ImGuiTableColumn* column = &table->Columns[column_n];
|
||||
column->DrawChannelCurrent = column->DrawChannelUnfrozen;
|
||||
column->ClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y;
|
||||
}
|
||||
IM_ASSERT(table->IsUnfrozenRows == false);
|
||||
table->IsUnfrozenRows = true;
|
||||
|
||||
// Update cliprect ahead of TableBeginCell() so clipper can access to new ClipRect->Min.y
|
||||
SetWindowClipRectBeforeSetChannel(window, table->Columns[0].ClipRect);
|
||||
table->DrawSplitter->SetCurrentChannel(window->DrawList, table->Columns[0].DrawChannelCurrent);
|
||||
// BgClipRect starts as table->InnerClipRect, reduce it now and make BgClipRectForDrawCmd == BgClipRect
|
||||
table->BgClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y = ImMin(y0, window->InnerClipRect.Max.y);
|
||||
table->BgClipRect.Max.y = table->Bg2ClipRectForDrawCmd.Max.y = window->InnerClipRect.Max.y;
|
||||
table->Bg2DrawChannelCurrent = table->Bg2DrawChannelUnfrozen;
|
||||
IM_ASSERT(table->Bg2ClipRectForDrawCmd.Min.y <= table->Bg2ClipRectForDrawCmd.Max.y);
|
||||
|
||||
float row_height = table->RowPosY2 - table->RowPosY1;
|
||||
table->RowPosY2 = window->DC.CursorPos.y = table->WorkRect.Min.y + table->RowPosY2 - table->OuterRect.Min.y;
|
||||
table->RowPosY1 = table->RowPosY2 - row_height;
|
||||
for (int column_n = 0; column_n < table->ColumnsCount; column_n++)
|
||||
{
|
||||
ImGuiTableColumn* column = &table->Columns[column_n];
|
||||
column->DrawChannelCurrent = column->DrawChannelUnfrozen;
|
||||
column->ClipRect.Min.y = table->Bg2ClipRectForDrawCmd.Min.y;
|
||||
}
|
||||
|
||||
// Update cliprect ahead of TableBeginCell() so clipper can access to new ClipRect->Min.y
|
||||
SetWindowClipRectBeforeSetChannel(window, table->Columns[0].ClipRect);
|
||||
table->DrawSplitter->SetCurrentChannel(window->DrawList, table->Columns[0].DrawChannelCurrent);
|
||||
}
|
||||
}
|
||||
|
||||
if (!(table->RowFlags & ImGuiTableRowFlags_Headers))
|
||||
|
@ -2192,8 +2207,8 @@ void ImGui::TableEndCell(ImGuiTable* table)
|
|||
// Note that actual columns widths are computed in TableUpdateLayout().
|
||||
//-------------------------------------------------------------------------
|
||||
|
||||
// Maximum column content width given current layout. Use column->MinX so this value on a per-column basis.
|
||||
float ImGui::TableGetMaxColumnWidth(const ImGuiTable* table, int column_n)
|
||||
// Maximum column content width given current layout. Use column->MinX so this value differs on a per-column basis.
|
||||
float ImGui::TableCalcMaxColumnWidth(const ImGuiTable* table, int column_n)
|
||||
{
|
||||
const ImGuiTableColumn* column = &table->Columns[column_n];
|
||||
float max_width = FLT_MAX;
|
||||
|
@ -2255,7 +2270,7 @@ void ImGui::TableSetColumnWidth(int column_n, float width)
|
|||
// Compare both requested and actual given width to avoid overwriting requested width when column is stuck (minimum size, bounded)
|
||||
IM_ASSERT(table->MinColumnWidth > 0.0f);
|
||||
const float min_width = table->MinColumnWidth;
|
||||
const float max_width = ImMax(min_width, TableGetMaxColumnWidth(table, column_n));
|
||||
const float max_width = ImMax(min_width, column_0->WidthMax); // Don't use TableCalcMaxColumnWidth() here as it would rely on MinX from last instance (#7933)
|
||||
column_0_width = ImClamp(column_0_width, min_width, max_width);
|
||||
if (column_0->WidthGiven == column_0_width || column_0->WidthRequest == column_0_width)
|
||||
return;
|
||||
|
@ -2740,7 +2755,7 @@ void ImGui::TableDrawBorders(ImGuiTable* table)
|
|||
const ImU32 outer_col = table->BorderColorStrong;
|
||||
if ((table->Flags & ImGuiTableFlags_BordersOuter) == ImGuiTableFlags_BordersOuter)
|
||||
{
|
||||
inner_drawlist->AddRect(outer_border.Min, outer_border.Max + ImVec2(1, 1), outer_col, 0.0f, 0, border_size);
|
||||
inner_drawlist->AddRect(outer_border.Min, outer_border.Max, outer_col, 0.0f, 0, border_size);
|
||||
}
|
||||
else if (table->Flags & ImGuiTableFlags_BordersOuterV)
|
||||
{
|
||||
|
@ -3004,7 +3019,8 @@ float ImGui::TableGetHeaderAngledMaxLabelWidth()
|
|||
// The intent is that advanced users willing to create customized headers would not need to use this helper
|
||||
// and can create their own! For example: TableHeader() may be preceded by Checkbox() or other custom widgets.
|
||||
// See 'Demo->Tables->Custom headers' for a demonstration of implementing a custom version of this.
|
||||
// This code is constructed to not make much use of internal functions, as it is intended to be a template to copy.
|
||||
// This code is intentionally written to not make much use of internal functions, to give you better direction
|
||||
// if you need to write your own.
|
||||
// FIXME-TABLE: TableOpenContextMenu() and TableGetHeaderRowHeight() are not public.
|
||||
void ImGui::TableHeadersRow()
|
||||
{
|
||||
|
@ -3012,7 +3028,8 @@ void ImGui::TableHeadersRow()
|
|||
ImGuiTable* table = g.CurrentTable;
|
||||
IM_ASSERT(table != NULL && "Need to call TableHeadersRow() after BeginTable()!");
|
||||
|
||||
// Layout if not already done (this is automatically done by TableNextRow, we do it here solely to facilitate stepping in debugger as it is frequent to step in TableUpdateLayout)
|
||||
// Call layout if not already done. This is automatically done by TableNextRow: we do it here _only_ to make
|
||||
// it easier to debug-step in TableUpdateLayout(). Your own version of this function doesn't need this.
|
||||
if (!table->IsLayoutLocked)
|
||||
TableUpdateLayout(table);
|
||||
|
||||
|
@ -3029,8 +3046,7 @@ void ImGui::TableHeadersRow()
|
|||
if (!TableSetColumnIndex(column_n))
|
||||
continue;
|
||||
|
||||
// Push an id to allow unnamed labels (generally accidental, but let's behave nicely with them)
|
||||
// In your own code you may omit the PushID/PopID all-together, provided you know they won't collide.
|
||||
// Push an id to allow empty/unnamed headers. This is also idiomatic as it ensure there is a consistent ID path to access columns (for e.g. automation)
|
||||
const char* name = (TableGetColumnFlags(column_n) & ImGuiTableColumnFlags_NoHeaderLabel) ? "" : TableGetColumnName(column_n);
|
||||
PushID(column_n);
|
||||
TableHeader(name);
|
||||
|
@ -3269,7 +3285,7 @@ void ImGui::TableAngledHeadersRowEx(ImGuiID row_id, float angle, float max_label
|
|||
ButtonBehavior(row_r, row_id, NULL, NULL);
|
||||
KeepAliveID(row_id);
|
||||
|
||||
const float ascent_scaled = g.Font->Ascent * (g.FontSize / g.Font->FontSize); // FIXME: Standardize those scaling factors better
|
||||
const float ascent_scaled = g.Font->Ascent * g.FontScale; // FIXME: Standardize those scaling factors better
|
||||
const float line_off_for_ascent_x = (ImMax((g.FontSize - ascent_scaled) * 0.5f, 0.0f) / -sin_a) * (flip_label ? -1.0f : 1.0f);
|
||||
const ImVec2 padding = g.Style.CellPadding; // We will always use swapped component
|
||||
const ImVec2 align = g.Style.TableAngledHeadersTextAlign;
|
||||
|
@ -3471,7 +3487,7 @@ void ImGui::TableDrawDefaultContextMenu(ImGuiTable* table, ImGuiTableFlags flags
|
|||
Separator();
|
||||
want_separator = true;
|
||||
|
||||
PushItemFlag(ImGuiItemFlags_SelectableDontClosePopup, true);
|
||||
PushItemFlag(ImGuiItemFlags_AutoClosePopups, false);
|
||||
for (int other_column_n = 0; other_column_n < table->ColumnsCount; other_column_n++)
|
||||
{
|
||||
ImGuiTableColumn* other_column = &table->Columns[other_column_n];
|
||||
|
@ -4425,12 +4441,12 @@ void ImGui::EndColumns()
|
|||
NavUpdateCurrentWindowIsScrollPushableX();
|
||||
}
|
||||
|
||||
void ImGui::Columns(int columns_count, const char* id, bool border)
|
||||
void ImGui::Columns(int columns_count, const char* id, bool borders)
|
||||
{
|
||||
ImGuiWindow* window = GetCurrentWindow();
|
||||
IM_ASSERT(columns_count >= 1);
|
||||
|
||||
ImGuiOldColumnFlags flags = (border ? 0 : ImGuiOldColumnFlags_NoBorder);
|
||||
ImGuiOldColumnFlags flags = (borders ? 0 : ImGuiOldColumnFlags_NoBorder);
|
||||
//flags |= ImGuiOldColumnFlags_NoPreserveWidths; // NB: Legacy behavior
|
||||
ImGuiOldColumns* columns = window->DC.CurrentColumns;
|
||||
if (columns != NULL && columns->Count == columns_count && columns->Flags == flags)
|
||||
|
|
1643
source/engine/thirdparty/imgui/imgui_widgets.cpp
vendored
1643
source/engine/thirdparty/imgui/imgui_widgets.cpp
vendored
File diff suppressed because it is too large
Load diff
1076
source/engine/thirdparty/sokol/sokol_app.h
vendored
1076
source/engine/thirdparty/sokol/sokol_app.h
vendored
File diff suppressed because it is too large
Load diff
14
source/engine/thirdparty/sokol/sokol_audio.h
vendored
14
source/engine/thirdparty/sokol/sokol_audio.h
vendored
|
@ -453,6 +453,7 @@
|
|||
the standard logger in sokol_log.h instead, otherwise you won't see any warnings or
|
||||
errors.
|
||||
|
||||
|
||||
LICENSE
|
||||
=======
|
||||
|
||||
|
@ -1067,6 +1068,7 @@ typedef struct {
|
|||
/* sokol-audio state */
|
||||
typedef struct {
|
||||
bool valid;
|
||||
bool setup_called;
|
||||
void (*stream_cb)(float* buffer, int num_frames, int num_channels);
|
||||
void (*stream_userdata_cb)(float* buffer, int num_frames, int num_channels, void* user_data);
|
||||
void* user_data;
|
||||
|
@ -2486,9 +2488,11 @@ void _saudio_backend_shutdown(void) {
|
|||
// >>public
|
||||
SOKOL_API_IMPL void saudio_setup(const saudio_desc* desc) {
|
||||
SOKOL_ASSERT(!_saudio.valid);
|
||||
SOKOL_ASSERT(!_saudio.setup_called);
|
||||
SOKOL_ASSERT(desc);
|
||||
SOKOL_ASSERT((desc->allocator.alloc_fn && desc->allocator.free_fn) || (!desc->allocator.alloc_fn && !desc->allocator.free_fn));
|
||||
_saudio_clear(&_saudio, sizeof(_saudio));
|
||||
_saudio.setup_called = true;
|
||||
_saudio.desc = *desc;
|
||||
_saudio.stream_cb = desc->stream_cb;
|
||||
_saudio.stream_userdata_cb = desc->stream_userdata_cb;
|
||||
|
@ -2519,6 +2523,8 @@ SOKOL_API_IMPL void saudio_setup(const saudio_desc* desc) {
|
|||
}
|
||||
|
||||
SOKOL_API_IMPL void saudio_shutdown(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
_saudio.setup_called = false;
|
||||
if (_saudio.valid) {
|
||||
_saudio_backend_shutdown();
|
||||
_saudio_fifo_shutdown(&_saudio.fifo);
|
||||
|
@ -2532,26 +2538,32 @@ SOKOL_API_IMPL bool saudio_isvalid(void) {
|
|||
}
|
||||
|
||||
SOKOL_API_IMPL void* saudio_userdata(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
return _saudio.desc.user_data;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL saudio_desc saudio_query_desc(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
return _saudio.desc;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL int saudio_sample_rate(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
return _saudio.sample_rate;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL int saudio_buffer_frames(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
return _saudio.buffer_frames;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL int saudio_channels(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
return _saudio.num_channels;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL bool saudio_suspended(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
#if defined(_SAUDIO_EMSCRIPTEN)
|
||||
if (_saudio.valid) {
|
||||
return 1 == saudio_js_suspended();
|
||||
|
@ -2565,6 +2577,7 @@ SOKOL_API_IMPL bool saudio_suspended(void) {
|
|||
}
|
||||
|
||||
SOKOL_API_IMPL int saudio_expect(void) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
if (_saudio.valid) {
|
||||
const int num_frames = _saudio_fifo_writable_bytes(&_saudio.fifo) / _saudio.bytes_per_frame;
|
||||
return num_frames;
|
||||
|
@ -2575,6 +2588,7 @@ SOKOL_API_IMPL int saudio_expect(void) {
|
|||
}
|
||||
|
||||
SOKOL_API_IMPL int saudio_push(const float* frames, int num_frames) {
|
||||
SOKOL_ASSERT(_saudio.setup_called);
|
||||
SOKOL_ASSERT(frames && (num_frames > 0));
|
||||
if (_saudio.valid) {
|
||||
const int num_bytes = num_frames * _saudio.bytes_per_frame;
|
||||
|
|
10
source/engine/thirdparty/sokol/sokol_fetch.h
vendored
10
source/engine/thirdparty/sokol/sokol_fetch.h
vendored
|
@ -1201,6 +1201,11 @@ inline sfetch_handle_t sfetch_send(const sfetch_request_t& request) { return sfe
|
|||
#define _SFETCH_HAS_THREADS (1)
|
||||
#endif
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4724) // potential mod by 0
|
||||
#endif
|
||||
|
||||
// ███████ ████████ ██████ ██ ██ ██████ ████████ ███████
|
||||
// ██ ██ ██ ██ ██ ██ ██ ██ ██
|
||||
// ███████ ██ ██████ ██ ██ ██ ██ ███████
|
||||
|
@ -2806,4 +2811,9 @@ SOKOL_API_IMPL void sfetch_cancel(sfetch_handle_t h) {
|
|||
item->user.cancel = true;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
#endif /* SOKOL_FETCH_IMPL */
|
||||
|
|
260
source/engine/thirdparty/sokol/sokol_gfx.h
vendored
260
source/engine/thirdparty/sokol/sokol_gfx.h
vendored
|
@ -963,7 +963,7 @@
|
|||
ON STORAGE BUFFERS
|
||||
==================
|
||||
Storage buffers can be used to pass large amounts of random access structured
|
||||
data fromt the CPU side to the shaders. They are similar to data textures, but are
|
||||
data from the CPU side to the shaders. They are similar to data textures, but are
|
||||
more convenient to use both on the CPU and shader side since they can be accessed
|
||||
in shaders as as a 1-dimensional array of struct items.
|
||||
|
||||
|
@ -1496,6 +1496,7 @@
|
|||
.wgpu.num_bindgroup_cache_hits
|
||||
.wgpu.num_bindgroup_cache_misses
|
||||
.wgpu.num_bindgroup_cache_collisions
|
||||
.wgpu_num_bindgroup_cache_invalidates
|
||||
.wgpu.num_bindgroup_cache_vs_hash_key_mismatch
|
||||
|
||||
The value to pay attention to is `.wgpu.num_bindgroup_cache_collisions`,
|
||||
|
@ -2097,13 +2098,10 @@ typedef enum sg_primitive_type {
|
|||
used in the sg_sampler_desc.min_filter, sg_sampler_desc.mag_filter
|
||||
and sg_sampler_desc.mipmap_filter members when creating a sampler object.
|
||||
|
||||
For min_filter and mag_filter the default is SG_FILTER_NEAREST.
|
||||
|
||||
For mipmap_filter the default is SG_FILTER_NONE.
|
||||
For the default is SG_FILTER_NEAREST.
|
||||
*/
|
||||
typedef enum sg_filter {
|
||||
_SG_FILTER_DEFAULT, // value 0 reserved for default-init
|
||||
SG_FILTER_NONE, // FIXME: deprecated
|
||||
SG_FILTER_NEAREST,
|
||||
SG_FILTER_LINEAR,
|
||||
_SG_FILTER_NUM,
|
||||
|
@ -2892,7 +2890,7 @@ typedef struct sg_image_desc {
|
|||
|
||||
.min_filter: SG_FILTER_NEAREST
|
||||
.mag_filter: SG_FILTER_NEAREST
|
||||
.mipmap_filter SG_FILTER_NONE
|
||||
.mipmap_filter SG_FILTER_NEAREST
|
||||
.wrap_u: SG_WRAP_REPEAT
|
||||
.wrap_v: SG_WRAP_REPEAT
|
||||
.wrap_w: SG_WRAP_REPEAT (only SG_IMAGETYPE_3D)
|
||||
|
@ -3482,6 +3480,7 @@ typedef struct sg_frame_stats_wgpu_bindings {
|
|||
uint32_t num_bindgroup_cache_hits;
|
||||
uint32_t num_bindgroup_cache_misses;
|
||||
uint32_t num_bindgroup_cache_collisions;
|
||||
uint32_t num_bindgroup_cache_invalidates;
|
||||
uint32_t num_bindgroup_cache_hash_vs_key_mismatch;
|
||||
} sg_frame_stats_wgpu_bindings;
|
||||
|
||||
|
@ -3592,7 +3591,7 @@ typedef struct sg_frame_stats {
|
|||
_SG_LOGITEM_XMACRO(WGPU_ATTACHMENTS_CREATE_TEXTURE_VIEW_FAILED, "wgpuTextureCreateView() failed in create attachments") \
|
||||
_SG_LOGITEM_XMACRO(IDENTICAL_COMMIT_LISTENER, "attempting to add identical commit listener") \
|
||||
_SG_LOGITEM_XMACRO(COMMIT_LISTENER_ARRAY_FULL, "commit listener array full") \
|
||||
_SG_LOGITEM_XMACRO(TRACE_HOOKS_NOT_ENABLED, "sg_install_trace_hooks() called, but SG_TRACE_HOOKS is not defined") \
|
||||
_SG_LOGITEM_XMACRO(TRACE_HOOKS_NOT_ENABLED, "sg_install_trace_hooks() called, but SOKOL_TRACE_HOOKS is not defined") \
|
||||
_SG_LOGITEM_XMACRO(DEALLOC_BUFFER_INVALID_STATE, "sg_dealloc_buffer(): buffer must be in ALLOC state") \
|
||||
_SG_LOGITEM_XMACRO(DEALLOC_IMAGE_INVALID_STATE, "sg_dealloc_image(): image must be in alloc state") \
|
||||
_SG_LOGITEM_XMACRO(DEALLOC_SAMPLER_INVALID_STATE, "sg_dealloc_sampler(): sampler must be in alloc state") \
|
||||
|
@ -3650,8 +3649,6 @@ typedef struct sg_frame_stats {
|
|||
_SG_LOGITEM_XMACRO(VALIDATE_IMAGEDESC_DYNAMIC_NO_DATA, "dynamic/stream images cannot be initialized with data") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_IMAGEDESC_COMPRESSED_IMMUTABLE, "compressed images must be immutable") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SAMPLERDESC_CANARY, "sg_sampler_desc not initialized") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SAMPLERDESC_MINFILTER_NONE, "sg_sampler_desc.min_filter cannot be SG_FILTER_NONE") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SAMPLERDESC_MAGFILTER_NONE, "sg_sampler_desc.mag_filter cannot be SG_FILTER_NONE") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SAMPLERDESC_ANISTROPIC_REQUIRES_LINEAR_FILTERING, "sg_sampler_desc.max_anisotropy > 1 requires min/mag/mipmap_filter to be SG_FILTER_LINEAR") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SHADERDESC_CANARY, "sg_shader_desc not initialized") \
|
||||
_SG_LOGITEM_XMACRO(VALIDATE_SHADERDESC_SOURCE, "shader source code required") \
|
||||
|
@ -3887,6 +3884,12 @@ typedef enum sg_log_item {
|
|||
before sg_setup() is called
|
||||
.environment.d3d11.device_context
|
||||
a pointer to the ID3D11DeviceContext object
|
||||
.d3d11_shader_debugging
|
||||
set this to true to compile shaders which are provided as HLSL source
|
||||
code with debug information and without optimization, this allows
|
||||
shader debugging in tools like RenderDoc, to output source code
|
||||
instead of byte code from sokol-shdc, omit the `--binary` cmdline
|
||||
option
|
||||
|
||||
WebGPU specific:
|
||||
.wgpu_disable_bindgroups_cache
|
||||
|
@ -3999,6 +4002,7 @@ typedef struct sg_desc {
|
|||
int uniform_buffer_size;
|
||||
int max_commit_listeners;
|
||||
bool disable_validation; // disable validation layer even in debug mode, useful for tests
|
||||
bool d3d11_shader_debugging; // if true, HLSL shaders are compiled with D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION
|
||||
bool mtl_force_managed_storage_mode; // for debugging: use Metal managed storage mode for resources even with UMA
|
||||
bool mtl_use_command_buffer_with_retained_references; // Metal: use a managed MTLCommandBuffer which ref-counts used resources
|
||||
bool wgpu_disable_bindgroups_cache; // set to true to disable the WebGPU backend BindGroup cache
|
||||
|
@ -5783,10 +5787,20 @@ typedef struct {
|
|||
uint32_t id;
|
||||
} _sg_wgpu_bindgroup_handle_t;
|
||||
|
||||
#define _SG_WGPU_BINDGROUPSCACHE_NUM_ITEMS (1 + _SG_WGPU_MAX_BINDGROUP_ENTRIES)
|
||||
typedef enum {
|
||||
_SG_WGPU_BINDGROUPSCACHEITEMTYPE_NONE = 0,
|
||||
_SG_WGPU_BINDGROUPSCACHEITEMTYPE_IMAGE = 0x1111111111111111,
|
||||
_SG_WGPU_BINDGROUPSCACHEITEMTYPE_SAMPLER = 0x2222222222222222,
|
||||
_SG_WGPU_BINDGROUPSCACHEITEMTYPE_STORAGEBUFFER = 0x3333333333333333,
|
||||
_SG_WGPU_BINDGROUPSCACHEITEMTYPE_PIPELINE = 0x4444444444444444,
|
||||
} _sg_wgpu_bindgroups_cache_item_type_t;
|
||||
|
||||
#define _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS (1 + _SG_WGPU_MAX_BINDGROUP_ENTRIES)
|
||||
typedef struct {
|
||||
uint64_t hash;
|
||||
uint32_t items[_SG_WGPU_BINDGROUPSCACHE_NUM_ITEMS];
|
||||
// the format of cache key items is (_sg_wgpu_bindgroups_cache_item_type_t << 32) | handle.id,
|
||||
// where the item type is a per-resource-type bit pattern
|
||||
uint64_t items[_SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS];
|
||||
} _sg_wgpu_bindgroups_cache_key_t;
|
||||
|
||||
typedef struct {
|
||||
|
@ -7142,14 +7156,12 @@ _SOKOL_PRIVATE GLenum _sg_gl_blend_op(sg_blend_op op) {
|
|||
_SOKOL_PRIVATE GLenum _sg_gl_min_filter(sg_filter min_f, sg_filter mipmap_f) {
|
||||
if (min_f == SG_FILTER_NEAREST) {
|
||||
switch (mipmap_f) {
|
||||
case SG_FILTER_NONE: return GL_NEAREST;
|
||||
case SG_FILTER_NEAREST: return GL_NEAREST_MIPMAP_NEAREST;
|
||||
case SG_FILTER_LINEAR: return GL_NEAREST_MIPMAP_LINEAR;
|
||||
default: SOKOL_UNREACHABLE; return (GLenum)0;
|
||||
}
|
||||
} else if (min_f == SG_FILTER_LINEAR) {
|
||||
switch (mipmap_f) {
|
||||
case SG_FILTER_NONE: return GL_LINEAR;
|
||||
case SG_FILTER_NEAREST: return GL_LINEAR_MIPMAP_NEAREST;
|
||||
case SG_FILTER_LINEAR: return GL_LINEAR_MIPMAP_LINEAR;
|
||||
default: SOKOL_UNREACHABLE; return (GLenum)0;
|
||||
|
@ -8299,40 +8311,57 @@ _SOKOL_PRIVATE sg_resource_state _sg_gl_create_image(_sg_image_t* img, const sg_
|
|||
_sg_gl_cache_store_texture_sampler_binding(0);
|
||||
_sg_gl_cache_bind_texture_sampler(0, img->gl.target, img->gl.tex[slot], 0);
|
||||
glTexParameteri(img->gl.target, GL_TEXTURE_MAX_LEVEL, img->cmn.num_mipmaps - 1);
|
||||
const int num_faces = img->cmn.type == SG_IMAGETYPE_CUBE ? 6 : 1;
|
||||
int data_index = 0;
|
||||
for (int face_index = 0; face_index < num_faces; face_index++) {
|
||||
for (int mip_index = 0; mip_index < img->cmn.num_mipmaps; mip_index++, data_index++) {
|
||||
GLenum gl_img_target = img->gl.target;
|
||||
if (SG_IMAGETYPE_CUBE == img->cmn.type) {
|
||||
gl_img_target = _sg_gl_cubeface_target(face_index);
|
||||
}
|
||||
const GLvoid* data_ptr = desc->data.subimage[face_index][mip_index].ptr;
|
||||
const int mip_width = _sg_miplevel_dim(img->cmn.width, mip_index);
|
||||
const int mip_height = _sg_miplevel_dim(img->cmn.height, mip_index);
|
||||
|
||||
// NOTE: workaround for https://issues.chromium.org/issues/355605685
|
||||
// FIXME: on GLES3 and GL 4.3 (e.g. not macOS) the texture initialization
|
||||
// should be rewritten to use glTexStorage + glTexSubImage
|
||||
bool tex_storage_allocated = false;
|
||||
#if defined(__EMSCRIPTEN__)
|
||||
if (desc->data.subimage[0][0].ptr == 0) {
|
||||
tex_storage_allocated = true;
|
||||
if ((SG_IMAGETYPE_2D == img->cmn.type) || (SG_IMAGETYPE_CUBE == img->cmn.type)) {
|
||||
if (is_compressed) {
|
||||
const GLsizei data_size = (GLsizei) desc->data.subimage[face_index][mip_index].size;
|
||||
glCompressedTexImage2D(gl_img_target, mip_index, gl_internal_format,
|
||||
mip_width, mip_height, 0, data_size, data_ptr);
|
||||
} else {
|
||||
const GLenum gl_type = _sg_gl_teximage_type(img->cmn.pixel_format);
|
||||
glTexImage2D(gl_img_target, mip_index, (GLint)gl_internal_format,
|
||||
mip_width, mip_height, 0, gl_format, gl_type, data_ptr);
|
||||
}
|
||||
glTexStorage2D(img->gl.target, img->cmn.num_mipmaps, gl_internal_format, img->cmn.width, img->cmn.height);
|
||||
} else if ((SG_IMAGETYPE_3D == img->cmn.type) || (SG_IMAGETYPE_ARRAY == img->cmn.type)) {
|
||||
int mip_depth = img->cmn.num_slices;
|
||||
if (SG_IMAGETYPE_3D == img->cmn.type) {
|
||||
mip_depth = _sg_miplevel_dim(mip_depth, mip_index);
|
||||
glTexStorage3D(img->gl.target, img->cmn.num_mipmaps, gl_internal_format, img->cmn.width, img->cmn.height, img->cmn.num_slices);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
if (!tex_storage_allocated) {
|
||||
const int num_faces = img->cmn.type == SG_IMAGETYPE_CUBE ? 6 : 1;
|
||||
int data_index = 0;
|
||||
for (int face_index = 0; face_index < num_faces; face_index++) {
|
||||
for (int mip_index = 0; mip_index < img->cmn.num_mipmaps; mip_index++, data_index++) {
|
||||
GLenum gl_img_target = img->gl.target;
|
||||
if (SG_IMAGETYPE_CUBE == img->cmn.type) {
|
||||
gl_img_target = _sg_gl_cubeface_target(face_index);
|
||||
}
|
||||
if (is_compressed) {
|
||||
const GLsizei data_size = (GLsizei) desc->data.subimage[face_index][mip_index].size;
|
||||
glCompressedTexImage3D(gl_img_target, mip_index, gl_internal_format,
|
||||
mip_width, mip_height, mip_depth, 0, data_size, data_ptr);
|
||||
} else {
|
||||
const GLenum gl_type = _sg_gl_teximage_type(img->cmn.pixel_format);
|
||||
glTexImage3D(gl_img_target, mip_index, (GLint)gl_internal_format,
|
||||
mip_width, mip_height, mip_depth, 0, gl_format, gl_type, data_ptr);
|
||||
const GLvoid* data_ptr = desc->data.subimage[face_index][mip_index].ptr;
|
||||
const int mip_width = _sg_miplevel_dim(img->cmn.width, mip_index);
|
||||
const int mip_height = _sg_miplevel_dim(img->cmn.height, mip_index);
|
||||
if ((SG_IMAGETYPE_2D == img->cmn.type) || (SG_IMAGETYPE_CUBE == img->cmn.type)) {
|
||||
if (is_compressed) {
|
||||
const GLsizei data_size = (GLsizei) desc->data.subimage[face_index][mip_index].size;
|
||||
glCompressedTexImage2D(gl_img_target, mip_index, gl_internal_format,
|
||||
mip_width, mip_height, 0, data_size, data_ptr);
|
||||
} else {
|
||||
const GLenum gl_type = _sg_gl_teximage_type(img->cmn.pixel_format);
|
||||
glTexImage2D(gl_img_target, mip_index, (GLint)gl_internal_format,
|
||||
mip_width, mip_height, 0, gl_format, gl_type, data_ptr);
|
||||
}
|
||||
} else if ((SG_IMAGETYPE_3D == img->cmn.type) || (SG_IMAGETYPE_ARRAY == img->cmn.type)) {
|
||||
int mip_depth = img->cmn.num_slices;
|
||||
if (SG_IMAGETYPE_3D == img->cmn.type) {
|
||||
mip_depth = _sg_miplevel_dim(mip_depth, mip_index);
|
||||
}
|
||||
if (is_compressed) {
|
||||
const GLsizei data_size = (GLsizei) desc->data.subimage[face_index][mip_index].size;
|
||||
glCompressedTexImage3D(gl_img_target, mip_index, gl_internal_format,
|
||||
mip_width, mip_height, mip_depth, 0, data_size, data_ptr);
|
||||
} else {
|
||||
const GLenum gl_type = _sg_gl_teximage_type(img->cmn.pixel_format);
|
||||
glTexImage3D(gl_img_target, mip_index, (GLint)gl_internal_format,
|
||||
mip_width, mip_height, mip_depth, 0, gl_format, gl_type, data_ptr);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -10683,6 +10712,12 @@ _SOKOL_PRIVATE ID3DBlob* _sg_d3d11_compile_shader(const sg_shader_stage_desc* st
|
|||
return NULL;
|
||||
}
|
||||
SOKOL_ASSERT(stage_desc->d3d11_target);
|
||||
UINT flags1 = D3DCOMPILE_PACK_MATRIX_COLUMN_MAJOR;
|
||||
if (_sg.desc.d3d11_shader_debugging) {
|
||||
flags1 |= D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION;
|
||||
} else {
|
||||
flags1 |= D3DCOMPILE_OPTIMIZATION_LEVEL3;
|
||||
}
|
||||
ID3DBlob* output = NULL;
|
||||
ID3DBlob* errors_or_warnings = NULL;
|
||||
HRESULT hr = _sg.d3d11.D3DCompile_func(
|
||||
|
@ -10693,7 +10728,7 @@ _SOKOL_PRIVATE ID3DBlob* _sg_d3d11_compile_shader(const sg_shader_stage_desc* st
|
|||
NULL, // pInclude
|
||||
stage_desc->entry ? stage_desc->entry : "main", // pEntryPoint
|
||||
stage_desc->d3d11_target, // pTarget
|
||||
D3DCOMPILE_PACK_MATRIX_COLUMN_MAJOR | D3DCOMPILE_OPTIMIZATION_LEVEL3, // Flags1
|
||||
flags1, // Flags1
|
||||
0, // Flags2
|
||||
&output, // ppCode
|
||||
&errors_or_warnings); // ppErrorMsgs
|
||||
|
@ -11437,12 +11472,15 @@ _SOKOL_PRIVATE void _sg_d3d11_append_buffer(_sg_buffer_t* buf, const sg_range* d
|
|||
}
|
||||
}
|
||||
|
||||
// see: https://learn.microsoft.com/en-us/windows/win32/direct3d11/overviews-direct3d-11-resources-subresources
|
||||
// also see: https://learn.microsoft.com/en-us/windows/win32/api/d3d11/nf-d3d11-d3d11calcsubresource
|
||||
_SOKOL_PRIVATE void _sg_d3d11_update_image(_sg_image_t* img, const sg_image_data* data) {
|
||||
SOKOL_ASSERT(img && data);
|
||||
SOKOL_ASSERT(_sg.d3d11.ctx);
|
||||
SOKOL_ASSERT(img->d3d11.res);
|
||||
const int num_faces = (img->cmn.type == SG_IMAGETYPE_CUBE) ? 6:1;
|
||||
const int num_slices = (img->cmn.type == SG_IMAGETYPE_ARRAY) ? img->cmn.num_slices:1;
|
||||
const int num_depth_slices = (img->cmn.type == SG_IMAGETYPE_3D) ? img->cmn.num_slices:1;
|
||||
UINT subres_index = 0;
|
||||
HRESULT hr;
|
||||
D3D11_MAPPED_SUBRESOURCE d3d11_msr;
|
||||
|
@ -11452,26 +11490,35 @@ _SOKOL_PRIVATE void _sg_d3d11_update_image(_sg_image_t* img, const sg_image_data
|
|||
SOKOL_ASSERT(subres_index < (SG_MAX_MIPMAPS * SG_MAX_TEXTUREARRAY_LAYERS));
|
||||
const int mip_width = _sg_miplevel_dim(img->cmn.width, mip_index);
|
||||
const int mip_height = _sg_miplevel_dim(img->cmn.height, mip_index);
|
||||
const int src_pitch = _sg_row_pitch(img->cmn.pixel_format, mip_width, 1);
|
||||
const int src_row_pitch = _sg_row_pitch(img->cmn.pixel_format, mip_width, 1);
|
||||
const int src_depth_pitch = _sg_surface_pitch(img->cmn.pixel_format, mip_width, mip_height, 1);
|
||||
const sg_range* subimg_data = &(data->subimage[face_index][mip_index]);
|
||||
const size_t slice_size = subimg_data->size / (size_t)num_slices;
|
||||
SOKOL_ASSERT(slice_size == (size_t)(src_depth_pitch * num_depth_slices));
|
||||
const size_t slice_offset = slice_size * (size_t)slice_index;
|
||||
const uint8_t* slice_ptr = ((const uint8_t*)subimg_data->ptr) + slice_offset;
|
||||
hr = _sg_d3d11_Map(_sg.d3d11.ctx, img->d3d11.res, subres_index, D3D11_MAP_WRITE_DISCARD, 0, &d3d11_msr);
|
||||
_sg_stats_add(d3d11.num_map, 1);
|
||||
if (SUCCEEDED(hr)) {
|
||||
// FIXME: need to handle difference in depth-pitch for 3D textures as well!
|
||||
if (src_pitch == (int)d3d11_msr.RowPitch) {
|
||||
memcpy(d3d11_msr.pData, slice_ptr, slice_size);
|
||||
} else {
|
||||
SOKOL_ASSERT(src_pitch < (int)d3d11_msr.RowPitch);
|
||||
const uint8_t* src_ptr = slice_ptr;
|
||||
uint8_t* dst_ptr = (uint8_t*) d3d11_msr.pData;
|
||||
for (int row_index = 0; row_index < mip_height; row_index++) {
|
||||
memcpy(dst_ptr, src_ptr, (size_t)src_pitch);
|
||||
src_ptr += src_pitch;
|
||||
dst_ptr += d3d11_msr.RowPitch;
|
||||
const uint8_t* src_ptr = slice_ptr;
|
||||
uint8_t* dst_ptr = (uint8_t*)d3d11_msr.pData;
|
||||
for (int depth_index = 0; depth_index < num_depth_slices; depth_index++) {
|
||||
if (src_row_pitch == (int)d3d11_msr.RowPitch) {
|
||||
const size_t copy_size = slice_size / (size_t)num_depth_slices;
|
||||
SOKOL_ASSERT((copy_size * (size_t)num_depth_slices) == slice_size);
|
||||
memcpy(dst_ptr, src_ptr, copy_size);
|
||||
} else {
|
||||
SOKOL_ASSERT(src_row_pitch < (int)d3d11_msr.RowPitch);
|
||||
const uint8_t* src_row_ptr = src_ptr;
|
||||
uint8_t* dst_row_ptr = dst_ptr;
|
||||
for (int row_index = 0; row_index < mip_height; row_index++) {
|
||||
memcpy(dst_row_ptr, src_row_ptr, (size_t)src_row_pitch);
|
||||
src_row_ptr += src_row_pitch;
|
||||
dst_row_ptr += d3d11_msr.RowPitch;
|
||||
}
|
||||
}
|
||||
src_ptr += src_depth_pitch;
|
||||
dst_ptr += d3d11_msr.DepthPitch;
|
||||
}
|
||||
_sg_d3d11_Unmap(_sg.d3d11.ctx, img->d3d11.res, subres_index);
|
||||
_sg_stats_add(d3d11.num_unmap, 1);
|
||||
|
@ -11853,8 +11900,6 @@ _SOKOL_PRIVATE MTLSamplerMinMagFilter _sg_mtl_minmag_filter(sg_filter f) {
|
|||
|
||||
_SOKOL_PRIVATE MTLSamplerMipFilter _sg_mtl_mipmap_filter(sg_filter f) {
|
||||
switch (f) {
|
||||
case SG_FILTER_NONE:
|
||||
return MTLSamplerMipFilterNotMipmapped;
|
||||
case SG_FILTER_NEAREST:
|
||||
return MTLSamplerMipFilterNearest;
|
||||
case SG_FILTER_LINEAR:
|
||||
|
@ -13410,7 +13455,6 @@ _SOKOL_PRIVATE WGPUFilterMode _sg_wgpu_sampler_minmag_filter(sg_filter f) {
|
|||
|
||||
_SOKOL_PRIVATE WGPUMipmapFilterMode _sg_wgpu_sampler_mipmap_filter(sg_filter f) {
|
||||
switch (f) {
|
||||
case SG_FILTER_NONE:
|
||||
case SG_FILTER_NEAREST:
|
||||
return WGPUMipmapFilterMode_Nearest;
|
||||
case SG_FILTER_LINEAR:
|
||||
|
@ -14005,6 +14049,26 @@ _SOKOL_PRIVATE uint64_t _sg_wgpu_hash(const void* key, int len, uint64_t seed) {
|
|||
return h;
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE uint64_t _sg_wgpu_bindgroups_cache_item(_sg_wgpu_bindgroups_cache_item_type_t type, uint32_t id) {
|
||||
return (((uint64_t)type) << 32) | id;
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE uint64_t _sg_wgpu_bindgroups_cache_pip_item(uint32_t id) {
|
||||
return _sg_wgpu_bindgroups_cache_item(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_PIPELINE, id);
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE uint64_t _sg_wgpu_bindgroups_cache_image_item(uint32_t id) {
|
||||
return _sg_wgpu_bindgroups_cache_item(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_IMAGE, id);
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE uint64_t _sg_wgpu_bindgroups_cache_sampler_item(uint32_t id) {
|
||||
return _sg_wgpu_bindgroups_cache_item(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_SAMPLER, id);
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE uint64_t _sg_wgpu_bindgroups_cache_sbuf_item(uint32_t id) {
|
||||
return _sg_wgpu_bindgroups_cache_item(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_STORAGEBUFFER, id);
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_init_bindgroups_cache_key(_sg_wgpu_bindgroups_cache_key_t* key, const _sg_bindings_t* bnd) {
|
||||
SOKOL_ASSERT(bnd);
|
||||
SOKOL_ASSERT(bnd->pip);
|
||||
|
@ -14016,38 +14080,39 @@ _SOKOL_PRIVATE void _sg_wgpu_init_bindgroups_cache_key(_sg_wgpu_bindgroups_cache
|
|||
SOKOL_ASSERT(bnd->num_fs_sbufs <= SG_MAX_SHADERSTAGE_STORAGEBUFFERS);
|
||||
|
||||
_sg_clear(key->items, sizeof(key->items));
|
||||
key->items[0] = bnd->pip->slot.id;
|
||||
const int vs_imgs_offset = 1;
|
||||
const int vs_smps_offset = vs_imgs_offset + SG_MAX_SHADERSTAGE_IMAGES;
|
||||
const int vs_sbufs_offset = vs_smps_offset + SG_MAX_SHADERSTAGE_SAMPLERS;
|
||||
const int fs_imgs_offset = vs_sbufs_offset + SG_MAX_SHADERSTAGE_STORAGEBUFFERS;
|
||||
const int fs_smps_offset = fs_imgs_offset + SG_MAX_SHADERSTAGE_IMAGES;
|
||||
const int fs_sbufs_offset = fs_smps_offset + SG_MAX_SHADERSTAGE_SAMPLERS;
|
||||
SOKOL_ASSERT((fs_sbufs_offset + SG_MAX_SHADERSTAGE_STORAGEBUFFERS) == _SG_WGPU_BINDGROUPSCACHE_NUM_ITEMS);
|
||||
int item_idx = 0;
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_pip_item(bnd->pip->slot.id);
|
||||
for (int i = 0; i < bnd->num_vs_imgs; i++) {
|
||||
SOKOL_ASSERT(bnd->vs_imgs[i]);
|
||||
key->items[vs_imgs_offset + i] = bnd->vs_imgs[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_image_item(bnd->vs_imgs[i]->slot.id);
|
||||
}
|
||||
for (int i = 0; i < bnd->num_vs_smps; i++) {
|
||||
SOKOL_ASSERT(bnd->vs_smps[i]);
|
||||
key->items[vs_smps_offset + i] = bnd->vs_smps[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_sampler_item(bnd->vs_smps[i]->slot.id);
|
||||
}
|
||||
for (int i = 0; i < bnd->num_vs_sbufs; i++) {
|
||||
SOKOL_ASSERT(bnd->vs_sbufs[i]);
|
||||
key->items[vs_sbufs_offset + i] = bnd->vs_sbufs[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_sbuf_item(bnd->vs_sbufs[i]->slot.id);
|
||||
}
|
||||
for (int i = 0; i < bnd->num_fs_imgs; i++) {
|
||||
SOKOL_ASSERT(bnd->fs_imgs[i]);
|
||||
key->items[fs_imgs_offset + i] = bnd->fs_imgs[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_image_item(bnd->fs_imgs[i]->slot.id);
|
||||
}
|
||||
for (int i = 0; i < bnd->num_fs_smps; i++) {
|
||||
SOKOL_ASSERT(bnd->fs_smps[i]);
|
||||
key->items[fs_smps_offset + i] = bnd->fs_smps[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_sampler_item(bnd->fs_smps[i]->slot.id);
|
||||
}
|
||||
for (int i = 0; i < bnd->num_fs_sbufs; i++) {
|
||||
SOKOL_ASSERT(bnd->fs_sbufs[i]);
|
||||
key->items[fs_sbufs_offset + i] = bnd->fs_sbufs[i]->slot.id;
|
||||
SOKOL_ASSERT(item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS);
|
||||
key->items[item_idx++] = _sg_wgpu_bindgroups_cache_sbuf_item(bnd->fs_sbufs[i]->slot.id);
|
||||
}
|
||||
SOKOL_ASSERT(item_idx == (1 + bnd->num_vs_imgs + bnd->num_vs_smps + bnd->num_vs_sbufs + bnd->num_fs_imgs + bnd->num_fs_smps + bnd->num_fs_sbufs));
|
||||
key->hash = _sg_wgpu_hash(&key->items, (int)sizeof(key->items), 0x1234567887654321);
|
||||
}
|
||||
|
||||
|
@ -14199,6 +14264,33 @@ _SOKOL_PRIVATE uint32_t _sg_wgpu_bindgroups_cache_get(uint64_t hash) {
|
|||
return _sg.wgpu.bindgroups_cache.items[index].id;
|
||||
}
|
||||
|
||||
// called from wgpu resource destroy functions to also invalidate any
|
||||
// bindgroups cache slot and bindgroup referencing that resource
|
||||
_SOKOL_PRIVATE void _sg_wgpu_bindgroups_cache_invalidate(_sg_wgpu_bindgroups_cache_item_type_t type, uint32_t id) {
|
||||
const uint64_t key_item = _sg_wgpu_bindgroups_cache_item(type, id);
|
||||
SOKOL_ASSERT(_sg.wgpu.bindgroups_cache.items);
|
||||
for (uint32_t cache_item_idx = 0; cache_item_idx < _sg.wgpu.bindgroups_cache.num; cache_item_idx++) {
|
||||
const uint32_t bg_id = _sg.wgpu.bindgroups_cache.items[cache_item_idx].id;
|
||||
if (bg_id != SG_INVALID_ID) {
|
||||
_sg_wgpu_bindgroup_t* bg = _sg_wgpu_lookup_bindgroup(bg_id);
|
||||
SOKOL_ASSERT(bg && (bg->slot.state == SG_RESOURCESTATE_VALID));
|
||||
// check if resource is in bindgroup, if yes discard bindgroup and invalidate cache slot
|
||||
bool invalidate_cache_item = false;
|
||||
for (int key_item_idx = 0; key_item_idx < _SG_WGPU_BINDGROUPSCACHEKEY_NUM_ITEMS; key_item_idx++) {
|
||||
if (bg->key.items[key_item_idx] == key_item) {
|
||||
invalidate_cache_item = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (invalidate_cache_item) {
|
||||
_sg_wgpu_discard_bindgroup(bg); bg = 0;
|
||||
_sg_wgpu_bindgroups_cache_set(cache_item_idx, SG_INVALID_ID);
|
||||
_sg_stats_add(wgpu.bindings.num_bindgroup_cache_invalidates, 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_bindings_cache_clear(void) {
|
||||
memset(&_sg.wgpu.bindings_cache, 0, sizeof(_sg.wgpu.bindings_cache));
|
||||
}
|
||||
|
@ -14259,7 +14351,7 @@ _SOKOL_PRIVATE void _sg_wgpu_bindings_cache_bg_update(const _sg_wgpu_bindgroup_t
|
|||
}
|
||||
}
|
||||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_set_bindings_bindgroup(_sg_wgpu_bindgroup_t* bg) {
|
||||
_SOKOL_PRIVATE void _sg_wgpu_set_bindgroup(_sg_wgpu_bindgroup_t* bg) {
|
||||
if (_sg_wgpu_bindings_cache_bg_dirty(bg)) {
|
||||
_sg_wgpu_bindings_cache_bg_update(bg);
|
||||
_sg_stats_add(wgpu.bindings.num_set_bindgroup, 1);
|
||||
|
@ -14305,7 +14397,7 @@ _SOKOL_PRIVATE bool _sg_wgpu_apply_bindgroup(_sg_bindings_t* bnd) {
|
|||
_sg_wgpu_bindgroups_cache_set(key.hash, bg->slot.id);
|
||||
}
|
||||
if (bg && bg->slot.state == SG_RESOURCESTATE_VALID) {
|
||||
_sg_wgpu_set_bindings_bindgroup(bg);
|
||||
_sg_wgpu_set_bindgroup(bg);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
|
@ -14314,7 +14406,7 @@ _SOKOL_PRIVATE bool _sg_wgpu_apply_bindgroup(_sg_bindings_t* bnd) {
|
|||
_sg_wgpu_bindgroup_t* bg = _sg_wgpu_create_bindgroup(bnd);
|
||||
if (bg) {
|
||||
if (bg->slot.state == SG_RESOURCESTATE_VALID) {
|
||||
_sg_wgpu_set_bindings_bindgroup(bg);
|
||||
_sg_wgpu_set_bindgroup(bg);
|
||||
}
|
||||
_sg_wgpu_discard_bindgroup(bg);
|
||||
} else {
|
||||
|
@ -14322,7 +14414,7 @@ _SOKOL_PRIVATE bool _sg_wgpu_apply_bindgroup(_sg_bindings_t* bnd) {
|
|||
}
|
||||
}
|
||||
} else {
|
||||
_sg_wgpu_set_bindings_bindgroup(0);
|
||||
_sg_wgpu_set_bindgroup(0);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@ -14455,8 +14547,10 @@ _SOKOL_PRIVATE sg_resource_state _sg_wgpu_create_buffer(_sg_buffer_t* buf, const
|
|||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_discard_buffer(_sg_buffer_t* buf) {
|
||||
SOKOL_ASSERT(buf);
|
||||
if (buf->cmn.type == SG_BUFFERTYPE_STORAGEBUFFER) {
|
||||
_sg_wgpu_bindgroups_cache_invalidate(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_STORAGEBUFFER, buf->slot.id);
|
||||
}
|
||||
if (buf->wgpu.buf) {
|
||||
wgpuBufferDestroy(buf->wgpu.buf);
|
||||
wgpuBufferRelease(buf->wgpu.buf);
|
||||
}
|
||||
}
|
||||
|
@ -14592,12 +14686,12 @@ _SOKOL_PRIVATE sg_resource_state _sg_wgpu_create_image(_sg_image_t* img, const s
|
|||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_discard_image(_sg_image_t* img) {
|
||||
SOKOL_ASSERT(img);
|
||||
_sg_wgpu_bindgroups_cache_invalidate(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_IMAGE, img->slot.id);
|
||||
if (img->wgpu.view) {
|
||||
wgpuTextureViewRelease(img->wgpu.view);
|
||||
img->wgpu.view = 0;
|
||||
}
|
||||
if (img->wgpu.tex) {
|
||||
wgpuTextureDestroy(img->wgpu.tex);
|
||||
wgpuTextureRelease(img->wgpu.tex);
|
||||
img->wgpu.tex = 0;
|
||||
}
|
||||
|
@ -14638,6 +14732,7 @@ _SOKOL_PRIVATE sg_resource_state _sg_wgpu_create_sampler(_sg_sampler_t* smp, con
|
|||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_discard_sampler(_sg_sampler_t* smp) {
|
||||
SOKOL_ASSERT(smp);
|
||||
_sg_wgpu_bindgroups_cache_invalidate(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_SAMPLER, smp->slot.id);
|
||||
if (smp->wgpu.smp) {
|
||||
wgpuSamplerRelease(smp->wgpu.smp);
|
||||
smp->wgpu.smp = 0;
|
||||
|
@ -14875,6 +14970,7 @@ _SOKOL_PRIVATE sg_resource_state _sg_wgpu_create_pipeline(_sg_pipeline_t* pip, _
|
|||
|
||||
_SOKOL_PRIVATE void _sg_wgpu_discard_pipeline(_sg_pipeline_t* pip) {
|
||||
SOKOL_ASSERT(pip);
|
||||
_sg_wgpu_bindgroups_cache_invalidate(_SG_WGPU_BINDGROUPSCACHEITEMTYPE_PIPELINE, pip->slot.id);
|
||||
if (pip == _sg.wgpu.cur_pipeline) {
|
||||
_sg.wgpu.cur_pipeline = 0;
|
||||
_sg.wgpu.cur_pipeline_id.id = SG_INVALID_ID;
|
||||
|
@ -16219,8 +16315,6 @@ _SOKOL_PRIVATE bool _sg_validate_sampler_desc(const sg_sampler_desc* desc) {
|
|||
_sg_validate_begin();
|
||||
_SG_VALIDATE(desc->_start_canary == 0, VALIDATE_SAMPLERDESC_CANARY);
|
||||
_SG_VALIDATE(desc->_end_canary == 0, VALIDATE_SAMPLERDESC_CANARY);
|
||||
_SG_VALIDATE(desc->min_filter != SG_FILTER_NONE, VALIDATE_SAMPLERDESC_MINFILTER_NONE);
|
||||
_SG_VALIDATE(desc->mag_filter != SG_FILTER_NONE, VALIDATE_SAMPLERDESC_MAGFILTER_NONE);
|
||||
// restriction from WebGPU: when anisotropy > 1, all filters must be linear
|
||||
if (desc->max_anisotropy > 1) {
|
||||
_SG_VALIDATE((desc->min_filter == SG_FILTER_LINEAR)
|
||||
|
@ -17040,7 +17134,7 @@ _SOKOL_PRIVATE sg_sampler_desc _sg_sampler_desc_defaults(const sg_sampler_desc*
|
|||
sg_sampler_desc def = *desc;
|
||||
def.min_filter = _sg_def(def.min_filter, SG_FILTER_NEAREST);
|
||||
def.mag_filter = _sg_def(def.mag_filter, SG_FILTER_NEAREST);
|
||||
def.mipmap_filter = _sg_def(def.mipmap_filter, SG_FILTER_NONE);
|
||||
def.mipmap_filter = _sg_def(def.mipmap_filter, SG_FILTER_NEAREST);
|
||||
def.wrap_u = _sg_def(def.wrap_u, SG_WRAP_REPEAT);
|
||||
def.wrap_v = _sg_def(def.wrap_v, SG_WRAP_REPEAT);
|
||||
def.wrap_w = _sg_def(def.wrap_w, SG_WRAP_REPEAT);
|
||||
|
|
|
@ -1661,7 +1661,6 @@ static int _sfons_render_create(void* user_ptr, int width, int height) {
|
|||
_sfons_clear(&smp_desc, sizeof(smp_desc));
|
||||
smp_desc.min_filter = SG_FILTER_LINEAR;
|
||||
smp_desc.mag_filter = SG_FILTER_LINEAR;
|
||||
smp_desc.mipmap_filter = SG_FILTER_NONE;
|
||||
sfons->smp = sg_make_sampler(&smp_desc);
|
||||
}
|
||||
|
||||
|
|
|
@ -1287,7 +1287,6 @@ _SOKOL_PRIVATE const char* _sgimgui_pixelformat_string(sg_pixel_format fmt) {
|
|||
|
||||
_SOKOL_PRIVATE const char* _sgimgui_filter_string(sg_filter f) {
|
||||
switch (f) {
|
||||
case SG_FILTER_NONE: return "SG_FILTER_NONE";
|
||||
case SG_FILTER_NEAREST: return "SG_FILTER_NEAREST";
|
||||
case SG_FILTER_LINEAR: return "SG_FILTER_LINEAR";
|
||||
default: return "???";
|
||||
|
@ -4287,7 +4286,7 @@ _SOKOL_PRIVATE void _sgimgui_draw_frame_stats_panel(sgimgui_t* ctx) {
|
|||
ImGuiTableFlags_SizingFixedFit |
|
||||
ImGuiTableFlags_Borders;
|
||||
if (igBeginTable("##frame_stats_table", 2, flags, IMVEC2(0, 0), 0)) {
|
||||
igTableSetupScrollFreeze(0, 2);
|
||||
igTableSetupScrollFreeze(0, 1);
|
||||
igTableSetupColumn("key", ImGuiTableColumnFlags_None, 0, 0);
|
||||
igTableSetupColumn("value", ImGuiTableColumnFlags_None, 0, 0);
|
||||
igTableHeadersRow();
|
||||
|
@ -4335,6 +4334,7 @@ _SOKOL_PRIVATE void _sgimgui_draw_frame_stats_panel(sgimgui_t* ctx) {
|
|||
_sgimgui_frame_stats(wgpu.bindings.num_bindgroup_cache_hits);
|
||||
_sgimgui_frame_stats(wgpu.bindings.num_bindgroup_cache_misses);
|
||||
_sgimgui_frame_stats(wgpu.bindings.num_bindgroup_cache_collisions);
|
||||
_sgimgui_frame_stats(wgpu.bindings.num_bindgroup_cache_invalidates);
|
||||
_sgimgui_frame_stats(wgpu.bindings.num_bindgroup_cache_hash_vs_key_mismatch);
|
||||
break;
|
||||
case SG_BACKEND_METAL_MACOS:
|
||||
|
|
140
source/engine/thirdparty/sokol/util/sokol_gl.h
vendored
140
source/engine/thirdparty/sokol/util/sokol_gl.h
vendored
|
@ -372,8 +372,8 @@
|
|||
the last call to sgl_draw() through sokol-gfx, and will 'rewind' the internal
|
||||
vertex-, uniform- and command-buffers.
|
||||
|
||||
--- each sokol-gl context tracks an internal error code, to query the
|
||||
current error code for the currently active context call:
|
||||
--- each sokol-gl context tracks internal error states which can
|
||||
be obtains via:
|
||||
|
||||
sgl_error_t sgl_error()
|
||||
|
||||
|
@ -381,18 +381,28 @@
|
|||
|
||||
sgl_error_t sgl_context_error(ctx);
|
||||
|
||||
...which can return the following error codes:
|
||||
...this returns a struct with the following booleans:
|
||||
|
||||
SGL_NO_ERROR - all OK, no error occurred since last sgl_draw()
|
||||
SGL_ERROR_VERTICES_FULL - internal vertex buffer is full (checked in sgl_end())
|
||||
SGL_ERROR_UNIFORMS_FULL - the internal uniforms buffer is full (checked in sgl_end())
|
||||
SGL_ERROR_COMMANDS_FULL - the internal command buffer is full (checked in sgl_end())
|
||||
SGL_ERROR_STACK_OVERFLOW - matrix- or pipeline-stack overflow
|
||||
SGL_ERROR_STACK_UNDERFLOW - matrix- or pipeline-stack underflow
|
||||
SGL_ERROR_NO_CONTEXT - the active context no longer exists
|
||||
.any - true if any of the below errors is true
|
||||
.vertices_full - internal vertex buffer is full (checked in sgl_end())
|
||||
.uniforms_full - the internal uniforms buffer is full (checked in sgl_end())
|
||||
.commands_full - the internal command buffer is full (checked in sgl_end())
|
||||
.stack_overflow - matrix- or pipeline-stack overflow
|
||||
.stack_underflow - matrix- or pipeline-stack underflow
|
||||
.no_context - the active context no longer exists
|
||||
|
||||
...if sokol-gl is in an error-state, sgl_draw() will skip any rendering,
|
||||
and reset the error code to SGL_NO_ERROR.
|
||||
...depending on the above error state, sgl_draw() may skip rendering
|
||||
completely, or only draw partial geometry
|
||||
|
||||
--- you can get the number of recorded vertices and draw commands in the current
|
||||
frame and active sokol-gl context via:
|
||||
|
||||
int sgl_num_vertices()
|
||||
int sgl_num_commands()
|
||||
|
||||
...this allows you to check whether the vertex or command pools are running
|
||||
full before the overflow actually happens (in this case you could also
|
||||
check the error booleans in the result of sgl_error()).
|
||||
|
||||
RENDER LAYERS
|
||||
=============
|
||||
|
@ -762,14 +772,14 @@ typedef struct sgl_context { uint32_t id; } sgl_context;
|
|||
Errors are reset each frame after calling sgl_draw(),
|
||||
get the last error code with sgl_error()
|
||||
*/
|
||||
typedef enum sgl_error_t {
|
||||
SGL_NO_ERROR = 0,
|
||||
SGL_ERROR_VERTICES_FULL,
|
||||
SGL_ERROR_UNIFORMS_FULL,
|
||||
SGL_ERROR_COMMANDS_FULL,
|
||||
SGL_ERROR_STACK_OVERFLOW,
|
||||
SGL_ERROR_STACK_UNDERFLOW,
|
||||
SGL_ERROR_NO_CONTEXT,
|
||||
typedef struct sgl_error_t {
|
||||
bool any;
|
||||
bool vertices_full;
|
||||
bool uniforms_full;
|
||||
bool commands_full;
|
||||
bool stack_overflow;
|
||||
bool stack_underflow;
|
||||
bool no_context;
|
||||
} sgl_error_t;
|
||||
|
||||
/*
|
||||
|
@ -832,6 +842,10 @@ SOKOL_GL_API_DECL void sgl_set_context(sgl_context ctx);
|
|||
SOKOL_GL_API_DECL sgl_context sgl_get_context(void);
|
||||
SOKOL_GL_API_DECL sgl_context sgl_default_context(void);
|
||||
|
||||
/* get information about recorded vertices and commands in current context */
|
||||
SOKOL_GL_API_DECL int sgl_num_vertices(void);
|
||||
SOKOL_GL_API_DECL int sgl_num_commands(void);
|
||||
|
||||
/* draw recorded commands (call inside a sokol-gfx render pass) */
|
||||
SOKOL_GL_API_DECL void sgl_draw(void);
|
||||
SOKOL_GL_API_DECL void sgl_context_draw(sgl_context ctx);
|
||||
|
@ -2342,7 +2356,7 @@ typedef struct {
|
|||
|
||||
/* state tracking */
|
||||
int base_vertex;
|
||||
int vtx_count; /* number of times vtx function has been called, used for non-triangle primitives */
|
||||
int quad_vtx_count; /* number of times vtx function has been called, used for non-triangle primitives */
|
||||
sgl_error_t error;
|
||||
bool in_begin;
|
||||
int layer_id;
|
||||
|
@ -2903,10 +2917,24 @@ static void _sgl_destroy_context(sgl_context ctx_id) {
|
|||
// ██ ██ ██ ███████ ██████
|
||||
//
|
||||
// >>misc
|
||||
|
||||
static sgl_error_t _sgl_error_defaults(void) {
|
||||
sgl_error_t defaults = {0};
|
||||
return defaults;
|
||||
}
|
||||
|
||||
static int _sgl_num_vertices(_sgl_context_t* ctx) {
|
||||
return ctx->vertices.next;
|
||||
}
|
||||
|
||||
static int _sgl_num_commands(_sgl_context_t* ctx) {
|
||||
return ctx->commands.next;
|
||||
}
|
||||
|
||||
static void _sgl_begin(_sgl_context_t* ctx, _sgl_primitive_type_t mode) {
|
||||
ctx->in_begin = true;
|
||||
ctx->base_vertex = ctx->vertices.next;
|
||||
ctx->vtx_count = 0;
|
||||
ctx->quad_vtx_count = 0;
|
||||
ctx->cur_prim_type = mode;
|
||||
}
|
||||
|
||||
|
@ -2916,7 +2944,7 @@ static void _sgl_rewind(_sgl_context_t* ctx) {
|
|||
ctx->uniforms.next = 0;
|
||||
ctx->commands.next = 0;
|
||||
ctx->base_vertex = 0;
|
||||
ctx->error = SGL_NO_ERROR;
|
||||
ctx->error = _sgl_error_defaults();
|
||||
ctx->layer_id = 0;
|
||||
ctx->matrix_dirty = true;
|
||||
}
|
||||
|
@ -2938,7 +2966,8 @@ static _sgl_vertex_t* _sgl_next_vertex(_sgl_context_t* ctx) {
|
|||
if (ctx->vertices.next < ctx->vertices.cap) {
|
||||
return &ctx->vertices.ptr[ctx->vertices.next++];
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_VERTICES_FULL;
|
||||
ctx->error.vertices_full = true;
|
||||
ctx->error.any = true;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -2947,7 +2976,8 @@ static _sgl_uniform_t* _sgl_next_uniform(_sgl_context_t* ctx) {
|
|||
if (ctx->uniforms.next < ctx->uniforms.cap) {
|
||||
return &ctx->uniforms.ptr[ctx->uniforms.next++];
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_UNIFORMS_FULL;
|
||||
ctx->error.uniforms_full = true;
|
||||
ctx->error.any = true;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -2964,7 +2994,8 @@ static _sgl_command_t* _sgl_next_command(_sgl_context_t* ctx) {
|
|||
if (ctx->commands.next < ctx->commands.cap) {
|
||||
return &ctx->commands.ptr[ctx->commands.next++];
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_COMMANDS_FULL;
|
||||
ctx->error.commands_full = true;
|
||||
ctx->error.any = true;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
@ -2991,7 +3022,7 @@ static void _sgl_vtx(_sgl_context_t* ctx, float x, float y, float z, float u, fl
|
|||
SOKOL_ASSERT(ctx->in_begin);
|
||||
_sgl_vertex_t* vtx;
|
||||
/* handle non-native primitive types */
|
||||
if ((ctx->cur_prim_type == SGL_PRIMITIVETYPE_QUADS) && ((ctx->vtx_count & 3) == 3)) {
|
||||
if ((ctx->cur_prim_type == SGL_PRIMITIVETYPE_QUADS) && ((ctx->quad_vtx_count & 3) == 3)) {
|
||||
/* for quads, before writing the last quad vertex, reuse
|
||||
the first and third vertex to start the second triangle in the quad
|
||||
*/
|
||||
|
@ -3007,7 +3038,7 @@ static void _sgl_vtx(_sgl_context_t* ctx, float x, float y, float z, float u, fl
|
|||
vtx->rgba = rgba;
|
||||
vtx->psize = ctx->point_size;
|
||||
}
|
||||
ctx->vtx_count++;
|
||||
ctx->quad_vtx_count++;
|
||||
}
|
||||
|
||||
static void _sgl_identity(_sgl_matrix_t* m) {
|
||||
|
@ -3342,7 +3373,7 @@ static bool _sgl_is_default_context(sgl_context ctx_id) {
|
|||
|
||||
static void _sgl_draw(_sgl_context_t* ctx, int layer_id) {
|
||||
SOKOL_ASSERT(ctx);
|
||||
if ((ctx->error == SGL_NO_ERROR) && (ctx->vertices.next > 0) && (ctx->commands.next > 0)) {
|
||||
if ((ctx->vertices.next > 0) && (ctx->commands.next > 0)) {
|
||||
sg_push_debug_group("sokol-gl");
|
||||
|
||||
uint32_t cur_pip_id = SG_INVALID_ID;
|
||||
|
@ -3356,6 +3387,8 @@ static void _sgl_draw(_sgl_context_t* ctx, int layer_id) {
|
|||
sg_update_buffer(ctx->vbuf, &range);
|
||||
}
|
||||
|
||||
// render all successfully recorded commands (this may be less than the
|
||||
// issued commands if we're in an error state)
|
||||
for (int i = 0; i < ctx->commands.next; i++) {
|
||||
const _sgl_command_t* cmd = &ctx->commands.ptr[i];
|
||||
if (cmd->layer_id != layer_id) {
|
||||
|
@ -3463,7 +3496,10 @@ SOKOL_API_IMPL sgl_error_t sgl_error(void) {
|
|||
if (ctx) {
|
||||
return ctx->error;
|
||||
} else {
|
||||
return SGL_ERROR_NO_CONTEXT;
|
||||
sgl_error_t err = _sgl_error_defaults();
|
||||
err.no_context = true;
|
||||
err.any = true;
|
||||
return err;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3472,7 +3508,10 @@ SOKOL_API_IMPL sgl_error_t sgl_context_error(sgl_context ctx_id) {
|
|||
if (ctx) {
|
||||
return ctx->error;
|
||||
} else {
|
||||
return SGL_ERROR_NO_CONTEXT;
|
||||
sgl_error_t err = _sgl_error_defaults();
|
||||
err.no_context = true;
|
||||
err.any = true;
|
||||
return err;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3521,6 +3560,26 @@ SOKOL_API_IMPL sgl_context sgl_default_context(void) {
|
|||
return SGL_DEFAULT_CONTEXT;
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL int sgl_num_vertices(void) {
|
||||
SOKOL_ASSERT(_SGL_INIT_COOKIE == _sgl.init_cookie);
|
||||
_sgl_context_t* ctx = _sgl.cur_ctx;
|
||||
if (ctx) {
|
||||
return _sgl_num_vertices(ctx);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL int sgl_num_commands(void) {
|
||||
SOKOL_ASSERT(_SGL_INIT_COOKIE == _sgl.init_cookie);
|
||||
_sgl_context_t* ctx = _sgl.cur_ctx;
|
||||
if (ctx) {
|
||||
return _sgl_num_commands(ctx);
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
SOKOL_API_IMPL sgl_pipeline sgl_make_pipeline(const sg_pipeline_desc* desc) {
|
||||
SOKOL_ASSERT(_SGL_INIT_COOKIE == _sgl.init_cookie);
|
||||
_sgl_context_t* ctx = _sgl.cur_ctx;
|
||||
|
@ -3576,7 +3635,8 @@ SOKOL_API_IMPL void sgl_push_pipeline(void) {
|
|||
ctx->pip_tos++;
|
||||
ctx->pip_stack[ctx->pip_tos] = ctx->pip_stack[ctx->pip_tos-1];
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_STACK_OVERFLOW;
|
||||
ctx->error.stack_overflow = true;
|
||||
ctx->error.any = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3589,7 +3649,8 @@ SOKOL_API_IMPL void sgl_pop_pipeline(void) {
|
|||
if (ctx->pip_tos > 0) {
|
||||
ctx->pip_tos--;
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_STACK_UNDERFLOW;
|
||||
ctx->error.stack_underflow = true;
|
||||
ctx->error.any = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3778,6 +3839,7 @@ SOKOL_API_IMPL void sgl_end(void) {
|
|||
SOKOL_ASSERT(ctx->in_begin);
|
||||
SOKOL_ASSERT(ctx->vertices.next >= ctx->base_vertex);
|
||||
ctx->in_begin = false;
|
||||
|
||||
bool matrix_dirty = ctx->matrix_dirty;
|
||||
if (matrix_dirty) {
|
||||
ctx->matrix_dirty = false;
|
||||
|
@ -3787,6 +3849,12 @@ SOKOL_API_IMPL void sgl_end(void) {
|
|||
uni->tm = *_sgl_matrix_texture(ctx);
|
||||
}
|
||||
}
|
||||
|
||||
// don't record any new commands when we're in an error state
|
||||
if (ctx->error.any) {
|
||||
return;
|
||||
}
|
||||
|
||||
// check if command can be merged with current command
|
||||
sg_pipeline pip = _sgl_get_pipeline(ctx->pip_stack[ctx->pip_tos], ctx->cur_prim_type);
|
||||
sg_image img = ctx->texturing_enabled ? ctx->cur_img : _sgl.def_img;
|
||||
|
@ -4205,7 +4273,8 @@ SOKOL_GL_API_DECL void sgl_push_matrix(void) {
|
|||
_sgl_matrix_t* dst = _sgl_matrix(ctx);
|
||||
*dst = *src;
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_STACK_OVERFLOW;
|
||||
ctx->error.stack_overflow = true;
|
||||
ctx->error.any = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4220,7 +4289,8 @@ SOKOL_GL_API_DECL void sgl_pop_matrix(void) {
|
|||
if (ctx->matrix_tos[ctx->cur_matrix_mode] > 0) {
|
||||
ctx->matrix_tos[ctx->cur_matrix_mode]--;
|
||||
} else {
|
||||
ctx->error = SGL_ERROR_STACK_UNDERFLOW;
|
||||
ctx->error.stack_underflow = true;
|
||||
ctx->error.any = true;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1844,13 +1844,13 @@ static const char* _simgui_fs_source_dummy = "";
|
|||
#endif
|
||||
|
||||
#if !defined(SOKOL_IMGUI_NO_SOKOL_APP)
|
||||
static void _simgui_set_clipboard(void* user_data, const char* text) {
|
||||
(void)user_data;
|
||||
static void _simgui_set_clipboard(ImGuiContext* ctx, const char* text) {
|
||||
(void)ctx;
|
||||
sapp_set_clipboard_string(text);
|
||||
}
|
||||
|
||||
static const char* _simgui_get_clipboard(void* user_data) {
|
||||
(void)user_data;
|
||||
static const char* _simgui_get_clipboard(ImGuiContext* ctx) {
|
||||
(void)ctx;
|
||||
return sapp_get_clipboard_string();
|
||||
}
|
||||
#endif
|
||||
|
@ -2200,6 +2200,7 @@ SOKOL_API_IMPL void simgui_setup(const simgui_desc_t* desc) {
|
|||
ImGui::CreateContext();
|
||||
ImGui::StyleColorsDark();
|
||||
ImGuiIO* io = &ImGui::GetIO();
|
||||
ImGuiPlatformIO* pio = &ImGui::GetPlatformIO();
|
||||
if (!_simgui.desc.no_default_font) {
|
||||
io->Fonts->AddFontDefault();
|
||||
}
|
||||
|
@ -2207,6 +2208,7 @@ SOKOL_API_IMPL void simgui_setup(const simgui_desc_t* desc) {
|
|||
igCreateContext(NULL);
|
||||
igStyleColorsDark(igGetStyle());
|
||||
ImGuiIO* io = igGetIO();
|
||||
ImGuiPlatformIO* pio = igGetPlatformIO();
|
||||
if (!_simgui.desc.no_default_font) {
|
||||
ImFontAtlas_AddFontDefault(io->Fonts, NULL);
|
||||
}
|
||||
|
@ -2218,8 +2220,8 @@ SOKOL_API_IMPL void simgui_setup(const simgui_desc_t* desc) {
|
|||
if (!_simgui.desc.disable_set_mouse_cursor) {
|
||||
io->BackendFlags |= ImGuiBackendFlags_HasMouseCursors;
|
||||
}
|
||||
io->SetClipboardTextFn = _simgui_set_clipboard;
|
||||
io->GetClipboardTextFn = _simgui_get_clipboard;
|
||||
pio->Platform_SetClipboardTextFn = _simgui_set_clipboard;
|
||||
pio->Platform_GetClipboardTextFn = _simgui_get_clipboard;
|
||||
#endif
|
||||
io->ConfigWindowsResizeFromEdges = !_simgui.desc.disable_windows_resize_from_edges;
|
||||
|
||||
|
@ -2400,7 +2402,6 @@ SOKOL_API_IMPL void simgui_create_fonts_texture(const simgui_font_tex_desc_t* de
|
|||
font_smp_desc.wrap_v = SG_WRAP_CLAMP_TO_EDGE;
|
||||
font_smp_desc.min_filter = desc->min_filter;
|
||||
font_smp_desc.mag_filter = desc->mag_filter;
|
||||
font_smp_desc.mipmap_filter = SG_FILTER_NONE;
|
||||
font_smp_desc.label = "sokol-imgui-font-sampler";
|
||||
_simgui.font_smp = sg_make_sampler(&font_smp_desc);
|
||||
|
||||
|
|
|
@ -236,7 +236,7 @@
|
|||
.overrides = {
|
||||
.min_filter = SG_FILTER_NEAREST,
|
||||
.mag_filter = SG_FILTER_NEAREST,
|
||||
.mipmap_filter = SG_FILTER_NONE,
|
||||
.mipmap_filter = SG_FILTER_NEAREST,
|
||||
.wrap_u = SG_WRAP_MIRROR,
|
||||
.wrap_v = SG_WRAP_MIRROR,
|
||||
.premul_alpha_enabled = ...,
|
||||
|
@ -4573,15 +4573,19 @@ static sg_filter _sspine_as_sampler_filter(spAtlasFilter filter) {
|
|||
|
||||
static sg_filter _sspine_as_sampler_mipmap_filter(spAtlasFilter filter) {
|
||||
switch (filter) {
|
||||
case SP_ATLAS_UNKNOWN_FILTER: return _SG_FILTER_DEFAULT;
|
||||
case SP_ATLAS_NEAREST: return SG_FILTER_NONE;
|
||||
case SP_ATLAS_LINEAR: return SG_FILTER_NONE;
|
||||
case SP_ATLAS_MIPMAP: return SG_FILTER_NEAREST;
|
||||
case SP_ATLAS_MIPMAP_NEAREST_NEAREST: return SG_FILTER_NEAREST;
|
||||
case SP_ATLAS_MIPMAP_LINEAR_NEAREST: return SG_FILTER_NEAREST;
|
||||
case SP_ATLAS_MIPMAP_NEAREST_LINEAR: return SG_FILTER_LINEAR;
|
||||
case SP_ATLAS_MIPMAP_LINEAR_LINEAR: return SG_FILTER_LINEAR;
|
||||
default: return SG_FILTER_NEAREST;
|
||||
case SP_ATLAS_UNKNOWN_FILTER:
|
||||
return _SG_FILTER_DEFAULT;
|
||||
case SP_ATLAS_NEAREST:
|
||||
case SP_ATLAS_LINEAR:
|
||||
case SP_ATLAS_MIPMAP:
|
||||
case SP_ATLAS_MIPMAP_NEAREST_NEAREST:
|
||||
case SP_ATLAS_MIPMAP_LINEAR_NEAREST:
|
||||
return SG_FILTER_NEAREST;
|
||||
case SP_ATLAS_MIPMAP_NEAREST_LINEAR:
|
||||
case SP_ATLAS_MIPMAP_LINEAR_LINEAR:
|
||||
return SG_FILTER_LINEAR;
|
||||
default:
|
||||
return SG_FILTER_NEAREST;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue