ImDebugger: Assorted UI improvements

This commit is contained in:
Henrik Rydgård 2024-12-13 21:58:22 +01:00
parent 79c0f413f9
commit 3cc7d6ef7a
5 changed files with 60 additions and 56 deletions

View file

@ -64,6 +64,14 @@ void ShowInWindowMenuItems(uint32_t addr, ImControl &control) {
}
}
void StatusBar(std::string_view status) {
ImGui::TextUnformatted(status.data(), status.data() + status.length());
ImGui::SameLine();
if (ImGui::SmallButton("Copy")) {
System_CopyStringToClipboard(status);
}
}
// TODO: Style it.
// Left click performs the preferred action, if any. Right click opens a menu for more.
void ImClickableAddress(uint32_t addr, ImControl &control, ImCmd cmd) {
@ -1170,8 +1178,10 @@ void ImMemWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImControl &
memView_.gotoAddr(gotoAddr_);
}
ImVec2 size(0, -ImGui::GetFrameHeightWithSpacing());
// Main views - list of interesting addresses to the left, memory view to the right.
if (ImGui::BeginChild("addr_list", ImVec2(200.0f, 0.0))) {
if (ImGui::BeginChild("addr_list", ImVec2(200.0f, size.y), ImGuiChildFlags_ResizeX)) {
if (ImGui::Selectable("Scratch")) {
GotoAddr(0x00010000);
}
@ -1182,18 +1192,19 @@ void ImMemWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImControl &
GotoAddr(0x08800000);
}
if (ImGui::Selectable("VRAM")) {
GotoAddr(0x08800000);
GotoAddr(0x04000000);
}
}
ImGui::EndChild();
ImGui::SameLine();
if (ImGui::BeginChild("memview", ImVec2(0, -ImGui::GetFrameHeightWithSpacing()))) {
if (ImGui::BeginChild("memview", size)) {
memView_.Draw(ImGui::GetWindowDrawList());
}
ImGui::EndChild();
ImGui::TextUnformatted(memView_.StatusMessage().c_str());
StatusBar(memView_.StatusMessage());
ImGui::End();
}
@ -1206,7 +1217,7 @@ void ImDisasmWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImContro
disasmView_.setDebugger(mipsDebug);
ImGui::SetNextWindowSize(ImVec2(520, 600), ImGuiCond_FirstUseEver);
if (!ImGui::Begin(Title(), &cfg.disasmOpen, ImGuiWindowFlags_NoNavInputs)) {
if (!ImGui::Begin(Title(), &cfg.disasmOpen)) {
ImGui::End();
return;
}
@ -1273,10 +1284,11 @@ void ImDisasmWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImContro
Core_RequestCPUStep(CPUStepType::Out, 0);
}
/*
ImGui::SameLine();
if (ImGui::SmallButton("Frame")) {
Core_RequestCPUStep(CPUStepType::Frame, 0);
}
}*/
ImGui::SameLine();
if (ImGui::SmallButton("Syscall")) {
@ -1346,12 +1358,10 @@ void ImDisasmWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImContro
disasmView_.scrollAddressIntoView();
}
if (ImGui::BeginTable("main", 2)) {
ImGui::TableSetupColumn("left", ImGuiTableColumnFlags_WidthFixed);
ImGui::TableSetupColumn("right", ImGuiTableColumnFlags_WidthStretch);
ImGui::TableNextRow();
ImGui::TableSetColumnIndex(0);
ImVec2 avail = ImGui::GetContentRegionAvail();
avail.y -= ImGui::GetTextLineHeightWithSpacing();
if (ImGui::BeginChild("left", ImVec2(150.0f, avail.y), ImGuiChildFlags_ResizeX)) {
if (symCache_.empty() || symsDirty_) {
symCache_ = g_symbolMap->GetAllSymbols(SymbolType::ST_FUNCTION);
symsDirty_ = false;
@ -1369,8 +1379,7 @@ void ImDisasmWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImContro
}
}
ImVec2 sz = ImGui::GetContentRegionAvail();
if (ImGui::BeginListBox("##symbols", ImVec2(150.0, sz.y - ImGui::GetTextLineHeightWithSpacing() * 2))) {
if (ImGui::BeginListBox("##symbols", ImGui::GetContentRegionAvail())) {
ImGuiListClipper clipper;
clipper.Begin((int)symCache_.size(), -1);
while (clipper.Step()) {
@ -1386,13 +1395,16 @@ void ImDisasmWindow::Draw(MIPSDebugInterface *mipsDebug, ImConfig &cfg, ImContro
clipper.End();
ImGui::EndListBox();
}
ImGui::TableSetColumnIndex(1);
disasmView_.Draw(ImGui::GetWindowDrawList(), control);
ImGui::EndTable();
ImGui::TextUnformatted(disasmView_.StatusBarText().c_str());
}
ImGui::EndChild();
ImGui::SameLine();
if (ImGui::BeginChild("right", ImVec2(0.0f, avail.y))) {
disasmView_.Draw(ImGui::GetWindowDrawList(), control);
}
ImGui::EndChild();
StatusBar(disasmView_.StatusBarText());
ImGui::End();
}

View file

@ -76,6 +76,7 @@ public:
symsDirty_ = true;
}
void GotoAddr(u32 addr) {
gotoAddr_ = addr;
memView_.gotoAddr(addr);
}
static const char *Title(int index);
@ -122,6 +123,7 @@ struct ImConfig {
bool geDebuggerOpen;
bool geStateOpen;
bool schedulerOpen;
bool watchOpen;
bool memViewOpen[4];
// HLE explorer settings
@ -195,3 +197,4 @@ private:
void ImClickableAddress(uint32_t addr, ImControl &control, ImCmd cmd);
void ShowInWindowMenuItems(uint32_t addr, ImControl &control);
void ShowInMemoryViewerMenuItem(uint32_t addr, ImControl &control);
void StatusBar(std::string_view str);

View file

@ -309,9 +309,7 @@ void ImDisasmView::Draw(ImDrawList *drawList, ImControl &control) {
ImVec2 canvas_p0 = ImGui::GetCursorScreenPos(); // ImDrawList API uses screen coordinates!
ImVec2 canvas_sz = ImGui::GetContentRegionAvail(); // Resize canvas to what's available
if (canvas_sz.x < 50.0f) canvas_sz.x = 50.0f;
if (canvas_sz.y < 50.0f) canvas_sz.y = 50.0f;
canvas_sz.y -= rowHeight_ * 2.0f; // space for status bar
const ImVec2 canvas_p1 = ImVec2(canvas_p0.x + canvas_sz.x, canvas_p0.y + canvas_sz.y);
// This will catch our interactions
bool pressed = ImGui::InvisibleButton("canvas", canvas_sz, ImGuiButtonFlags_MouseButtonLeft | ImGuiButtonFlags_MouseButtonRight);
@ -323,8 +321,6 @@ void ImDisasmView::Draw(ImDrawList *drawList, ImControl &control) {
}
ImGui::SetItemKeyOwner(ImGuiKey_MouseWheelY);
const ImVec2 canvas_p1 = ImVec2(canvas_p0.x + canvas_sz.x, canvas_p0.y + canvas_sz.y);
drawList->PushClipRect(canvas_p0, canvas_p1, true);
drawList->AddRectFilled(canvas_p0, canvas_p1, IM_COL32(25, 25, 25, 255));
if (is_active) {

View file

@ -426,23 +426,25 @@ void ImGeDebuggerWindow::Draw(ImConfig &cfg, ImControl &control, GPUDebugInterfa
ImGui::BeginChild("left pane", ImVec2(400, 0), ImGuiChildFlags_Borders | ImGuiChildFlags_ResizeX);
for (auto index : gpuDebug->GetDisplayListQueue()) {
const auto &list = gpuDebug->GetDisplayList(index);
char title[64];
snprintf(title, sizeof(title), "List %d", list.id);
if (ImGui::CollapsingHeader(title)) {
ImGui::Text("State: %s", DLStateToString(list.state));
ImGui::TextUnformatted("PC:");
ImGui::SameLine();
ImClickableAddress(list.pc, control, ImCmd::SHOW_IN_GE_DISASM);
ImGui::Text("StartPC:");
ImGui::SameLine();
ImClickableAddress(list.startpc, control, ImCmd::SHOW_IN_GE_DISASM);
if (list.pendingInterrupt) {
ImGui::TextUnformatted("(Pending interrupt)");
if (ImGui::CollapsingHeader("Display lists")) {
for (auto index : gpuDebug->GetDisplayListQueue()) {
const auto &list = gpuDebug->GetDisplayList(index);
char title[64];
snprintf(title, sizeof(title), "List %d", list.id);
if (ImGui::CollapsingHeader(title)) {
ImGui::Text("State: %s", DLStateToString(list.state));
ImGui::TextUnformatted("PC:");
ImGui::SameLine();
ImClickableAddress(list.pc, control, ImCmd::SHOW_IN_GE_DISASM);
ImGui::Text("StartPC:");
ImGui::SameLine();
ImClickableAddress(list.startpc, control, ImCmd::SHOW_IN_GE_DISASM);
if (list.pendingInterrupt) {
ImGui::TextUnformatted("(Pending interrupt)");
}
ImGui::Text("Stack depth: %d", (int)list.stackptr);
ImGui::Text("BBOX result: %d", (int)list.bboxResult);
}
ImGui::Text("Stack depth: %d", (int)list.stackptr);
ImGui::Text("BBOX result: %d", (int)list.bboxResult);
}
}

View file

@ -27,17 +27,6 @@ ImMemView::ImMemView() {
ImMemView::~ImMemView() {}
/*
LRESULT CALLBACK ImMemView::wndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) {
if (GET_WHEEL_DELTA_WPARAM(wParam) > 0) {
ccp->ScrollWindow(-3, GotoModeFromModifiers(false));
} else if (GET_WHEEL_DELTA_WPARAM(wParam) < 0) {
ccp->ScrollWindow(3, GotoModeFromModifiers(false));
}
return DefWindowProc(hwnd, msg, wParam, lParam);
}
*/
static uint32_t pickTagColor(std::string_view tag) {
uint32_t colors[6] = { 0xFF301010, 0xFF103030, 0xFF403010, 0xFF103000, 0xFF301030, 0xFF101030 };
int which = XXH3_64bits(tag.data(), tag.length()) % ARRAY_SIZE(colors);
@ -107,7 +96,7 @@ void ImMemView::Draw(ImDrawList *drawList) {
char temp[32];
uint32_t address = windowStart_ + i * rowSize_;
snprintf(temp, sizeof(temp), "%08X", address);
snprintf(temp, sizeof(temp), "%08x", address);
drawList->AddText(ImVec2(canvas_p0.x + addressStartX_, canvas_p0.y + rowY), IM_COL32(0xE0, 0xE0, 0xE0, 0xFF), temp);
union {
@ -136,7 +125,7 @@ void ImMemView::Draw(ImDrawList *drawList) {
char c;
if (valid) {
snprintf(temp, sizeof(temp), "%02X ", memory.bytes[j]);
snprintf(temp, sizeof(temp), "%02x ", memory.bytes[j]);
c = (char)memory.bytes[j];
if (memory.bytes[j] < 32 || memory.bytes[j] >= 128)
c = '.';
@ -188,8 +177,8 @@ void ImMemView::Draw(ImDrawList *drawList) {
if (bg != 0) {
int bgWidth = 2; // continueRect ? 3 : 2;
drawList->AddRectFilled(ImVec2(canvas_p0.x + hexX - 1, canvas_p0.y + rowY), ImVec2(canvas_p0.x + hexX + charWidth_ * bgWidth, canvas_p0.y + rowY + charHeight_), bg);
drawList->AddText(ImVec2(canvas_p0.x + hexX, canvas_p0.y + rowY), fg, &temp[0], &temp[2]);
}
drawList->AddText(ImVec2(canvas_p0.x + hexX, canvas_p0.y + rowY), fg, &temp[0], &temp[2]);
if (underline >= 0) {
float x = canvas_p0.x + hexX + underline * charWidth_;
drawList->AddRectFilled(ImVec2(x, canvas_p0.y + rowY + charHeight_ - 2), ImVec2(x + charWidth_, canvas_p0.y + rowY + charHeight_), IM_COL32(0xFF, 0xFF, 0xFF, 0xFF));
@ -197,7 +186,9 @@ void ImMemView::Draw(ImDrawList *drawList) {
fg = asciiTextCol;
bg = asciiBGCol;
drawList->AddRectFilled(ImVec2(canvas_p0.x + asciiX, canvas_p0.y + rowY), ImVec2(canvas_p0.x + asciiX + charWidth_, canvas_p0.y + rowY + charHeight_), bg);
if (bg) {
drawList->AddRectFilled(ImVec2(canvas_p0.x + asciiX, canvas_p0.y + rowY), ImVec2(canvas_p0.x + asciiX + charWidth_, canvas_p0.y + rowY + charHeight_), bg);
}
drawList->AddText(ImVec2(canvas_p0.x + asciiX, canvas_p0.y + rowY), fg, &c, &c + 1);
}
}
@ -533,7 +524,7 @@ void ImMemView::updateStatusBarText() {
snprintf(text, sizeof(text), "%08x", curAddress_);
// There should only be one.
for (MemBlockInfo info : memRangeInfo) {
snprintf(text, sizeof(text), "%08x - %s %08x-%08x (alloc'd at PC %08x / %lld ticks)", curAddress_, info.tag.c_str(), info.start, info.start + info.size, info.pc, info.ticks);
snprintf(text, sizeof(text), "%08x - %s %08x-%08x (PC %08x / %lld ticks)", curAddress_, info.tag.c_str(), info.start, info.start + info.size, info.pc, info.ticks);
}
statusMessage_ = text;
}