Step 360: Phase 13d Integration and Sprint 13 Summary (8/8 tests)
This commit is contained in:
@@ -2134,4 +2134,8 @@ add_executable(step359_test tests/step359_test.cpp)
|
||||
target_include_directories(step359_test PRIVATE src)
|
||||
target_link_libraries(step359_test PRIVATE nlohmann_json::nlohmann_json)
|
||||
|
||||
add_executable(step360_test tests/step360_test.cpp)
|
||||
target_include_directories(step360_test PRIVATE src)
|
||||
target_link_libraries(step360_test PRIVATE nlohmann_json::nlohmann_json)
|
||||
|
||||
# Step 12: Dear ImGui shell scaffolding created (main.cpp exists but not built due to dependencies)
|
||||
|
||||
198
editor/tests/step360_test.cpp
Normal file
198
editor/tests/step360_test.cpp
Normal file
@@ -0,0 +1,198 @@
|
||||
// Step 360: Phase 13d Integration + Sprint 13 Summary (8 tests)
|
||||
|
||||
#include <cassert>
|
||||
#include <iostream>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include "PanelManager.h"
|
||||
#include "ThemeData.h"
|
||||
#include "KeybindingRegistry.h"
|
||||
#include "KeySymbolRenderer.h"
|
||||
#include "CommandPalette.h"
|
||||
#include "MenuBar.h"
|
||||
#include "KeyboardShortcutsPanel.h"
|
||||
#include "panels/BreadcrumbBar.h"
|
||||
#include "panels/StatusBar.h"
|
||||
#include "panels/NavigationTools.h"
|
||||
#include "panels/FindReplaceBar.h"
|
||||
#include "ast/Function.h"
|
||||
|
||||
int main() {
|
||||
int passed = 0;
|
||||
WhetstoneTheme theme = getDefaultDarkTheme();
|
||||
|
||||
// Shared module/project for navigation tests
|
||||
Module mod("m1", "app", "python");
|
||||
auto* helper = new Function("f1", "helper");
|
||||
helper->setSpan(9, 0, 12, 0);
|
||||
auto* caller = new Function("f2", "caller");
|
||||
caller->setSpan(19, 0, 24, 0);
|
||||
mod.addChild("functions", helper);
|
||||
mod.addChild("functions", caller);
|
||||
std::vector<std::pair<std::string, const Module*>> modules = {{"app.py", &mod}};
|
||||
|
||||
// Test 1: keyboard workflow + definition + breadcrumb click-back
|
||||
{
|
||||
FunctionCall call;
|
||||
call.functionName = "helper";
|
||||
auto def = goToDefinition(&call, "app.py", modules);
|
||||
assert(def.has_value());
|
||||
auto crumbs = buildBreadcrumbBar(&mod, def->node, theme);
|
||||
assert(!crumbs.segments.empty());
|
||||
auto back = navigateBreadcrumbClick(crumbs, 0);
|
||||
assert(back == &mod);
|
||||
std::cout << "Test 1 PASSED: keyboard -> definition -> breadcrumb back\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 2: command palette -> find -> project search -> navigate to result
|
||||
{
|
||||
KeybindingRegistry reg;
|
||||
reg.loadDefaults();
|
||||
CommandPalette palette;
|
||||
palette.registerFromKeybindings(reg);
|
||||
auto cmdMatches = palette.search("find");
|
||||
assert(!cmdMatches.empty());
|
||||
auto selected = palette.executeSelected(cmdMatches);
|
||||
assert(selected.has_value());
|
||||
assert(selected.value().find("find") != std::string::npos);
|
||||
|
||||
FindReplaceBar bar;
|
||||
bar.openFind();
|
||||
bar.setQuery("helper", "helper()\n");
|
||||
auto results = bar.searchProject({{"app.py", "helper()\n"}, {"other.py", "x\n"}});
|
||||
assert(!results.empty());
|
||||
assert(results[0].filePath == "app.py");
|
||||
std::cout << "Test 2 PASSED: palette find -> project results\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 3: status bar reflects buffer switches
|
||||
{
|
||||
StatusBarInput py;
|
||||
py.language = "python";
|
||||
py.filePath = "a.py";
|
||||
py.line = 4;
|
||||
py.column = 2;
|
||||
py.errorCount = 1;
|
||||
auto a = buildStatusBar(py, theme);
|
||||
|
||||
StatusBarInput cpp;
|
||||
cpp.language = "cpp";
|
||||
cpp.filePath = "a.cpp";
|
||||
cpp.line = 30;
|
||||
cpp.column = 1;
|
||||
cpp.warningCount = 2;
|
||||
auto b = buildStatusBar(cpp, theme);
|
||||
|
||||
assert(a.languageBadge != b.languageBadge);
|
||||
assert(a.centerText != b.centerText);
|
||||
assert(a.diagnosticsText != b.diagnosticsText);
|
||||
std::cout << "Test 3 PASSED: status bar reflects buffer switch\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 4: all panels docked (no floating windows in model)
|
||||
{
|
||||
PanelManager pm;
|
||||
pm.registerDefaults();
|
||||
auto visible = pm.getVisiblePanels();
|
||||
assert(visible.size() == 8);
|
||||
for (const auto& p : visible) {
|
||||
assert(p.currentDock == DockPosition::Left ||
|
||||
p.currentDock == DockPosition::CenterTop ||
|
||||
p.currentDock == DockPosition::CenterBottom ||
|
||||
p.currentDock == DockPosition::Right ||
|
||||
p.currentDock == DockPosition::Bottom);
|
||||
}
|
||||
std::cout << "Test 4 PASSED: panels are docked\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 5: theme consistency across panels/navigation elements
|
||||
{
|
||||
auto crumbs = buildBreadcrumbBar(&mod, helper, theme);
|
||||
StatusBarInput in;
|
||||
in.filePath = "app.py";
|
||||
auto status = buildStatusBar(in, theme);
|
||||
auto badge = KeySymbolRenderer::renderKeySymbol(KeyCombo::ctrl("S"), theme);
|
||||
assert(crumbs.textColor.toHex() == theme.text.toHex());
|
||||
assert(status.textColor.toHex() == theme.text.toHex());
|
||||
assert(badge.textColor.toHex() == theme.text.toHex());
|
||||
std::cout << "Test 5 PASSED: theme consistency\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 6: key symbols visible in menu, palette, shortcuts panel
|
||||
{
|
||||
KeybindingRegistry reg;
|
||||
reg.loadDefaults();
|
||||
auto menu = MenuBar::buildDefaults(reg, theme);
|
||||
auto saveItem = menu.findItem("save-buffer");
|
||||
assert(!saveItem.symbols.empty());
|
||||
|
||||
CommandPalette palette;
|
||||
palette.registerFromKeybindings(reg);
|
||||
bool paletteHasSymbol = false;
|
||||
for (const auto& entry : palette.all()) {
|
||||
if (entry.id == "save-buffer") {
|
||||
paletteHasSymbol = !entry.symbols.empty();
|
||||
}
|
||||
}
|
||||
assert(paletteHasSymbol);
|
||||
|
||||
KeyboardShortcutsPanel panel;
|
||||
panel.loadFromRegistry(reg);
|
||||
bool panelHasSymbol = false;
|
||||
for (const auto& row : panel.rows()) {
|
||||
if (row.actionId == "save-buffer") panelHasSymbol = !row.symbols.empty();
|
||||
}
|
||||
assert(panelHasSymbol);
|
||||
std::cout << "Test 6 PASSED: key symbols visible everywhere\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 7: layout save/restart/restore
|
||||
{
|
||||
PanelManager pm;
|
||||
pm.registerDefaults();
|
||||
pm.setVisible("workflow", false);
|
||||
pm.movePanelToDock("diagnostics", DockPosition::Right);
|
||||
auto snap = pm.toJson();
|
||||
auto restored = PanelManager::fromJson(snap);
|
||||
assert(!restored.isVisible("workflow"));
|
||||
assert(restored.getPanel("diagnostics").currentDock == DockPosition::Right);
|
||||
std::cout << "Test 7 PASSED: layout restore\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
// Test 8: Sprint 13 summary gates operational
|
||||
{
|
||||
bool dockingOk = true;
|
||||
bool themeOk = true;
|
||||
bool keysOk = true;
|
||||
bool navOk = true;
|
||||
|
||||
PanelManager pm;
|
||||
pm.registerDefaults();
|
||||
dockingOk = pm.panelCount() >= 8;
|
||||
|
||||
KeybindingRegistry reg;
|
||||
reg.loadDefaults();
|
||||
keysOk = reg.bindingCount() >= 15;
|
||||
|
||||
auto st = buildStatusBar(StatusBarInput{"python", "app.py"}, theme);
|
||||
themeOk = (st.bgColor.toHex() == theme.bgPanel.toHex());
|
||||
|
||||
auto symbols = collectFileSymbols(&mod, "app.py");
|
||||
navOk = !symbols.empty();
|
||||
|
||||
assert(dockingOk && themeOk && keysOk && navOk);
|
||||
std::cout << "Test 8 PASSED: sprint summary gates\n";
|
||||
passed++;
|
||||
}
|
||||
|
||||
std::cout << "\nResults: " << passed << "/8\n";
|
||||
assert(passed == 8);
|
||||
return 0;
|
||||
}
|
||||
33
progress.md
33
progress.md
@@ -2007,6 +2007,39 @@ Model behavior includes open/close modes, highlight state, and match counter tex
|
||||
- `step358_test` — PASS (12/12) regression coverage
|
||||
- `step359_test` — PASS (12/12) new step coverage
|
||||
|
||||
### Step 360: Phase 13d Integration + Sprint 13 Summary
|
||||
**Status:** PASS (8/8 tests)
|
||||
|
||||
Completed Phase 13d integration with end-to-end checks across keyboard navigation,
|
||||
go-to-definition, breadcrumb navigation, command palette search flows, status bar
|
||||
state transitions, key symbol visibility, and panel layout persistence.
|
||||
|
||||
**Files created:**
|
||||
- `editor/tests/step360_test.cpp` — 8 integration tests:
|
||||
1. keyboard workflow + definition jump + breadcrumb back-navigation
|
||||
2. command palette find flow + project result navigation
|
||||
3. status bar response to buffer/language/cursor/diagnostic changes
|
||||
4. docked-panel invariant (no floating model state)
|
||||
5. theme consistency across navigation components
|
||||
6. key symbols in menu + palette + shortcuts panel
|
||||
7. layout snapshot/restore roundtrip
|
||||
8. sprint-level operational gates (docking/theme/keys/navigation)
|
||||
|
||||
**Files modified:**
|
||||
- `editor/CMakeLists.txt` — `step360_test` target
|
||||
|
||||
**Verification run:**
|
||||
- `step358_test` — PASS (12/12) regression coverage
|
||||
- `step359_test` — PASS (12/12) regression coverage
|
||||
- `step360_test` — PASS (8/8) phase integration coverage
|
||||
|
||||
**Key results:**
|
||||
- Phase 13d complete: all 5 steps pass (56/56 tests across steps 356–360)
|
||||
- Sprint 13 complete: all phases pass (212/212 tests across steps 342–360)
|
||||
- Navigation foundation in place: breadcrumbs, status model, symbol navigation,
|
||||
find/replace model, and full keyboard-centric integration path
|
||||
- Key symbol consistency validated across all primary interaction surfaces
|
||||
|
||||
# Roadmap Planning — Sprints 12-25+
|
||||
|
||||
## Status: Planning Complete (Sprints 12-19 detailed, 20-25 in roadmap.md)
|
||||
|
||||
Reference in New Issue
Block a user