From 7abe46380134d09984ccefd4543a0fddeff9063a Mon Sep 17 00:00:00 2001 From: ocornut Date: Thu, 26 Nov 2020 22:17:55 +0100 Subject: [PATCH] ImStrv: rework toward ensuring End is always set to constant can be compile time calculated --- imgui.cpp | 15 ++------------- imgui.h | 19 +++++++++---------- imgui_draw.cpp | 6 ------ imgui_widgets.cpp | 4 ---- 4 files changed, 11 insertions(+), 33 deletions(-) diff --git a/imgui.cpp b/imgui.cpp index e033d4c4..c7cc72c8 100644 --- a/imgui.cpp +++ b/imgui.cpp @@ -1632,7 +1632,6 @@ const char* ImStristr(const char* haystack, const char* haystack_end, const char const char* ImStrstr(ImStrv haystack, ImStrv needle) { - IM_IMSTR_ENSURE_HAS_END(needle); const char un0 = (char)*needle.Begin; while ((!haystack.End && *haystack.Begin) || (haystack.End && haystack.Begin < haystack.End)) { @@ -2361,8 +2360,7 @@ bool ImGuiTextFilter::PassFilter(ImStrv text) const if (Filters.empty()) return true; - IM_IMSTR_ENSURE_HAS_END(text); - if (text.Empty()) + if (text.Empty()) // FIXME-IMSTR text.Begin = text.End = ""; for (int i = 0; i != Filters.Size; i++) @@ -3032,14 +3030,9 @@ void ImGui::RenderText(ImVec2 pos, ImStrv text, bool hide_text_after_hash) // Hide anything after a '##' string const char* text_display_end; if (hide_text_after_hash) - { text_display_end = FindRenderedTextEnd(text); - } else - { - IM_IMSTR_ENSURE_HAS_END(text); text_display_end = text.End; - } if (text.Begin != text_display_end) { @@ -3053,7 +3046,6 @@ void ImGui::RenderTextWrapped(ImVec2 pos, ImStrv text, float wrap_width) { ImGuiContext& g = *GImGui; ImGuiWindow* window = g.CurrentWindow; - IM_IMSTR_ENSURE_HAS_END(text); if (text.Begin != text.End) { @@ -3313,7 +3305,6 @@ ImGuiID ImGuiWindow::GetID(ImStrv str) ImGuiID id = ImHashStr(str, seed); ImGui::KeepAliveID(id); ImGuiContext& g = *GImGui; - IM_IMSTR_ENSURE_HAS_END(str); if (g.DebugHookIdInfo == id) ImGui::DebugHookIdInfo(id, ImGuiDataType_String, str.Begin, str.End); return id; @@ -3344,8 +3335,7 @@ ImGuiID ImGuiWindow::GetID(int n) ImGuiID ImGuiWindow::GetIDNoKeepAlive(ImStrv str) { ImGuiID seed = IDStack.back(); - IM_IMSTR_ENSURE_HAS_END(str); - ImGuiID id = ImHashStr(str.Begin, str.End - str.Begin, seed); + ImGuiID id = ImHashStr(str, seed); ImGuiContext& g = *GImGui; if (g.DebugHookIdInfo == id) ImGui::DebugHookIdInfo(id, ImGuiDataType_String, str.Begin, str.End); @@ -5009,7 +4999,6 @@ ImVec2 ImGui::CalcTextSize(ImStrv text, bool hide_text_after_double_hash, float { ImGuiContext& g = *GImGui; - IM_IMSTR_ENSURE_HAS_END(text); if (hide_text_after_double_hash) text.End = FindRenderedTextEnd(text); // Hide anything after a '##' string diff --git a/imgui.h b/imgui.h index 93986aca..a2b89ace 100644 --- a/imgui.h +++ b/imgui.h @@ -269,8 +269,7 @@ struct ImVec4 #endif }; -#define IM_IMSTR_LENGTH(s) (s.Begin ? (s.End ? (size_t)(s.End - s.Begin) : strlen(s.Begin)) : 0) -#define IM_IMSTR_ENSURE_HAS_END(s) if (s.End == NULL) s.End = s.Begin + strlen(s.Begin) +#define IM_IMSTR_LENGTH(s) (size_t)(s.End - s.Begin) // String view class. #define IMGUI_HAS_IMSTR @@ -278,11 +277,11 @@ struct ImStrv { const char* Begin; const char* End; - ImStrv() { Begin = End = NULL; } - ImStrv(const char* b) { Begin = b; End = NULL; } - ImStrv(const char* b, const char* e) { Begin = b; End = e; } - ImStrv(const char* b, size_t size) { Begin = b; End = b + size; } - bool Empty() const { return Begin == NULL || Begin == End || Begin[0] == 0; } + ImStrv() { Begin = End = NULL; } + ImStrv(const char* b) { Begin = b; End = b ? b + strlen(b) : NULL; } + ImStrv(const char* b, const char* e){ Begin = b; End = e ? e : b + strlen(b); } + ImStrv(const char* b, size_t size) { Begin = b; End = b + size; } + bool Empty() const { return Begin == End || Begin[0] == 0; } // FIXME: Ambiguous // void EnsureHasEnd() { if (End == NULL) End = Begin + Length(); } // size_t Length() const // { @@ -301,10 +300,10 @@ struct ImStrv return memcmp(Begin, other.Begin, len) == 0; return false; } - operator bool() const { return Begin != NULL; } - char operator[](int index) const { return Begin[index]; } + inline operator bool() const { return Begin != NULL; } + inline char operator[](int index) const { return Begin[index]; } #ifdef IM_IMSTR_CLASS_EXTRA - IM_IMSTR_CLASS_EXTRA // Define additional constructors and implicit cast operators in imconfig.h to convert back and forth between your math types and ImStrv. + IM_IMSTR_CLASS_EXTRA // Define additional constructors and implicit cast operators in imconfig.h to convert back and forth between your string types and ImStrv. #endif }; diff --git a/imgui_draw.cpp b/imgui_draw.cpp index 8912fe36..c1020099 100644 --- a/imgui_draw.cpp +++ b/imgui_draw.cpp @@ -1578,7 +1578,6 @@ void ImDrawList::AddText(const ImFont* font, float font_size, const ImVec2& pos, if ((col & IM_COL32_A_MASK) == 0) return; - IM_IMSTR_ENSURE_HAS_END(text); if (text.Empty()) return; @@ -3345,7 +3344,6 @@ const char* ImFont::CalcWordWrapPositionA(float scale, ImStrv text, float wrap_w // Cut words that cannot possibly fit within one line. // e.g.: "The tropical fish" with ~5 characters worth of width --> "The tr" "opical" "fish" - IM_IMSTR_ENSURE_HAS_END(text); float line_width = 0.0f; float word_width = 0.0f; @@ -3431,8 +3429,6 @@ const char* ImFont::CalcWordWrapPositionA(float scale, ImStrv text, float wrap_w ImVec2 ImFont::CalcTextSizeA(float size, float max_width, float wrap_width, ImStrv text, const char** remaining) const { - IM_IMSTR_ENSURE_HAS_END(text); - const float line_height = size; const float scale = size / FontSize; @@ -3540,8 +3536,6 @@ void ImFont::RenderChar(ImDrawList* draw_list, float size, ImVec2 pos, ImU32 col // Note: as with every ImDrawList drawing function, this expects that the font atlas texture is bound. void ImFont::RenderText(ImDrawList* draw_list, float size, ImVec2 pos, ImU32 col, const ImVec4& clip_rect, ImStrv text, float wrap_width, bool cpu_fine_clip) const { - IM_IMSTR_ENSURE_HAS_END(text); // ImGui:: functions generally already provides a valid text_end, so this is merely to handle direct calls. - // Align to be pixel perfect pos.x = IM_FLOOR(pos.x); pos.y = IM_FLOOR(pos.y); diff --git a/imgui_widgets.cpp b/imgui_widgets.cpp index 1dd71be6..d07b390e 100644 --- a/imgui_widgets.cpp +++ b/imgui_widgets.cpp @@ -155,8 +155,6 @@ void ImGui::TextEx(ImStrv text, ImGuiTextFlags flags) return; ImGuiContext& g = *GImGui; - IM_IMSTR_ENSURE_HAS_END(text); - const ImVec2 text_pos(window->DC.CursorPos.x, window->DC.CursorPos.y + window->DC.CurrLineTextBaseOffset); const float wrap_pos_x = window->DC.TextWrapPos; const bool wrap_enabled = (wrap_pos_x >= 0.0f); @@ -4360,7 +4358,6 @@ bool ImGui::InputTextEx(ImStrv label, ImStrv hint, char* buf, int buf_size, cons if (ImStrv clipboard = GetClipboardText()) { // Filter pasted buffer - IM_IMSTR_ENSURE_HAS_END(clipboard); const int clipboard_len = (int)IM_IMSTR_LENGTH(clipboard); ImWchar* clipboard_filtered = (ImWchar*)IM_ALLOC((clipboard_len + 1) * sizeof(ImWchar)); int clipboard_filtered_len = 0; @@ -4570,7 +4567,6 @@ bool ImGui::InputTextEx(ImStrv label, ImStrv hint, char* buf, int buf_size, cons const char* buf_display_end = NULL; // We have specialized paths below for setting the length if (is_displaying_hint) { - IM_IMSTR_ENSURE_HAS_END(hint); buf_display = hint.Begin; buf_display_end = hint.End; }