Internal: Log/Capture: Rework to add an internal LogToBuffer() function which is useful for writing automated tests. Clarified logging state by adding an enum.
diff --git a/imgui.cpp b/imgui.cpp
index ce7494d..22696b1 100644
--- a/imgui.cpp
+++ b/imgui.cpp
@@ -3615,7 +3615,7 @@
fclose(g.LogFile);
g.LogFile = NULL;
}
- g.LogClipboard.clear();
+ g.LogBuffer.clear();
g.Initialized = false;
}
@@ -8786,7 +8786,7 @@
if (g.LogFile)
vfprintf(g.LogFile, fmt, args);
else
- g.LogClipboard.appendfv(fmt, args);
+ g.LogBuffer.appendfv(fmt, args);
va_end(args);
}
@@ -8830,7 +8830,7 @@
}
}
-// Start logging ImGui output to TTY
+// Start logging/capturing text output to TTY
void ImGui::LogToTTY(int max_depth)
{
ImGuiContext& g = *GImGui;
@@ -8841,12 +8841,13 @@
IM_ASSERT(g.LogFile == NULL);
g.LogFile = stdout;
g.LogEnabled = true;
+ g.LogType = ImGuiLogType_TTY;
g.LogStartDepth = window->DC.TreeDepth;
if (max_depth >= 0)
g.LogAutoExpandMaxDepth = max_depth;
}
-// Start logging ImGui output to given file
+// Start logging/capturing text output to given file
void ImGui::LogToFile(int max_depth, const char* filename)
{
ImGuiContext& g = *GImGui;
@@ -8855,26 +8856,25 @@
ImGuiWindow* window = g.CurrentWindow;
if (!filename)
- {
filename = g.IO.LogFilename;
- if (!filename)
- return;
- }
+ if (!filename || !filename[0])
+ return;
IM_ASSERT(g.LogFile == NULL);
- g.LogFile = ImFileOpen(filename, "ab");
+ g.LogFile = ImFileOpen(filename, "ab"); // FIXME: Why not logging in text mode? Then we don't need to bother the user with IM_NEWLINE..
if (!g.LogFile)
{
IM_ASSERT(0);
return;
}
g.LogEnabled = true;
+ g.LogType = ImGuiLogType_File;
g.LogStartDepth = window->DC.TreeDepth;
if (max_depth >= 0)
g.LogAutoExpandMaxDepth = max_depth;
}
-// Start logging ImGui output to clipboard
+// Start logging/capturing text output to clipboard
void ImGui::LogToClipboard(int max_depth)
{
ImGuiContext& g = *GImGui;
@@ -8883,8 +8883,27 @@
ImGuiWindow* window = g.CurrentWindow;
IM_ASSERT(g.LogFile == NULL);
- g.LogFile = NULL;
+ IM_ASSERT(g.LogBuffer.empty());
g.LogEnabled = true;
+ g.LogType = ImGuiLogType_Clipboard;
+ g.LogFile = NULL;
+ g.LogStartDepth = window->DC.TreeDepth;
+ if (max_depth >= 0)
+ g.LogAutoExpandMaxDepth = max_depth;
+}
+
+void ImGui::LogToBuffer(int max_depth)
+{
+ ImGuiContext& g = *GImGui;
+ if (g.LogEnabled)
+ return;
+ ImGuiWindow* window = g.CurrentWindow;
+
+ IM_ASSERT(g.LogFile == NULL);
+ IM_ASSERT(g.LogBuffer.empty());
+ g.LogEnabled = true;
+ g.LogType = ImGuiLogType_Clipboard;
+ g.LogFile = NULL;
g.LogStartDepth = window->DC.TreeDepth;
if (max_depth >= 0)
g.LogAutoExpandMaxDepth = max_depth;
@@ -8897,23 +8916,30 @@
return;
LogText(IM_NEWLINE);
- if (g.LogFile != NULL)
+ switch (g.LogType)
{
- if (g.LogFile == stdout)
- fflush(g.LogFile);
- else
- fclose(g.LogFile);
- g.LogFile = NULL;
+ case ImGuiLogType_TTY:
+ fflush(g.LogFile);
+ break;
+ case ImGuiLogType_File:
+ fclose(g.LogFile);
+ break;
+ case ImGuiLogType_Buffer:
+ break;
+ case ImGuiLogType_Clipboard:
+ if (!g.LogBuffer.empty())
+ SetClipboardText(g.LogBuffer.begin());
+ break;
}
- if (g.LogClipboard.size() > 1)
- {
- SetClipboardText(g.LogClipboard.begin());
- g.LogClipboard.clear();
- }
+
g.LogEnabled = false;
+ g.LogType = ImGuiLogType_None;
+ g.LogFile = NULL;
+ g.LogBuffer.clear();
}
// Helper to display logging buttons
+// FIXME-OBSOLETE: We should probably obsolete this and let the user have their own helper (this is one of the oldest function alive!)
void ImGui::LogButtons()
{
ImGuiContext& g = *GImGui;
diff --git a/imgui_internal.h b/imgui_internal.h
index cc355e9..c79aeab 100644
--- a/imgui_internal.h
+++ b/imgui_internal.h
@@ -384,6 +384,15 @@
ImGuiLayoutType_Vertical = 1
};
+enum ImGuiLogType
+{
+ ImGuiLogType_None = 0,
+ ImGuiLogType_TTY,
+ ImGuiLogType_File,
+ ImGuiLogType_Buffer,
+ ImGuiLogType_Clipboard
+};
+
// X/Y enums are fixed to 0/1 so they may be used to index ImVec2
enum ImGuiAxis
{
@@ -928,8 +937,9 @@
// Logging
bool LogEnabled;
+ ImGuiLogType LogType;
FILE* LogFile; // If != NULL log to stdout/ file
- ImGuiTextBuffer LogClipboard; // Accumulation buffer when log to clipboard. This is pointer so our GImGui static constructor doesn't call heap allocators.
+ ImGuiTextBuffer LogBuffer; // Accumulation buffer when log to clipboard. This is pointer so our GImGui static constructor doesn't call heap allocators.
int LogStartDepth;
int LogAutoExpandMaxDepth;
@@ -1041,6 +1051,7 @@
SettingsDirtyTimer = 0.0f;
LogEnabled = false;
+ LogType = ImGuiLogType_None;
LogFile = NULL;
LogStartDepth = 0;
LogAutoExpandMaxDepth = 2;
@@ -1396,6 +1407,9 @@
IMGUI_API void PushItemFlag(ImGuiItemFlags option, bool enabled);
IMGUI_API void PopItemFlag();
+ // Logging/Capture
+ IMGUI_API void LogToBuffer(int max_depth = -1); // Start logging to internal buffer
+
// Popups, Modals, Tooltips
IMGUI_API void OpenPopupEx(ImGuiID id);
IMGUI_API void ClosePopupToLevel(int remaining, bool apply_focus_to_window_under);