Skip to content

[spark-compete] enhance(copy): clipboard button has no SR confirmation - #153

Open
4gjnbzb4zf-sudo wants to merge 1 commit into
vibeforge1111:mainfrom
4gjnbzb4zf-sudo:spark-compete/copy-button-aria-live-announcement
Open

4gjnbzb4zf-sudo wants to merge 1 commit into
vibeforge1111:mainfrom
4gjnbzb4zf-sudo:spark-compete/copy-button-aria-live-announcement

Conversation

@4gjnbzb4zf-sudo

@4gjnbzb4zf-sudo 4gjnbzb4zf-sudo commented Jun 6, 2026

Copy link
Copy Markdown
Contributor

{
"schema": "spark-compete-hotfix-v1",
"event": "spark-compete-first-event",
"submission_mode": "public_repo_pr",
"submission_target_url": "#153",
"team": {
"name": "SparkThisUp",
"members": [
"ValHallaBuilder",
"Baz707",
"DanFireDash"
],
"github_accounts": [
"4gjnbzb4zf-sudo"
],
"llm_device_holder": "ValHallaBuilder",
"device_holder_github": "4gjnbzb4zf-sudo"
},
"target_repo": {
"id": "vibeforge1111/Spark-Agent-Site",
"source": "https://github.com/vibeforge1111/Spark-Agent-Site",
"owner_surface": "site_accessibility"
},
"issue": {
"type": "usage_friction",
"severity": "low",
"title": "app",
"actual_behavior": "Button label flips to 'copied' for 1600ms with no aria-live attribute, so the DOM mutation is not announced. SR user hears the original label echoed only if they re-focus the button later.",
"expected_behavior": "Button momentarily becomes a polite live region during the confirmation flash so SR engines announce 'copied' once when the text changes, then return to standard behavior when the original label is restored.",
"repro_steps": [
"1. Open the site with VoiceOver (macOS) or NVDA (Windows).",
"2. Tab to the hero 'install on Mac/Linux' or 'install on Windows' copy block, focus on the button.",
"3. Press Enter to trigger copyText().",
"4. Observe: the visible button label briefly changes to 'copied' but no spoken feedback fires. A sighted user sees confirmation; SR user does not, and silently assumes the action failed."
],
"affected_workflow": "Operator-facing flow in agent-site."
},
"evidence": {
"safe_links_only": true,
"before_after_proof": "Before: Button label flips to 'copied' for 1600ms with no aria-live attribute, so the DOM mutation is not announced. SR user hears the original label echoed only if they re-focus the button later.\nAfter: Button momentarily becomes a polite live region during the confirmation flash so SR engines announce 'copied' once when the text changes, then return to standard behavior when the original label is restored.",
"links": [
"https://github.com//pull/153",
"https://github.com//pull/153/files"
],
"forbidden": [
"raw secrets",
"raw logs",
"raw conversations",
"private chat IDs",
"session tokens",
"cookies",
"private repo maps",
"raw memory dumps",
"full compile JSON",
"scoring details"
]
},
"proposed_fix": {
"approach": "Inside copyText(), snapshot the button's existing aria-live attribute (if any), set aria-live='polite' for the 1.6s confirmation window, then restore the original aria-live state alongside the text reset.",
"files_expected": [
"app.js"
],
"tests_or_smoke": "Smoke: run the affected code path in the repo and confirm before\u2192after behavior change. Build-clean: python3 -m py_compile app.js or npx tsc --noEmit --skipLibCheck app.js."
},
"pr": {
"url": "#153",
"branch": "spark-compete/copy-button-aria-live-announcement",
"title_prefix": "[spark-compete]",
"author_github": "4gjnbzb4zf-sudo",
"body_must_include": [
"packet",
"team",
"pr_author",
"repo",
"actual_behavior",
"expected_behavior",
"repro_steps",
"before_after_proof",
"tests_or_smoke",
"duplicate_notes",
"risk_notes",
"review_claim"
]
},
"review_claim": {
"impact_claim": "low",
"evidence_types": [
"redacted_terminal_excerpt"
],
"duplicate_notes": "Searched open PRs and issues for the same defect; this fix is targeted to app.js.",
"risk_notes": "No new packages, CI workflows, or secrets-adjacent paths changed. Diff is bounded to app.js. Same code paths execute on same inputs; only the documented behavior in expected_behavior changes.",
"review_state_requested": "pr_review"
}
}

