Skip to content

[pull] main from MetaMask:main#790

Merged
pull[bot] merged 7 commits into
Reality2byte:mainfrom
MetaMask:main
May 27, 2026
Merged

[pull] main from MetaMask:main#790
pull[bot] merged 7 commits into
Reality2byte:mainfrom
MetaMask:main

Conversation

@pull
Copy link
Copy Markdown

@pull pull Bot commented May 27, 2026

See Commits and Changes for more details.


Created by pull[bot] (v2.0.0-alpha.4)

Can you help keep this open source service alive? 💖 Please sponsor : )

javiergarciavera and others added 7 commits May 27, 2026 18:17
…tor c… (#29128)

…omponents

- BridgeTokenSelector, TokenButton, TokenSelectorItem: Pressable →
TouchableOpacity

<!--
Please submit this PR as a draft initially.

Do not mark it as "Ready for review" until this PR meets the canonical
Definition of Ready For Review in `docs/readme/ready-for-review.md`.

In short: the template must be materially complete (not just section
titles
present), all status checks must be currently passing, and the only
expected
follow-up commits must be reviewer-driven.
-->

## **Description**

<!--
Write a short description of the changes included in this pull request,
also include relevant motivation and context. Have in mind the following
questions:
1. What is the reason for the change?
2. What is the improvement/solution?
-->

## **Changelog**

<!--
If this PR is not End-User-Facing and should not show up in the
CHANGELOG, you can choose to either:
1. Write `CHANGELOG entry: null`
2. Label with `no-changelog`

If this PR is End-User-Facing, please write a short User-Facing
description in the past tense like:
`CHANGELOG entry: Added a new tab for users to see their NFTs`
`CHANGELOG entry: Fixed a bug that was causing some NFTs to flicker`

(This helps the Release Engineer do their job more quickly and
accurately)
-->

CHANGELOG entry:

## **Related issues**

Fixes:

## **Manual testing steps**

```gherkin
Feature: my feature name

  Scenario: user [verb for user action]
    Given [describe expected initial app state]

    When user [verb for user action]
    Then [describe expected outcome]
```

## **Screenshots/Recordings**

<!-- If applicable, add screenshots and/or recordings to visualize the
before and after of your change. -->

### **Before**

<!-- [screenshots/recordings] -->

### **After**

<!-- [screenshots/recordings] -->

## **Pre-merge author checklist**

<!--
Every checklist item must be consciously assessed before marking this PR
as
"Ready for review". A checked box means you deliberately considered that
responsibility, not that you literally performed every action listed.

Unchecked boxes are ambiguous: they are not an implicit "N/A" and they
are not
a silent "skip". See `docs/readme/ready-for-review.md` for the full
checklist
semantics.
-->

- [ ] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [ ] I've completed the PR template to the best of my ability
- [ ] I've included tests if applicable
- [ ] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [ ] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

<!--
Reviewer checklist items follow the same semantics as the author
checklist: an
unchecked box is ambiguous, a checked box means the reviewer consciously
assessed that responsibility. See `docs/readme/ready-for-review.md`.
-->

- [ ] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [ ] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> UI-only changes to Bridge token list rendering and accessibility; no
auth, transactions, or API contract changes.
> 
> **Overview**
> Improves **Bridge token selector** scrolling performance and **iOS
VoiceOver** behavior without changing selection or balance logic.
> 
> **`BridgeTokenSelector`** tunes the token list:
`ESTIMATED_ITEM_HEIGHT` is **68** (documented from padding/avatar
sizes), and the `FlatList` gets **`initialNumToRender`**,
**`maxToRenderPerBatch`**, **`windowSize`**, and
**`removeClippedSubviews`** to cut over-rendering on long lists.
> 
> **`TokenSelectorItem`** wraps the row in **`React.memo`**, hoists
shared balance text styles, and sets **`accessible={false}`** on inner
`Box` layouts so the row’s **`TouchableOpacity`** stays the single
focusable control on iOS. Balance rows pass explicit `textVariant` /
`textColor` instead of spreading style objects.
> 
> **`TokenButton`** drops the `Box` wrapper: layout moves onto
**`TouchableOpacity`**’s `pillContainer` style so the pill is one
simpler touch target.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
7185cac. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->

---------

Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
…-7.79.0 (#30699)

## **Description**

Fixes World Cup/sports game cards that could show only two outcomes for
draw-capable moneyline games when one outcome had very low odds.

The shared market staleness filter removes outcomes priced at or below
5% or at or above 95%. That behavior is useful for multi-outcome
non-game cards, but it breaks game cards that need the complete
moneyline set. For example, Germany vs. Curacao has Germany, Draw, and
Curacao outcomes, but Curacao can be priced below 5%. Once that outcome
is filtered out, the card falls back to a binary path and the away-team
button can open the `No` token for the favorite instead of the underdog
moneyline.

This change skips stale-price outcome filtering and stale-price ranking
penalties for game markets. Closed markets and ended games are still
filtered out as before.

## **Changelog**

CHANGELOG entry: Fixed a bug where sports game cards could hide
low-probability outcomes and open the wrong prediction.

## **Related issues**

Fixes:
https://consensyssoftware.atlassian.net/browse/PRED-934?atlOrigin=eyJpIjoiZjVmNDJkY2I3NzBjNGQ4MjgwZWY5MjQ5ZjcyOTlkYWMiLCJwIjoiaiJ9

## **Manual testing steps**

```gherkin
Feature: World Cup game card outcomes

  Scenario: user opens a draw-capable World Cup game card with a low-probability away team
    Given the World Cup feed includes a game with home, draw, and away moneyline outcomes
    And one of the moneyline outcomes is priced at or below 5%

    When user views the game card
    Then the card shows all available moneyline outcomes

    When user taps the away-team prediction button
    Then the buy sheet opens for the away-team outcome, not the favorite team's No token
```

## **Screenshots/Recordings**

### **Before**

<img width="420" height="861" alt="Screenshot 2026-05-27 at 14 27 35"
src="https://github.com/user-attachments/assets/6ec940a0-5db6-4323-a7aa-58cb422c00a8"
/>


### **After**

<img width="420" height="875" alt="Screenshot 2026-05-27 at 14 27 49"
src="https://github.com/user-attachments/assets/6f277b93-5d88-4353-87e0-68588e88f944"
/>

## **Testing**

- `node .yarn/releases/yarn-4.14.1.cjs jest
app/components/UI/Predict/utils/marketStaleness.test.ts`

## **Pre-merge author checklist**

- [ ] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [ ] I've completed the PR template to the best of my ability
- [ ] I've included tests if applicable
- [ ] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [ ] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

- [ ] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [ ] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> Scoped to Predict visibility/ranking utilities; closed and ended games
remain hidden; non-game staleness behavior unchanged.
> 
> **Overview**
> **Game markets** with a `game` attachment are now exempt from
Predict’s stale-price outcome filtering (≤5% / ≥95%) and from
staleness-based feed ranking penalties, matching the existing
**highlighted** market behavior.
> 
> `getVisiblePredictMarket` returns the full market for open game
markets after the usual closed/expired checks, so moneyline sets (e.g.
home / draw / away) stay intact when an underdog is priced very low.
Non-game cards still drop “dead” outcomes and can be deprioritized in
the list.
> 
> Tests cover full outcome preservation on game cards and unchanged
ordering when a game market would otherwise be penalized.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
2ead89a. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
…ive for first-level sheets (#30696)

## **Description**

Corrects the elevated surface token used across bottom sheets and action
list
surfaces for the pure black dark mode initiative.

The initial implementation used `background.section` as the elevated
surface
color when `MM_PURE_BLACK_PREVIEW` is enabled. This was incorrect — the
design
token elevation hierarchy is `default > alternative > section >
subsection`,
so bottom sheets (the first level above the screen background) should
use
`background.alternative`, not `background.section`.

Updated `getElevatedSurfaceColor` and `useElevatedSurface` in
`app/util/theme/themeUtils.ts` to return `background.alternative` /
`bg-alternative`
in dark mode when pure black is active. All callsites (sheet containers
and
list rows inside sheets) are correctly covered by this single
correction.
## **Changelog**

<!--
If this PR is not End-User-Facing and should not show up in the
CHANGELOG, you can choose to either:
1. Write `CHANGELOG entry: null`
2. Label with `no-changelog`

If this PR is End-User-Facing, please write a short User-Facing
description in the past tense like:
`CHANGELOG entry: Added a new tab for users to see their NFTs`
`CHANGELOG entry: Fixed a bug that was causing some NFTs to flicker`

(This helps the Release Engineer do their job more quickly and
accurately)
-->

CHANGELOG entry:nuill

## **Related issues**


Fixes: https://consensyssoftware.atlassian.net/browse/TMCU-798

## **Manual testing steps**

```gherkin
Feature: Pure black elevated surface token correction

  Scenario: user opens bottom sheets with pure black flag enabled
    Given the app is in dark mode with MM_PURE_BLACK_PREVIEW=true
    When user opens Trade, Buy/Sell, Network, Fund, or Money sheets
    Then each sheet surface renders at background.alternative (#1a1a1a)
     And sheet surfaces are visibly elevated above the pure black background
     And light mode appearance is unchanged
```

## **Screenshots/Recordings**


https://github.com/user-attachments/assets/88edab80-ed64-499e-b9f5-3717b0d4eae0

### **Before**


https://github.com/user-attachments/assets/5a581895-bfac-40c3-bdc1-e8e243778896

### **After**


https://github.com/user-attachments/assets/88edab80-ed64-499e-b9f5-3717b0d4eae0

## **Pre-merge author checklist**

<!--
Every checklist item must be consciously assessed before marking this PR
as
"Ready for review". A checked box means you deliberately considered that
responsibility, not that you literally performed every action listed.

Unchecked boxes are ambiguous: they are not an implicit "N/A" and they
are not
a silent "skip". See `docs/readme/ready-for-review.md` for the full
checklist
semantics.
-->

- [x] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [x] I've completed the PR template to the best of my ability
- [x] I've included tests if applicable
- [x] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [\x] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

<!--
Reviewer checklist items follow the same semantics as the author
checklist: an
unchecked box is ambiguous, a checked box means the reviewer consciously
assessed that responsibility. See `docs/readme/ready-for-review.md`.
-->

- [x] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [x] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> Two-token swap behind an existing feature flag with no auth, data, or
API impact.
> 
> **Overview**
> When **`MM_PURE_BLACK_PREVIEW`** is on, pure-black dark mode now
treats **first-level elevated surfaces** (bottom sheets, action list
rows, etc.) as **`background.alternative`** / **`bg-alternative`**
instead of **`background.section`** / **`bg-section`**.
> 
> **`getElevatedSurfaceColor`** and **`useElevatedSurface`** in
`app/util/theme/themeUtils.ts` are the only code changes; existing
callers pick up the corrected token without further edits. Light mode
and non–pure-black behavior are unchanged.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
6c8cf7f. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
…I components (#30679)

## **Description**

Adds the reusable Predict portfolio UI components for PRED-899.

This PR is stacked on top of
`predict/PRED-902-create-shared-predict-portfolio-data-hook-and-derived-model`,
which introduces the shared `usePredictPortfolio` data/model hook used
by these components.

Included components:

- `PredictPortfolioModule` for the homepage balance/portfolio surface
- `PredictPortfolioSummary` for primary portfolio value and optional
P&L/available balance display
- `PredictPortfolioActions` and `PredictPortfolioAction` for Positions,
Add funds, and Withdraw actions
- `PredictPortfolio` test IDs and barrel exports

The module supports first-time, returning, loading, privacy mode,
claimable winnings, positions badge count, guarded
deposit/withdraw/claim flows, and amount-only P&L display when the
portfolio model omits a percent.

This PR intentionally does **not** wire the portfolio module into
`PredictFeed`, feature flag rendering, or confirmation navigation. That
integration will be handled in a follow-up stacked branch.

## **Changelog**

CHANGELOG entry: null

## **Related issues**

Fixes: https://consensyssoftware.atlassian.net/browse/PRED-899

Depends on: https://consensyssoftware.atlassian.net/browse/PRED-902

## **Manual testing steps**

```gherkin
Feature: Predict portfolio UI components

  Scenario: reusable portfolio module renders portfolio states
    Given the shared Predict portfolio hook returns first-time, returning, claimable, loading, or privacy-mode data

    When the Predict portfolio module is rendered
    Then it displays the expected value, optional P&L line, action row, positions badge, and claim CTA for that state
```

Manual app QA: N/A for this stacked PR because the components are not
integrated into the Predict feed in this branch.

## **Screenshots/Recordings**

N/A. This branch adds reusable components only; feed integration and
visual QA screenshots will be covered by the follow-up integration
branch.

### **Before**

N/A

### **After**


https://github.com/user-attachments/assets/b725df1e-4584-4aeb-b517-b71be9c5905c

## **Testing**

- `NODE_OPTIONS=--max-old-space-size=8192 node
.yarn/releases/yarn-4.14.1.cjs jest
app/components/UI/Predict/components/PredictPortfolio/PredictPortfolioModule.test.tsx
app/components/UI/Predict/components/PredictPortfolio/PredictPortfolioSummary.test.tsx
--runInBand --watchman=false --forceExit --silent --coverage=false`
- `node .yarn/releases/yarn-4.14.1.cjs lint:tsc`
- `git diff --check`

## **Pre-merge author checklist**

- [ ] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [ ] I've completed the PR template to the best of my ability
- [ ] I've included tests if applicable
- [ ] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [ ] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
- [ ] I've tested with a power user scenario
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics

## **Pre-merge reviewer checklist**

- [ ] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [ ] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> New UI and hook tweaks only; deposit/withdraw/claim reuse existing
guarded flows and the module is not yet integrated into the Predict
feed.
> 
> **Overview**
> Introduces reusable **Predict portfolio** UI for the homepage balance
surface: `PredictPortfolioModule` composes summary, Positions / Add
funds / Withdraw actions, and an optional claim CTA, wired through
`usePredictPortfolio`, privacy mode, `usePredictActionGuard`, and
deposit-wallet withdraw feature flags. **PredictPortfolioSummary** shows
portfolio value with optional unrealized P&L and available balance
(amount-only P&L when percent is omitted), loading skeletons, and masked
values in privacy mode.
> 
> **usePredictPortfolio** now enables account state when **portfolio
value** is positive (not only cash balance), and account state failures
no longer surface on the aggregate `error` field. New
`predict.portfolio.*` strings and test IDs support automation. Feed
integration is explicitly out of scope for this branch.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
781b9ca. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
…rd (#30663)

<!--
Please submit this PR as a draft initially.

Do not mark it as "Ready for review" until this PR meets the canonical
Definition of Ready For Review in `docs/readme/ready-for-review.md`.

In short: the template must be materially complete (not just section
titles
present), all status checks must be currently passing, and the only
expected
follow-up commits must be reviewer-driven.
-->

## **Description**
Migrate Card onboarding screens from navigator-rendered headers to
in-screen HeaderStandard (from @metamask/design-system-react-native).

**Why**: This is a prerequisite for migrating the Card navigation stack
from @react-navigation/stack (JS stack) to
@react-navigation/native-stack. Native stack on iOS 26 / iPhone 17 Pro
Max renders the system "liquid glass" navigation bar, which doesn't
match the Card screens' flat bg-background-default and breaks visual
consistency. By moving the header into each screen body, header styling
becomes navigator-type-agnostic — the follow-up native-stack PR can then
be a small, mechanical swap with no further header rework.

**What changed**:

1. All 9 Card onboarding screens now hide the navigator header
(headerShown: false, gestureEnabled: false) and render HeaderStandard
in-screen via OnboardingStep.
2. New useCardOnboardingNavigationHandlers hook centralizes the three
header behaviors:
- back — back arrow → goBack() (SignUp, ConfirmEmail, Complete)
- close-with-confirmation — close (X) → exit-confirmation Alert →
WALLET.HOME (SetPhoneNumber, ConfirmPhoneNumber, VerifyIdentity,
PersonalDetails, PhysicalAddress)
- close-direct — close (X) → straight to WALLET.HOME
(VerifyingVeriffKYC)
3. OnboardingNavigator simplified: removed cardDefaultNavigationOptions,
PostEmailNavigationOptions, KYCStatusNavigationOptions,
HeaderlessNavigationOptions factories. Replaced 11 per-screen options
with a single shared screenOptions={{ headerShown: false,
gestureEnabled: false }}.
4. KYCFailed and KYCPending are unchanged — they already used the
in-screen header pattern with their custom purple/dark backgrounds.
5. The exit-onboarding-button testID is preserved on the close button
(passed via closeButtonProps) so existing E2E selectors continue to
work.
6. Tests for the removed navigation-options factories were dropped;
equivalent coverage now lives in
useCardOnboardingNavigationHandlers.test.tsx.




## **Changelog**

<!--
If this PR is not End-User-Facing and should not show up in the
CHANGELOG, you can choose to either:
1. Write `CHANGELOG entry: null`
2. Label with `no-changelog`

If this PR is End-User-Facing, please write a short User-Facing
description in the past tense like:
`CHANGELOG entry: Added a new tab for users to see their NFTs`
`CHANGELOG entry: Fixed a bug that was causing some NFTs to flicker`

(This helps the Release Engineer do their job more quickly and
accurately)
-->

CHANGELOG entry: null

## **Related issues**

Fixes:

## **Manual testing steps**

```gherkin
Feature: Card Onboarding in-screen header
  Scenario: User taps back from SignUp / ConfirmEmail / Complete
    Given the user is on a Card Onboarding screen with a back-only header
    When user taps the back arrow in the header
    Then the user is returned to the previous screen
  
Scenario: User taps close from a post-email screen
    Given the user is on SetPhoneNumber, ConfirmPhoneNumber, VerifyIdentity, PersonalDetails, or PhysicalAddress
    When user taps the close (X) icon in the header
    Then an exit confirmation Alert is displayed
    When user taps the destructive "Exit" action in the Alert
    Then the user is navigated to Wallet Home
  
Scenario: User taps close on VerifyingVeriffKYC
    Given the user is on the VerifyingVeriffKYC screen
    When user taps the close (X) icon in the header
    Then the user is navigated directly to Wallet Home with no confirmation
  
Scenario: KYC status screens render their own header
    Given the user reaches KYCFailed or KYCPending
    Then the screen renders with its custom purple / dark header (unchanged from main)
  
Scenario: Returning user resumes onboarding
    Given the user has an in-progress onboarding session and returns to the Card flow
    When OnboardingNavigator mounts
    Then the "Keep going" modal is shown over the resolved initial route
  
Scenario: Header background matches screen background
    Given the user is on any Card Onboarding screen with HeaderStandard
    Then the header background matches the screen body (no glass / material navigation bar)
    And the back / close icons sit inside the screen body, not the navigator chrome

```

## **Screenshots/Recordings**

<!-- If applicable, add screenshots and/or recordings to visualize the
before and after of your change. -->

### **Before**
<img width="392" height="768" alt="Card Before"
src="https://github.com/user-attachments/assets/7fd3beac-07e2-4bc2-b780-a758b8ac99b1"
/>


### **After**
<img width="392" height="768" alt="Card Header After"
src="https://github.com/user-attachments/assets/2806a648-50fb-433e-b04a-1abc6d67bb8b"
/>

Android test:


https://github.com/user-attachments/assets/97923e40-38ea-4dbe-90f7-aa21ed46aacf


<!-- [screenshots/recordings] -->

## **Pre-merge author checklist**

<!--
Every checklist item must be consciously assessed before marking this PR
as
"Ready for review". A checked box means you deliberately considered that
responsibility, not that you literally performed every action listed.

Unchecked boxes are ambiguous: they are not an implicit "N/A" and they
are not
a silent "skip". See `docs/readme/ready-for-review.md` for the full
checklist
semantics.
-->

- [x] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [x] I've completed the PR template to the best of my ability
- [x] I've included tests if applicable
- [x] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [x] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

<!--
Reviewer checklist items follow the same semantics as the author
checklist: an
unchecked box is ambiguous, a checked box means the reviewer consciously
assessed that responsibility. See `docs/readme/ready-for-review.md`.
-->

- [x] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [x] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> UI and navigation chrome refactor with preserved exit flows and E2E
testIDs; no auth, payment, or data-model changes.
> 
> **Overview**
> Card onboarding moves header chrome from the stack navigator into each
screen via **`OnboardingStep`** and design-system **`HeaderStandard`**,
so headers match the flat onboarding background and are ready for a
future native-stack swap.
> 
> **`OnboardingNavigator`** drops per-screen header factories
(`PostEmailNavigationOptions`, `KYCStatusNavigationOptions`, etc.) in
favor of shared **`headerShown: false`** / **`gestureEnabled: false`**.
A new **`useCardOnboardingNavigationHandlers`** hook centralizes
**back**, **close with exit alert → wallet home**, and **close direct →
wallet home**; each step passes a **`headerMode`**. The
**`exit-onboarding-button`** testID is kept on close actions. Navigator
option tests were removed in favor of hook unit tests; sticky-step
layout no longer sets a fixed iOS **`keyboardVerticalOffset`**.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
f6623ab. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
<!--
Please submit this PR as a draft initially.

Do not mark it as "Ready for review" until this PR meets the canonical
Definition of Ready For Review in `docs/readme/ready-for-review.md`.

In short: the template must be materially complete (not just section
titles
present), all status checks must be currently passing, and the only
expected
follow-up commits must be reviewer-driven.
-->

## **Description**

This attempts to fix what was intended to be fixed in PR #30419 but for
some reason that PR did not work - to ensure that a source token is used
when opening an Ondo swap from Rewards. It also updates the button text
to say "Trade now" instead of "Open Position."

## **Changelog**

<!--
If this PR is not End-User-Facing and should not show up in the
CHANGELOG, you can choose to either:
1. Write `CHANGELOG entry: null`
2. Label with `no-changelog`

If this PR is End-User-Facing, please write a short User-Facing
description in the past tense like:
`CHANGELOG entry: Added a new tab for users to see their NFTs`
`CHANGELOG entry: Fixed a bug that was causing some NFTs to flicker`

(This helps the Release Engineer do their job more quickly and
accurately)
-->

CHANGELOG entry: null

## **Related issues**

Fixes: n/a

## **Manual testing steps**

```gherkin
Feature: my feature name

  Scenario: user [verb for user action]
    Given [describe expected initial app state]

    When user [verb for user action]
    Then [describe expected outcome]
```

## **Screenshots/Recordings**

<!-- If applicable, add screenshots and/or recordings to visualize the
before and after of your change. -->

### **Before**

<!-- [screenshots/recordings] -->

### **After**

<!-- [screenshots/recordings] -->

## **Pre-merge author checklist**

<!--
Every checklist item must be consciously assessed before marking this PR
as
"Ready for review". A checked box means you deliberately considered that
responsibility, not that you literally performed every action listed.

Unchecked boxes are ambiguous: they are not an implicit "N/A" and they
are not
a silent "skip". See `docs/readme/ready-for-review.md` for the full
checklist
semantics.
-->

- [x] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [x] I've completed the PR template to the best of my ability
- [x] I've included tests if applicable
- [x] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [x] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [ ] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

<!--
Reviewer checklist items follow the same semantics as the author
checklist: an
unchecked box is ambiguous, a checked box means the reviewer consciously
assessed that responsibility. See `docs/readme/ready-for-review.md`.
-->

- [ ] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [ ] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> **Low Risk**
> Copy and Rewards swap prefill logic only; changes are localized with
new unit tests and no auth or payment impact.
> 
> **Overview**
> Renames the opted-in, no-positions Ondo campaign CTA from **Open
Position** to **Trade now** via `rewards.campaign_details.open_position`
in `en.json`, with matching test and comment updates.
> 
> Fixes **open position** swaps from Rewards by resolving default source
tokens through a new `getOndoOpenPositionSourceToken` helper: chain
defaults are keyed by hex (`0x1` → USDC, `0x38` → USDT) instead of
CAIP-only map lookups, and the helper accepts hex or `eip155:` chain IDs
(including after-hours confirm). USDY balance preference is unchanged;
tests cover BNB/USDT and the helper edge cases.
> 
> <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit
be88b88. Bugbot is set up for automated
code reviews on this repo. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
## **Description**
Migrate the Card Onboarding flow off the JS stack navigator and
react-navigation header in favor of native stack:

- `app/components/UI/Card/routes/OnboardingNavigator.tsx` now uses
`createNativeStackNavigator` from `@react-navigation/native-stack`
instead of `createStackNavigator`. The navigator-level header is hidden
for every screen (`headerShown: false`, `gestureEnabled: false`), so
screens own their own header chrome.


## **Changelog**

<!--
If this PR is not End-User-Facing and should not show up in the
CHANGELOG, you can choose to either:
1. Write `CHANGELOG entry: null`
2. Label with `no-changelog`

If this PR is End-User-Facing, please write a short User-Facing
description in the past tense like:
`CHANGELOG entry: Added a new tab for users to see their NFTs`
`CHANGELOG entry: Fixed a bug that was causing some NFTs to flicker`

(This helps the Release Engineer do their job more quickly and
accurately)
-->

CHANGELOG entry:null

## **Related issues**

Fixes:

## **Manual testing steps**

```gherkin
Feature: Card Onboarding header & navigation
Scenario: Back navigation on early onboarding screens
    Given I am on the Card Onboarding "Sign Up", "Confirm Email", or "Complete" screen
    When I tap the back arrow in the header
    Then the navigator goes back to the previous screen
  
Scenario: Exit with confirmation on post-email screens
    Given I am on "Set Phone Number", "Confirm Phone Number", "Verify Identity", "Personal Details", or "Physical Address"
    When I tap the close button in the header
    Then a confirmation alert appears asking me to confirm exiting onboarding
    When I confirm exit
    Then I am navigated to Wallet Home
  
Scenario: Exit directly from KYC status screen
    Given I am on the "Verifying Veriff KYC" screen
    When I tap the close button in the header
    Then I am navigated directly to Wallet Home without a confirmation alert
  
Scenario: Keyboard does not obscure inputs
    Given I am on any onboarding screen with a text input
    When I focus the input and the keyboard opens
    Then the input remains visible and the sticky action button (if any) stays above the keyboard
  
Scenario: Resume incomplete onboarding (regression)
    Given I am a returning user with incomplete onboarding
    When I re-enter the Card flow
    Then the "Keep going" modal is shown and routes me to the correct resume step
```

## **Screenshots/Recordings**

<!-- If applicable, add screenshots and/or recordings to visualize the
before and after of your change. -->

### **Before**
<img width="328" height="676" alt="card onboarding before"
src="https://github.com/user-attachments/assets/81f6ec2d-e3a8-439a-9bf0-52ce4b47ae2b"
/>

### **After**
<img width="342" height="744" alt="Card Onboarding Navigation after"
src="https://github.com/user-attachments/assets/26c198bb-d39c-40b0-ace0-3de1c467965e"
/>

Android

https://github.com/user-attachments/assets/d85c4de6-514d-4186-a792-309a0e4452a2

<!-- [screenshots/recordings] -->

## **Pre-merge author checklist**

<!--
Every checklist item must be consciously assessed before marking this PR
as
"Ready for review". A checked box means you deliberately considered that
responsibility, not that you literally performed every action listed.

Unchecked boxes are ambiguous: they are not an implicit "N/A" and they
are not
a silent "skip". See `docs/readme/ready-for-review.md` for the full
checklist
semantics.
-->

- [x] I've followed [MetaMask Contributor
Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile
Coding
Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md).
- [x] I've completed the PR template to the best of my ability
- [x] I've included tests if applicable
- [x] I've documented my code using [JSDoc](https://jsdoc.app/) format
if applicable
- [x] I've applied the right labels on the PR (see [labeling
guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)).
Not required for external contributors.

#### Performance checks (if applicable)

- [x] I've tested on Android
  - Ideally on a mid-range device; emulator is acceptable
- [ ] I've tested with a power user scenario
- Use these [power-user
SRPs](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/edit-v2/401401446401?draftShareId=9d77e1e1-4bdc-4be1-9ebb-ccd916988d93)
to import wallets with many accounts and tokens
- [ ] I've instrumented key operations with Sentry traces for production
performance metrics
- See [`trace()`](/app/util/trace.ts) for usage and
[`addToken`](/app/components/Views/AddAsset/components/AddCustomToken/AddCustomToken.tsx#L274)
for an example

For performance guidelines and tooling, see the [Performance
Guide](https://consensyssoftware.atlassian.net/wiki/spaces/TL1/pages/400085549067/Performance+Guide+for+Engineers).

## **Pre-merge reviewer checklist**

<!--
Reviewer checklist items follow the same semantics as the author
checklist: an
unchecked box is ambiguous, a checked box means the reviewer consciously
assessed that responsibility. See `docs/readme/ready-for-review.md`.
-->

- [x] I've manually tested the PR (e.g. pull and build branch, run the
app, test code being changed).
- [x] I confirm that this PR addresses all acceptance criteria described
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.

<!-- CURSOR_SUMMARY -->
---

> [!NOTE]
> <sup>[Cursor Bugbot](https://cursor.com/bugbot) is generating a
summary for commit 1dc693e. Configure
[here](https://www.cursor.com/dashboard/bugbot).</sup>
<!-- /CURSOR_SUMMARY -->
@pull pull Bot locked and limited conversation to collaborators May 27, 2026
@pull pull Bot added the ⤵️ pull label May 27, 2026
@pull pull Bot merged commit de13f1e into Reality2byte:main May 27, 2026
0 of 2 checks passed
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants