Skip to content

Streaming widget: light-theme parity and button/primitive alignment (#255) - #256

Merged
L03TJ3 merged 4 commits into
mainfrom
copilot/goodbounty-patch-streaming-widget-light-theme
Oct 30, 2026
Merged

L03TJ3 merged 4 commits into
mainfrom
copilot/goodbounty-patch-streaming-widget-light-theme

Conversation

Copilot AI commented Oct 15, 2026 •

Copy link
Copy Markdown
Contributor

@goodwidget/streaming-widget was effectively dark-only in Storybook (#254). It also routed every button through a local ActionButton that hardcoded minWidth={100}, outside the compactButtonProps convention the other widgets use. This PR aligns the widget with that convention, adds light/dark parity to the stories, and runs every Playwright flow in both themes.

Related: #26, #36, #254

Widget (packages/streaming-widget)

  • Removed the ActionButton wrapper. All 22 call sites now render Button directly.
  • Added a package-local compactButtonProps in components/shared.tsx, mirroring ai-credits and superfluid-campaign, and spread it on every size="sm" button:
    <Button size="sm" {...compactButtonProps} onPress={onRefresh}>
  • Primary CTAs now use fullWidth at the default size, as in governance and citizen-claim:
    • Connect Wallet (WalletGate)
    • Set / Update Stream (SetStreamForm)
  • In SetStreamForm, Reset moved below the CTA as a compact full-width secondary button, replacing the shared row.
  • Primitive audit found no local reimplementations. Badge, Separator, Spinner, Input, Select, TokenAmount, AddressDisplay and WidgetTabs all come from @goodwidget/ui.

Storybook

  • Story shell: StoryShell in helpers/streamingWidgetStories.tsx now passes the widget's defaultTheme to its outer GoodWidgetProvider. Previously that provider was always dark, so light renders sat inside a dark frame. The extra light provider wrapped around LightThemePopulatedStory is removed as redundant.
  • Theme overrides story (StreamingWidgetThemeOverrides.stories.tsx), following GovernanceWidgetThemeOverrides.stories.tsx:
    • Each control writes both the light_* and dark_* key for Button, StreamRow and BalanceCard.
    • Adds a defaultTheme radio control.
    • Drops the hard-pinned defaultTheme="dark" and the withDefaultPreset decorator.
  • Rename: StreamingWidget.stories.tsx is now StreamingWidgetShowcase.stories.tsx. The MDX import is updated; the story ID is unchanged.

Playwright (tests/widgets/streaming-widget/states.spec.ts)

  • Every existing flow now runs once per theme via args=defaultTheme:<theme>.
  • A new test checks that the theme-overrides playground shows both light_* and dark_* keys.
  • Screenshots are now written to test-results/{dark,light}/, and the old untagged screenshots are removed.

Open items for review

  • Light-theme button contrast:

    • White on light_Button is about 2.4:1.
    • $primary secondary text on the light background is about 2.3:1.

    Both come from the shared light_Button preset in packages/ui, which GovernanceWidget uses as well. Changing packages/ui is out of scope, so this needs a separate follow-up.

  • SUP Reserve off Base: the reserve card still renders its data instead of being hidden or disabled. Changing that is data-layer behaviour ([GoodBounty] Finalize Streaming Widget PR #36) and out of scope.

  • Pool refresh after receipt: not covered by Storybook fixtures; it needs a live wallet.

Functional validation (Storybook QA fixtures)

Flow Light Dark Evidence
Streams: empty / populated ✅ ✅ sw-05, sw-07
Streams: create / update / cancel ✅ ✅ sw-08–sw-11, sw-28–sw-30
Streams: incoming / outgoing / all ✅ ✅ sw-07
Pools: empty / populated ✅ ✅ sw-12, sw-23
Pools: Pending / Done / Failed badges ✅ ✅ sw-13–sw-15 (refresh after receipt not covered)
Balances: G$ / SUP ✅ ✅ sw-02, sw-04, sw-16
Balances: SUP Reserve lockers / inline error ✅ ✅ sw-16, sw-06
Balances: off Base ⚠️ ⚠️ sw-17 (reserve still shown, #36)
History ✅ ✅ sw-22, sw-26, sw-27
Disconnected / unsupported chain ✅ ✅ sw-01, sw-03
Mobile (390px) / desktop (1280px) ✅ ✅ sw-18, sw-19

Copilot AI balanced review requested due to automatic review settings October 15, 2026 15:55

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot wasn't able to review any files in this pull request. Check if the Files changed in this pull request are included in default exclusions.

…Button, refresh screenshots (#255)

Co-authored-by: blueogin <43612769+blueogin@users.noreply.github.com>
Copilot AI changed the title [WIP] Add light-theme parity and UI structure alignment for streaming widget Streaming widget: light-theme parity and button/primitive alignment (#255) Oct 15, 2026
Copilot AI requested a review from blueogin October 15, 2026 16:07
@Khemmie-Ray

Copy link
Copy Markdown

QA report: Streaming widget full exploratory sweep (#263)

Linked PR: #256

  • Commit: 4625089809ad5e50b232bce8cf27a2f9dd162de2 on copilot/goodbounty-patch-streaming-widget-light-theme
  • Setup: [Browser + version], macOS M2 Pro, Node v26.9.0, pnpm v12.14.0. Commands: pnpm install, pnpm build, pnpm storybook
  • Verdict: Hold — three Fails open (wrong-chain overflow, outlined-button labels, SUP Reserve off-Base), none blocking but all visible.

Storybook fixtures only. No live wallet or transactions used.

Case results

Results: Pass / Fail / Blocked / Not run

Connection / navigation

ID Case Dark Light Observation and evidence Finding / next action
C-01 no-wallet: disconnected wallet gate Pass Pass Gate card and Connect Wallet button render in both themes; gate stays across all four tabs. Connect Wallet click does nothing, as expected: fixture uses a mock adapter where connect is a no-op. No console errors. None
C-02 wrong-chain: unsupported network prompt Fail Fail "Unsupported network" card renders with Switch to Celo / Switch to Base buttons. "Switch to Base" overflows the card's right edge at 390px. See FIND-01
C-03 populated-state: tab navigation Streams / History / Pools / Balances Pass Pass Streams and History both show populated data with an accurate filter option. Outlined filter buttons lose their label on hover/press. See FIND-02

Streams list

ID Case Dark Light Observation and evidence Finding / next action
S-01 loading-state: streams + history loading Pass Pass Loading state renders in both themes, consistent across both tabs. None
S-02 empty-state: streams + history empty Pass Pass Empty state renders in both themes, consistent across streams and history. See FIND-02
S-03 error-state: error + retry, streams + history Pass Pass Error state renders in both themes, consistent across streams and history. See FIND-02
S-04 populated-state: incoming / outgoing / all filters Pass Pass Filters work for incoming and outgoing in both themes. See FIND-02
S-05 Stream details expand / collapse Pass Pass Expand renders populated data in both themes; collapse keeps a concise summary. See FIND-02
S-06 History: active filter / ended filter Pass Pass Filters work for active and ended in both themes. See FIND-02

Create / update / cancel stream

ID Case Dark Light Observation and evidence Finding / next action
F-01 create-update-invalid-input: validation messaging, frequency dropdown options Pass Pass Validation message shows for an invalid recipient address, but a zero-value input produces none. Confirm whether zero-value should be rejected; if so, missing validation is a minor gap.
F-02 create-update-pending Pass Pass Loading state signifies the pending state and renders in both themes. None
F-03 create-update-success Pass Pass Success message is visible. See FIND-02
F-04 create-update-failure Pass Pass Failure message is visible. See FIND-02
F-05 cancel-stream-pending Pass Pass Loading state depicts pending in both themes. None
F-06 cancel-stream-failure Pass Pass Failure message and cancel button are visible. See FIND-02
F-07 update-stream-form Pass Pass Form renders properly in both themes. None

Pools

ID Case Dark Light Observation and evidence Finding / next action
P-01 pool-claim-state: claimable amount + claim button Pass Pass Claimable amount and button render in both themes. See FIND-02
P-02 pool-connected-state: connected, no claim/connect actions Pass Pass Connected state is visible; no claim or connect action present, only a disconnect button. None
P-03 pool-claim-pending Pass Pass Pending badge is visible in both themes. None
P-04 pool-claim-success Pass Pass Done badge is visible in both themes. None
P-05 pool-claim-error Pass Pass Error message and failed badge render in both themes. None
P-06 pool-claimable-amount-error + retry → loading Pass Pass Error message and a retry button that leads to a loading state render in both themes. See FIND-02

Balances

ID Case Dark Light Observation and evidence Finding / next action
B-01 base-sup-balance-and-reserve: SUP balance + reserve locker (available/staked) Pass Pass Base balance and reserve locker address are visible in both themes. None
B-02 non-base-sup-reserve-disabled: off-Base behavior Fail Fail SUP Balance and SUP Reserve cards render identically on Celo (chain 42220) and Base (chain 8453), both labelled read-only Base. Only the Super Token Balance tracks the connected chain (712.1 SUP on Base vs 128.5 G$ on Celo); the reserve section does not change or disable off-Base. Tracked as K-02 / GoodWidget #36. See K-02. Confirm expected off-Base behavior (hide vs disable vs read-only), then gate the reserve cards on chain === Base if they should not show off-Base.
Image

Image |

Theme / layout

ID Case Dark Light Observation and evidence Finding / next action
T-01 Theme-overrides playground: light_* and dark_* keys both register Pass Pass With a brand preset applied (Teal, Cobalt), overrides register in both themes: dark mode picks up the dark_* keys and light mode the light_* keys. Neither prefix is dropped and values do not bleed across themes. None
T-02 populated-state at 390px (mobile) Pass Pass Content renders appropriately within this viewport. None
T-03 populated-state at 1280px (desktop) Pass Pass Content renders appropriately within this viewport. None
T-04 Other widths (note breakpoints that break) Fail Fail wrong-chain fixture breaks at 390px (Switch to Base overflow). See FIND-01

Known open items from #256

Item Status Evidence
K-01 Light-theme button/text contrast (white on light_Button, $primary secondary text) Still reproducible — measured ratios: 2.4:1, 2.3:1 (both below WCAG AA: 4.5:1 text, 3:1 UI). From the shared packages/ui preset, so also affects GovernanceWidget. See FIND-03
K-02 SUP Reserve off-Base still renders data (#36) Still reproducible — renders read-only Base data on Celo instead of hiding/disabling; identical across chains. See B-02. B-02 screenshots
K-03 Pool refresh after receipt Not run: requires live wallet and real receipt, not coverable in Storybook. Alternative: verify via testnet wallet against a live deployment, or an E2E test with a forked-chain/mocked receipt event.

Findings

FIND-01: Switch to Base button overflows the Unsupported network card

  • Case / impact: C-02, T-04, both themes, at 390px. Button breaks out of its container; layout looks broken on the network-switch prompt.
  • Reproduction steps: Open wrong-chain story, set viewport to 390px.
  • Expected vs actual: Expected both buttons to fit inside the card (wrap or shrink when space is tight). Actual: "Switch to Base" extends past the card border.
  • Evidence:
Image

FIND-02: Outlined buttons lose their label in hover / pressed states

  • Case / impact: C-03, S-02, S-03, S-04, S-05, S-06, F-03, F-04, F-06, P-01, P-06, both themes. Button labels become invisible when interacted with, so users can't tell what the button does.
  • Instances:
Button Location Story Trigger
Connect Pools pool-claim-state pressed / focus
Refresh History populated-state pressed / focus
Update Streams → expanded stream populated-state pressed / focus
All / Active / Ended filters History empty-state pressed / focus
All / Active / Ended filters History error-state hover
All / Incoming / Outgoing filters Active streams populated-state hover
Reset Streams → create/update create-update-success hover
Retry / Connect Pools → claimable amount error pool-claimable-amount-error hover
  • Reproduction steps: Open populated-state, go to History, press Refresh. Or open error-state, go to History, hover over the All / Active / Ended filter.
  • Expected vs actual: Expected labels to stay readable in every state. Actual: background fills with the primary color while the label stays primary-colored, so the text disappears.
  • Evidence: [before] Image

[after] Image

FIND-03: Light-theme contrast below WCAG AA (shared preset, do not fix here)

  • Case / impact: Light theme. White on light_Button ≈ 2.4:1 and $primary secondary text ≈ 2.3:1, both below WCAG AA (4.5:1 for text, 3:1 for UI components). Originates in the shared packages/ui preset, so it also affects GovernanceWidget.
  • Reproduction steps: Open any light-theme story with a primary button / secondary text and measure foreground-to-background contrast.
  • Expected vs actual: Expected ≥ 4.5:1 for text. Actual: 2.4:1 and 2.3:1.
  • Finding / next action: Confirmed, do not fix in this widget. Raise against the shared packages/ui preset so the correction covers both GoodWidget and GovernanceWidget.
  • Evidence: [add contrast-checker screenshots if available]

Exploratory notes

  • Wrong chain: badge shows the raw chain ID ("Chain 1") rather than a network name.

Verdict

Hold for the tested Storybook scope.

Remaining gaps: Live transactions and pool refresh after a real receipt (K-03) are not verified by Storybook. No cases Blocked; K-03 is the only Not run.

L03TJ3 commented Oct 30, 2026

Copy link
Copy Markdown
Contributor

@copilot please pick up the UI fixes:

  1. Fix the unsupported-network prompt so both “Switch to Celo” and “Switch to Base” buttons stay inside the card at 390px.
  2. Keep outlined/secondary button labels readable on hover, focus and press, including filters, Refresh, Update, Reset, Retry and Connect.

Add focused regression tests for both fixes in light and dark themes, and verify the mobile layout and interactive button states. Please keep this task limited to these two UI fixes.

…ry button labels readable in interactive states

Co-authored-by: L03TJ3 <6606028+L03TJ3@users.noreply.github.com>

Copilot AI commented Oct 30, 2026

Copy link
Copy Markdown
Contributor Author

@copilot please pick up the UI fixes:

  1. Fix the unsupported-network prompt so both “Switch to Celo” and “Switch to Base” buttons stay inside the card at 390px....

Both UI fixes are in 516284a.

  1. Switch-network buttons: the button row in the "Unsupported network" card now wraps. At 390px, "Switch to Celo" and "Switch to Base" sit on two rows inside the card. Before, "Switch to Base" ran about 57px past the card edge.
  2. Outlined button labels: hover, press and focus used to fill these buttons with the brand colour, which is the same colour as the label, so the text vanished. A new secondaryButtonStateProps in shared.tsx keeps the fill transparent and highlights the border instead. It covers every secondary button: the filters, Refresh, Update, Reset, Retry, Connect and Disconnect.

I added two Playwright tests that run in both light and dark:

  • One checks that both switch buttons stay inside the card at 390px.
  • One checks label contrast on hover, press and keyboard focus for each of those buttons.

Both tests fail without the fix: the button overflows (right edge at 395px, card ends at 338px) and the hover contrast is 1:1. With the fix the full streaming suite passes 38/38. The new screenshots are sw-32-wrong-chain-mobile and sw-33-secondary-button-hover, in both themes.

At rest, the outlined labels in light theme are still about 2.3:1. That colour comes from the shared light_Button theme in packages/ui, so changing it is outside this fix.

Copilot AI requested a review from L03TJ3 October 30, 2026 14:57
@L03TJ3

L03TJ3 commented Oct 30, 2026

Copy link
Copy Markdown
Contributor

@Khemmie-Ray Thanks QA reported accepted.
For the remainder of points raised not covered by copilot follow-up:

  • Base and sup reserve balanceshould be visible, regardless of chain active connection
  • The 0 value is a wrongly tested flow, but not reproducible in a the production flow
  • contrast ratio is nitpicking, not resolving right now

So you can go ahead into the gardens pool and request your payment.
Don't remember if you already did bounties, but for reference: https://docs.gooddollar.org/for-developers/contributing/open-source-contributors/payments-for-reviews-contributors-and-qa

The instructions for payments are at the bottom of the page.
The reward distribution is not relevant. as per qa request, including 50K G$ bonus for the UI bugs, 250K G$'s can be requested.

Make sure to use a verified G$ wallet.
Thanks for the contribution 💯

@L03TJ3
L03TJ3 marked this pull request as ready for review October 30, 2026 15:23
@L03TJ3
L03TJ3 requested a review from a team October 30, 2026 15:23
…goodbounty-patch-streaming-widget-light-theme
@L03TJ3

L03TJ3 commented Oct 30, 2026

Copy link
Copy Markdown
Contributor

Tests failing due to some timeout in claim widget. needs follow up, but merging this PR as not related to the streaming widget

@L03TJ3
L03TJ3 merged commit 94750c2 into main Oct 30, 2026
7 of 8 checks passed

This branch was successfully deployed

2 active deployments
preview-storybook — 1cb8cc2f Deployed Oct 30, 2026 by L03TJ3 via preview #504
internal — 1cb8cc2f Deployed Oct 30, 2026 by L03TJ3 via authorize-preview #504
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.

[GoodBounty-Patch] Streaming widget: light-theme parity and UI structure alignment

5 participants