Skip to content

Commit 57f2041

Browse files
committed
PR_26174_ALFA_018-game-selection-button-state
1 parent 50fe81c commit 57f2041

10 files changed

Lines changed: 135 additions & 36 deletions

assets/theme-v2/css/tables.css

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -115,9 +115,10 @@ td {
115115
cursor: pointer
116116
}
117117

118-
.data-table [data-game-active-cell="true"] {
119-
box-shadow: inset var(--space-3) 0 0 var(--gold);
120-
border-bottom-color: var(--gold-border-muted)
118+
.data-table [data-game-toggle][aria-current="true"] {
119+
border-color: var(--gold);
120+
background: color-mix(in srgb, var(--gold) 18%, var(--panel-soft));
121+
box-shadow: inset 0 0 0 1px var(--gold-border-muted)
121122
}
122123

123124
.idea-board-idea-label {
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
# PR_26174_ALFA_018-game-selection-button-state
2+
3+
## Summary
4+
5+
Moved Game Hub selected-game indication to the game button only.
6+
7+
## Implementation
8+
9+
- Removed active-game markers from parent rows.
10+
- Removed active-game markers from parent table cells.
11+
- Replaced the left-border cell highlight with selected styling on the game button.
12+
- Removed the `Selected {game}.` status log update when selecting a game row.
13+
- Preserved child row behavior so Source Idea and Readiness Output follow the selected game.
14+
- Added targeted Playwright assertions for one selected button, unchanged sibling columns, child row movement, and no selected status copy.
15+
16+
## Scope Control
17+
18+
- Preserved the existing API/service contract.
19+
- Preserved the Game row parent structure.
20+
- Preserved Source Idea and Readiness Output child rows/tables.
21+
- Did not add browser-owned product data.
22+
- Did not introduce silent fallbacks.
23+
24+
## ZIP
25+
26+
- `tmp/PR_26174_ALFA_018-game-selection-button-state_delta.zip`
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
Branch validation: PASS
2+
3+
Branch:
4+
pr/26174-ALFA-018-game-selection-button-state
5+
6+
Base stack branch:
7+
pr/26174-ALFA-017-game-hub-guest-save-and-crew-cleanup
8+
9+
Checks:
10+
- Current branch is the ALFA_018 branch: PASS
11+
- Worktree was clean before ALFA_018 edits: PASS
12+
- Scope limited to Game Hub selection state, targeted Playwright coverage, and required reports: PASS
13+
- No protected Project Instructions changes: PASS
14+
- No merge to main performed: PASS
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
Manual validation notes: PASS
2+
3+
- Reviewed `docs_build/dev/ProjectInstructions/addendums/table_first_ui.md`.
4+
- Confirmed selected state remains on the game button through `aria-current`.
5+
- Confirmed parent rows no longer receive active attributes.
6+
- Confirmed cells no longer receive active markers.
7+
- Confirmed the old left-border cell selector was removed.
8+
- Confirmed selecting another game leaves only one selected game button.
9+
- Confirmed Source Idea and Readiness Output child rows move with the selected game.
10+
- Confirmed the bottom status area no longer receives `Selected {game}.` when a game row is selected.
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
Requirement checklist: PASS
2+
3+
- Selected game is indicated only by the Game button: PASS
4+
- Row-level selection indicators removed: PASS
5+
- Left border highlight removed: PASS
6+
- Row background highlight removed: PASS
7+
- Cell background highlights removed: PASS
8+
- Purpose, Status, and Actions columns remain visually identical for all rows: PASS
9+
- Only one game may be selected at a time: PASS
10+
- Selecting a different game moves selected styling to that game button: PASS
11+
- Child rows continue to follow the selected game: PASS
12+
- Follow table_first_ui.md: PASS
13+
- Removed selected-game status copy from bottom status area: PASS
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
Validation lane: PASS
2+
3+
Commands:
4+
- `git diff --check -- toolbox/game-hub/game-hub.js assets/theme-v2/css/tables.css tests/playwright/tools/GameHubMockRepository.spec.mjs`
5+
- PASS
6+
- `node --check toolbox/game-hub/game-hub.js`
7+
- PASS
8+
- `npx playwright test tests/playwright/tools/GameHubMockRepository.spec.mjs -g "Game Hub"`
9+
- PASS, 11 passed
10+
11+
Generated coverage reports were restored after Playwright validation to keep this PR scoped.
Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
1-
docs_build/dev/reports/PR_26174_ALFA_017-game-hub-guest-save-and-crew-cleanup.md
2-
docs_build/dev/reports/PR_26174_ALFA_017-game-hub-guest-save-and-crew-cleanup_branch-validation.txt
3-
docs_build/dev/reports/PR_26174_ALFA_017-game-hub-guest-save-and-crew-cleanup_manual-validation-notes.txt
4-
docs_build/dev/reports/PR_26174_ALFA_017-game-hub-guest-save-and-crew-cleanup_requirement-checklist.txt
5-
docs_build/dev/reports/PR_26174_ALFA_017-game-hub-guest-save-and-crew-cleanup_validation-lane.txt
1+
assets/theme-v2/css/tables.css
2+
docs_build/dev/reports/PR_26174_ALFA_018-game-selection-button-state.md
3+
docs_build/dev/reports/PR_26174_ALFA_018-game-selection-button-state_branch-validation.txt
4+
docs_build/dev/reports/PR_26174_ALFA_018-game-selection-button-state_manual-validation-notes.txt
5+
docs_build/dev/reports/PR_26174_ALFA_018-game-selection-button-state_requirement-checklist.txt
6+
docs_build/dev/reports/PR_26174_ALFA_018-game-selection-button-state_validation-lane.txt
67
docs_build/dev/reports/codex_changed_files.txt
78
docs_build/dev/reports/codex_review.diff
89
tests/playwright/tools/GameHubMockRepository.spec.mjs
910
toolbox/game-hub/game-hub.js
10-
toolbox/game-hub/index.html
-14.1 KB
Binary file not shown.

tests/playwright/tools/GameHubMockRepository.spec.mjs

Lines changed: 51 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -290,24 +290,48 @@ test("Game Hub creates, opens, and deletes mock games", async ({ page }) => {
290290
const demoGameRow = page.locator("[data-game-row='demo-game']");
291291
await expect(demoGameRow.locator("td")).toHaveText(["Game", "Under Construction", "Edit"]);
292292
await expect(demoGameRow).not.toContainText("User 1");
293-
await expect(demoGameRow).toHaveAttribute("data-game-active", "true");
294-
await expect(demoGameRow).toHaveAttribute("aria-current", "true");
295-
await expect(demoGameRow.locator("th[data-game-active-cell='true']")).toContainText("Demo Game");
296-
const activeCellStyle = await demoGameRow.locator("th[data-game-active-cell='true']").evaluate((cell) => {
297-
const styles = getComputedStyle(cell);
298-
return {
299-
backgroundColor: styles.backgroundColor,
300-
boxShadow: styles.boxShadow,
301-
};
302-
});
303-
const inactiveCellBackground = await page.locator("[data-game-row='gravity-demo'] th").evaluate((cell) => getComputedStyle(cell).backgroundColor);
304-
expect(activeCellStyle.backgroundColor).toBe(inactiveCellBackground);
305-
expect(activeCellStyle.boxShadow).not.toBe("none");
293+
await expect(demoGameRow).not.toHaveAttribute("data-game-active", "true");
294+
await expect(demoGameRow).not.toHaveAttribute("aria-current", "true");
295+
await expect(demoGameRow.locator("th[data-game-active-cell='true']")).toHaveCount(0);
296+
await expect(page.locator("[data-game-row][data-game-active='true']")).toHaveCount(0);
297+
await expect(page.locator("[data-game-row][aria-current='true']")).toHaveCount(0);
298+
await expect(page.locator("[data-game-active-cell='true']")).toHaveCount(0);
299+
const rowVisuals = await page.locator("[data-game-row]").evaluateAll((rows) => rows.map((row) => {
300+
const cells = Array.from(row.children).slice(1);
301+
return cells.map((cell) => {
302+
const styles = getComputedStyle(cell);
303+
return {
304+
backgroundColor: styles.backgroundColor,
305+
boxShadow: styles.boxShadow,
306+
};
307+
});
308+
}));
309+
expect(rowVisuals[0]).toEqual(rowVisuals[1]);
306310
await expect(demoGameRow.locator("> .status")).toHaveCount(0);
307311
await expect(demoGameRow.locator("[data-game-toggle='demo-game']")).toHaveAttribute("aria-expanded", "false");
308312
await expect(demoGameRow.locator("[data-game-toggle='demo-game']")).not.toHaveClass(/primary/);
309313
await expect(demoGameRow.locator("[data-game-toggle='demo-game']")).toHaveClass(/\bbtn--compact\b/);
314+
await expect(demoGameRow.locator("[data-game-toggle='demo-game']")).toHaveAttribute("data-game-active", "true");
310315
await expect(demoGameRow.locator("[data-game-toggle='demo-game']")).toHaveAttribute("aria-current", "true");
316+
await expect(page.locator("[data-game-toggle][aria-current='true']")).toHaveCount(1);
317+
await expect(page.locator("[data-game-toggle][data-game-active='true']")).toHaveCount(1);
318+
const activeButtonStyle = await demoGameRow.locator("[data-game-toggle='demo-game']").evaluate((button) => {
319+
const styles = getComputedStyle(button);
320+
return {
321+
backgroundColor: styles.backgroundColor,
322+
borderColor: styles.borderColor,
323+
boxShadow: styles.boxShadow,
324+
};
325+
});
326+
const inactiveButtonStyle = await page.locator("[data-game-row='gravity-demo'] [data-game-toggle='gravity-demo']").evaluate((button) => {
327+
const styles = getComputedStyle(button);
328+
return {
329+
backgroundColor: styles.backgroundColor,
330+
borderColor: styles.borderColor,
331+
boxShadow: styles.boxShadow,
332+
};
333+
});
334+
expect(activeButtonStyle).not.toEqual(inactiveButtonStyle);
311335
await expect(demoGameRow.getByRole("button", { name: "Edit Demo Game" })).toHaveText("Edit");
312336
await expect(demoGameRow.getByRole("button", { name: "Edit Demo Game" })).not.toHaveClass(/primary/);
313337
await expect(demoGameRow.getByRole("button", { name: "Edit Demo Game" })).toHaveClass(/\bbtn--compact\b/);
@@ -348,7 +372,10 @@ test("Game Hub creates, opens, and deletes mock games", async ({ page }) => {
348372
await addGameRow.getByLabel("Status").selectOption("Ready for Testing");
349373
await addGameRow.getByRole("button", { name: "Save" }).click();
350374
await expect(page.locator("[data-game-list]")).toContainText("Launch Test Game");
351-
await expect(page.locator("[data-game-row='launch-test-game-1']")).toHaveAttribute("data-game-active", "true");
375+
await expect(page.locator("[data-game-row='launch-test-game-1']")).not.toHaveAttribute("data-game-active", "true");
376+
await expect(page.locator("[data-game-row='launch-test-game-1']")).not.toHaveAttribute("aria-current", "true");
377+
await expect(page.locator("[data-game-toggle][aria-current='true']")).toHaveCount(1);
378+
await expect(page.locator("[data-game-row='launch-test-game-1'] [data-game-toggle='launch-test-game-1']")).toHaveAttribute("aria-current", "true");
352379
await expect(page.locator("[data-game-row='launch-test-game-1'] [data-game-toggle='launch-test-game-1']")).not.toHaveClass(/primary/);
353380
await expect(page.locator("[data-game-row='launch-test-game-1']").getByRole("button", { name: "Edit Launch Test Game" })).not.toHaveClass(/primary/);
354381
await expect(page.locator("[data-game-row='launch-test-game-1'] td").nth(0)).toHaveText("Learning Game");
@@ -376,14 +403,21 @@ test("Game Hub creates, opens, and deletes mock games", async ({ page }) => {
376403
await page.getByRole("button", { name: "Add Game" }).click();
377404
await page.locator("[data-game-add-row='input']").getByLabel("Game").fill("Archive Game");
378405
await page.locator("[data-game-add-row='input']").getByRole("button", { name: "Save" }).click();
379-
await expect(page.locator("[data-game-row='archive-game-2']")).toHaveAttribute("data-game-active", "true");
406+
await expect(page.locator("[data-game-row='archive-game-2']")).not.toHaveAttribute("data-game-active", "true");
407+
await expect(page.locator("[data-game-row='archive-game-2'] [data-game-toggle='archive-game-2']")).toHaveAttribute("aria-current", "true");
380408
await expect(page.locator("[data-game-row='archive-game-2'] [data-game-toggle='archive-game-2']")).not.toHaveClass(/primary/);
381409

382410
await page.locator("[data-game-row='launch-test-game-1'] [data-game-toggle='launch-test-game-1']").click();
383-
await expect(page.locator("[data-game-row='launch-test-game-1']")).toHaveAttribute("data-game-active", "true");
411+
await expect(page.locator("[data-game-row='launch-test-game-1']")).not.toHaveAttribute("data-game-active", "true");
412+
await expect(page.locator("[data-game-row='launch-test-game-1'] [data-game-toggle='launch-test-game-1']")).toHaveAttribute("aria-current", "true");
413+
await expect(page.locator("[data-game-row='archive-game-2'] [data-game-toggle='archive-game-2']")).not.toHaveAttribute("aria-current", "true");
414+
await expect(page.locator("[data-game-toggle][aria-current='true']")).toHaveCount(1);
415+
await expect(page.locator("[data-game-toggle][data-game-active='true']")).toHaveCount(1);
416+
await expect(page.locator("[data-game-expanded-row='launch-test-game-1']")).toHaveCount(2);
417+
await expect(page.locator("[data-game-expanded-row='archive-game-2']")).toHaveCount(0);
384418
await expect(page.locator("[data-game-row='launch-test-game-1'] [data-game-toggle='launch-test-game-1']")).not.toHaveClass(/primary/);
385419
await expect(page.locator("[data-game-row='launch-test-game-1']").getByRole("button", { name: "Edit Launch Test Game" })).not.toHaveClass(/primary/);
386-
await expect(page.locator("[data-game-hub-log]")).toHaveText("Selected Launch Test Game.");
420+
await expect(page.locator("[data-game-hub-log]")).not.toHaveText("Selected Launch Test Game.");
387421

388422
await page.getByRole("button", { name: "Delete Open Game" }).click();
389423
await expect(page.locator("[data-game-row='launch-test-game-1']")).toHaveCount(0);

toolbox/game-hub/game-hub.js

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -482,16 +482,9 @@ function renderGameParentRow(tbody, game, activeGame, progress) {
482482

483483
const row = document.createElement("tr");
484484
row.dataset.gameRow = game.id;
485-
if (active) {
486-
row.dataset.gameActive = "true";
487-
row.setAttribute("aria-current", "true");
488-
}
489485

490486
const nameCell = document.createElement("th");
491487
nameCell.scope = "row";
492-
if (active) {
493-
nameCell.dataset.gameActiveCell = "true";
494-
}
495488
nameCell.append(createGameToggleButton(game, expanded, active));
496489
row.append(
497490
nameCell,
@@ -731,9 +724,6 @@ elements.gameList?.addEventListener("click", (event) => {
731724
renderWorkspace();
732725
return;
733726
}
734-
if (game) {
735-
setStatusLog(`Selected ${game.name}.`);
736-
}
737727
state.expandedGameId = state.expandedGameId === toggle.dataset.gameToggle ? "" : toggle.dataset.gameToggle;
738728
renderWorkspace();
739729
return;

0 commit comments

Comments
 (0)