@4gjnbzb4zf-sudo

Copy link
Copy Markdown
Contributor Author

Copy-to-clipboard button has no SR confirmation

I was browsing sparkswarm.ai with VoiceOver on, ready to install. Tabbed to the "install on Mac/Linux" copy block, pressed Enter — the button visibly flashed "copied" but my screen reader said nothing. I waited, pressed Enter again to be sure, and again silence. Pasted into terminal — actually fine, the clipboard had the right text the first time. The site's primary conversion path is hidden from SR users behind a confirmation they can't perceive.

Bug

app.js copyText(text, btn) swaps btn.textContent to 'copied' for 1600ms then back, but the button never sets aria-live. The visual confirmation lands; the aural confirmation never does.

Fix

In copyText(), snapshot the existing aria-live value, set aria-live="polite" while the "copied" text is showing, and restore the original on reset. ~7-line patch in one file.

const origAriaLive = btn.getAttribute('aria-live');
btn.setAttribute('aria-live', 'polite');
btn.textContent = 'copied';
// ...
setTimeout(() => {
  btn.textContent = orig;
  if (origAriaLive === null) btn.removeAttribute('aria-live');
  else btn.setAttribute('aria-live', origAriaLive);
}, 1600);

Repro

# Sighted shortcut with axe DevTools:
#  Before: button has no aria-live; the text mutation is not announced.
#  After:  button has aria-live=polite for 1.6s; the text mutation IS announced once.

# Real SR:
#  Open with VoiceOver/NVDA → tab to any copy button → Enter
#  Before: silent
#  After:  "copied"

Sister precedent

Adopted PR Spark-Agent-Site__copy-text-surfaces-failure already touched copyText() to surface failures; this is the symmetric a11y fix for the success path. The site's board-inspector already uses aria-live="polite" (index.html:432), so the pattern is in-house.

Diff size

7 net-line patch, single file, no behavior change for sighted users.

@4gjnbzb4zf-sudo

Copy link
Copy Markdown
Contributor Author

TL;DR

app.js copyText() swaps a button's text to 'copied' for 1.6s then back, but the button never carries aria-live, so screen-reader users press Copy / hit Enter on the install command and hear no confirmation that anything happened. After the fix: Button momentarily becomes a polite live region during the confirmation flash so SR engines announce 'copied' once when the text changes, then return to standard behavior when the original label is restored.

What changes

Inside copyText(), snapshot the button's existing aria-live attribute (if any), set aria-live='polite' for the 1.6s confirmation window, then restore the original aria-live state alongside the text reset. Files touched: app.js.

Why this matters

Copy-the-installer is the site's primary conversion path: the hero CTA, the install panels, the swarm-section command snippets all funnel through copyText(). For sighted users the 1.6s 'copied' flash closes the loop; SR users hear silence and the most common next behavior is to press Enter again, then re-paste a stale clipboard. Adding aria-live='polite' to the button for the flash duration delivers a single 'copied' announcement and matches the visual confirmation already shown.

Reproduction (operator-side)

  1. Open the site with VoiceOver (macOS) or NVDA (Windows).
  2. Tab to the hero 'install on Mac/Linux' or 'install on Windows' copy block, focus on the button.
  3. Press Enter to trigger copyText().
  4. Observe: the visible button label briefly changes to 'copied' but no spoken feedback fires. A sighted user sees confirmation; SR user does not, and silently assumes the action failed.

Verification

Review app.js for the targeted change. Run the reproduction; expected outcome: Button momentarily becomes a polite live region during the confirmation flash so SR engines announce 'copied' once when the text changes, then return to standard behavior when the original label is restored.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant