chore(runway): cherry-pick fix(predict): keep time-slot scroll anchored left when live slot expires cp-7.81.0#31423
Merged
Conversation
…ed left when live slot expires cp-7.81.0 (#31231) ## **Description** This PR bundles four UI/behavior fixes on the Predict **crypto up/down** details screen (plus one shared positions tweak). All changes are confined to `app/components/UI/Predict/`. **1. Time-slot picker loses its left anchor when the live slot expires (primary fix)** When the live time slot expired and rolled to the next window, the horizontal `TimeSlotPicker` no longer kept the live/selected pill anchored at the left. Root cause: the auto-scroll read pill x-coordinates from a cached `pillPositions` map that (1) retained stale entries for markets that had been filtered out, and (2) was read by a fixed 50ms settle timer that raced ahead of React Native's async re-layout — so `scrollTo` used the pre-shift offset and over-scrolled. - Prune `pillPositions` to only currently-rendered markets whenever `markets` changes. - Re-run the settle-delay anchor on the ordered `marketsKey` so a left shift re-anchors even when the resolved selection is unchanged. - Re-anchor immediately when the selected pill reports a new layout `x`, beating the timer/layout race. - Adds a regression test that reproduces the expiry race (verified failing pre-fix, passing post-fix). **2. Even spacing around the time-slot picker** The picker is a flush `h-11` container with no vertical padding of its own, so the gap above (title `pb-3` = 12px) and below (price summary `pt-5` = 20px) were uneven. Changed the price-summary top padding `pt-5 → pt-3` so the picker has equal 12px above and below. **3. Centered separator dot in positions rows** The `Up/Down · entry` separator dot was baseline-glued to the entry label via a `' · '` string, so it sat slightly off-center. Split it into its own `Text` node so it aligns optically in the center-aligned row. **4. Remove the `$100 → $X` payout preview from the up/down CTA + grow the chart** Removed the payout estimate under the buy buttons on the crypto up/down details page by no longer passing `showPayoutEstimate` to the shared `PredictMarketDetailsActions`. The prop, formatter, and gated rendering remain intact on that component for any other surface that wants the preview (none currently enable it), so the change is regression-safe. The freed vertical space is reclaimed by growing the with-positions chart height (ratio `0.4 → 0.44`, max `380 → 430`) so the chart fills the gap above the sticky actions while keeping the first position row visible and the rest scrollable. ## **Changelog** CHANGELOG entry: Fixed the Predict crypto up/down time-slot selector so the live slot stays anchored to the left when it rolls to the next window, evened out the spacing around the selector, and removed the payout estimate from the buy buttons to give the price chart more room. ## **Related issues** Refs: No external ticket — incremental UX polish on the Predict crypto up/down details screen reported during QA review (live-slot scroll anchoring regression, uneven selector spacing, off-center separator dot, payout-preview removal + chart sizing). ## **Manual testing steps** ```gherkin Feature: Predict crypto up/down details screen Scenario: Live time slot stays anchored left when it expires Given I am on a crypto up/down market details screen And the live time slot is the left-most pill in the selector When the live slot expires and the next slot becomes live Then the new live slot is anchored to the left edge of the selector And the selector is not over-scrolled or visually shifted Scenario: Time-slot selector is evenly spaced Given I am on a crypto up/down market details screen Then the vertical space above and below the time-slot selector is equal Scenario: Separator dot is centered in a position row Given I am on a crypto up/down market details screen And I hold at least one position in the series Then the dot between the outcome label and the entry price is vertically centered Scenario: No payout preview under the buy buttons and chart fills the space Given I am on a crypto up/down market details screen Then no "$100 -> $..." payout estimate is shown under the Up and Down buttons And the price chart uses the freed space above the sticky action buttons Scenario: First position visible and the rest scroll Given I am on a crypto up/down market details screen And I hold more positions than fit on screen Then the first position row is visible above the sticky action buttons And the remaining position rows are reachable by scrolling ``` ## **Screenshots/Recordings** ### **Before** N/A — author to attach device capture before marking Ready for review (changes are visual layout tweaks on the crypto up/down details screen that need a simulator/device to record). ### **After** N/A — author to attach device capture before marking Ready for review. ## **Pre-merge author checklist** - [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 - [x] 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 - [x] 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** > Predict UI-only changes in TimeSlotPicker and crypto up/down details; scroll logic is covered by new tests with no auth or data-path impact. > > **Overview** > Fixes **Predict crypto up/down** layout and **TimeSlotPicker** scroll behavior when a live slot rolls off. > > **Time slot picker:** When the live pill disappears and the list shifts left, horizontal scroll no longer drifts off the left edge. Stale `pillPositions` entries are pruned, anchoring re-runs on `marketsKey` changes, and the selected pill’s `onLayout` re-scrolls immediately so a 50ms timer doesn’t win a race against re-layout. Regression tests cover initial anchor and post-expiry re-anchor. > > **Details screen polish:** Price-summary top padding is tightened (`pt-5` → `pt-3`) so spacing above/below the picker matches. With positions, the chart grows (ratio **0.44**, max **430px**) after dropping the buy-button payout estimate (`showPayoutEstimate` no longer passed). **Position rows:** the `·` separator is its own `Text` node for better vertical alignment with the outcome/entry labels. > > <sup>Reviewed by [Cursor Bugbot](https://cursor.com/bugbot) for commit 8308aa7. Bugbot is set up for automated code reviews on this repo. Configure [here](https://www.cursor.com/dashboard/bugbot).</sup> <!-- /CURSOR_SUMMARY -->
Contributor
|
CLA Signature Action: All authors have signed the CLA. You may need to manually re-run the blocking PR check if it doesn't pass in a few minutes. |
Contributor
🔍 Smart E2E Test Selection⏭️ Smart E2E selection skipped - PR targets a release or stable branch (release/* or stable) All E2E tests pre-selected. |
sleepytanya
approved these changes
Jun 10, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to subscribe to this conversation on GitHub.
Already have an account?
Sign in.
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
This PR bundles four UI/behavior fixes on the Predict crypto up/down
details screen (plus one shared positions tweak). All changes are
confined to
app/components/UI/Predict/.1. Time-slot picker loses its left anchor when the live slot expires
(primary fix)
When the live time slot expired and rolled to the next window, the
horizontal
TimeSlotPickerno longer kept the live/selected pillanchored at the left. Root cause: the auto-scroll read pill
x-coordinates from a cached
pillPositionsmap that (1) retained staleentries for markets that had been filtered out, and (2) was read by a
fixed 50ms settle timer that raced ahead of React Native's async
re-layout — so
scrollToused the pre-shift offset and over-scrolled.pillPositionsto only currently-rendered markets whenevermarketschanges.marketsKeyso a leftshift re-anchors even when the resolved selection is unchanged.
x,beating the timer/layout race.
failing pre-fix, passing post-fix).
2. Even spacing around the time-slot picker
The picker is a flush
h-11container with no vertical padding of itsown, so the gap above (title
pb-3= 12px) and below (price summarypt-5= 20px) were uneven. Changed the price-summary top paddingpt-5 → pt-3so the picker has equal 12px above and below.3. Centered separator dot in positions rows
The
Up/Down · entryseparator dot was baseline-glued to the entrylabel via a
' · 'string, so it sat slightly off-center. Split it intoits own
Textnode so it aligns optically in the center-aligned row.4. Remove the
$100 → $Xpayout preview from the up/down CTA + growthe chart
Removed the payout estimate under the buy buttons on the crypto up/down
details page by no longer passing
showPayoutEstimateto the sharedPredictMarketDetailsActions. The prop, formatter, and gated renderingremain intact on that component for any other surface that wants the
preview (none currently enable it), so the change is regression-safe.
The freed vertical space is reclaimed by growing the with-positions
chart height (ratio
0.4 → 0.44, max380 → 430) so the chart fillsthe gap above the sticky actions while keeping the first position row
visible and the rest scrollable.
Changelog
CHANGELOG entry: Fixed the Predict crypto up/down time-slot selector so
the live slot stays anchored to the left when it rolls to the next
window, evened out the spacing around the selector, and removed the
payout estimate from the buy buttons to give the price chart more room.
Related issues
Refs: No external ticket — incremental UX polish on the Predict crypto
up/down details screen reported during QA review (live-slot scroll
anchoring regression, uneven selector spacing, off-center separator dot,
payout-preview removal + chart sizing).
Manual testing steps
Screenshots/Recordings
Before
N/A — author to attach device capture before marking Ready for review
(changes are visual layout tweaks on the crypto up/down details screen
that need a simulator/device to record).
After
N/A — author to attach device capture before marking Ready for review.
Pre-merge author checklist
Docs and MetaMask Mobile
Coding
Standards.
if applicable
guidelines).
Not required for external contributors.
Performance checks (if applicable)
SRPs
to import wallets with many accounts and tokens
performance metrics
trace()for usage andaddTokenfor an example
For performance guidelines and tooling, see the Performance
Guide.
Pre-merge reviewer checklist
app, test code being changed).
in the ticket it closes and includes the necessary testing evidence such
as recordings and or screenshots.
Note
Low Risk
Predict UI-only changes in TimeSlotPicker and crypto up/down details;
scroll logic is covered by new tests with no auth or data-path impact.
Overview
Fixes Predict crypto up/down layout and TimeSlotPicker scroll
behavior when a live slot rolls off.
Time slot picker: When the live pill disappears and the list
shifts left, horizontal scroll no longer drifts off the left edge. Stale
pillPositionsentries are pruned, anchoring re-runs onmarketsKeychanges, and the selected pill’s
onLayoutre-scrolls immediately so a50ms timer doesn’t win a race against re-layout. Regression tests cover
initial anchor and post-expiry re-anchor.
Details screen polish: Price-summary top padding is tightened
(
pt-5→pt-3) so spacing above/below the picker matches. Withpositions, the chart grows (ratio 0.44, max 430px) after
dropping the buy-button payout estimate (
showPayoutEstimateno longerpassed). Position rows: the
·separator is its ownTextnode forbetter vertical alignment with the outcome/entry labels.
Reviewed by Cursor Bugbot for commit
8308aa7. Bugbot is set up for automated
code reviews on this repo. Configure
here.