Skip to content

ui fixes after QA review - PRO-3679/pulse-preview-screen#403

Merged
RanaBug merged 2 commits intostagingfrom
PRO-3679/pulse-preview-screen
Sep 19, 2025
Merged

ui fixes after QA review - PRO-3679/pulse-preview-screen#403
RanaBug merged 2 commits intostagingfrom
PRO-3679/pulse-preview-screen

Conversation

@RanaBug
Copy link
Collaborator

@RanaBug RanaBug commented Sep 19, 2025

Description

How Has This Been Tested?

Screenshots (if appropriate):

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)

Summary by CodeRabbit

  • New Features

    • Consistent small-number formatting to avoid scientific notation across Search, Sell, and Portfolio lists.
    • Dynamic token names and symbols in Buy/Sell previews.
    • Normalized native token addresses and consistent shortened-address display.
    • Tooltip now fades in only after positioning for smoother appearance.
  • Style

    • Refined USD value and balance presentation; clearer dollar sign layout.
    • Improved token label and address styling in previews.
  • Tests

    • Updated test expectations to match the new formatting and labels.

@RanaBug RanaBug requested a review from IAmKio September 19, 2025 14:15
@RanaBug RanaBug self-assigned this Sep 19, 2025
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Sep 19, 2025

Walkthrough

Adds a small-number formatter and native-token address normalizer, applies them across Buy/Sell/Search UIs and lists, updates tooltip fade-in gating, and adjusts related tests to match revised formatting and labels.

Changes

Cohort / File(s) Summary
Address formatting & Buy/Sell header
src/apps/pulse/components/Buy/PreviewBuy.tsx, src/apps/pulse/components/Sell/PreviewSell.tsx, src/apps/pulse/utils/blockchain.ts
Adds formatNativeTokenAddress and uses it to normalize token addresses before truncation; Buy now shows buyToken.name for token label; Sell renders token symbol inline with name.
Numeric small-number formatting
src/utils/number.tsx, src/apps/pulse/components/Search/Search.tsx, src/apps/pulse/components/Search/PortfolioTokenList.tsx, src/apps/pulse/components/Sell/Sell.tsx
Adds formatExponentialSmallNumber and applies it to price, balance, USD values, and amount propagation (wrapping limitDigitsNumber outputs) to avoid exponential notation for tiny values.
Tooltip fade/positioning
src/apps/pulse/components/Misc/Tooltip.tsx
Introduces isPositioned state; computes position only when visible and mounted; sets opacity to 0 until positioned and transitions to 1 after positioning; removes prior timeout delay.
Tests updated for formatting/labels
src/apps/pulse/components/Buy/tests/PreviewBuy.test.tsx, src/apps/pulse/components/Sell/tests/PreviewSell.test.tsx, src/apps/pulse/components/Sell/tests/Sell.test.tsx
Adjusts test assertions to reflect UI text/formatting changes (token label counts and numeric formatting differences).

Sequence Diagram(s)

sequenceDiagram
  autonumber
  actor User
  participant HoverTarget as Hover Target
  participant Tooltip as Tooltip Component
  participant Positioner as calculatePosition()

  User->>HoverTarget: mouseenter
  HoverTarget->>Tooltip: set isVisible = true
  Tooltip->>Positioner: calculatePosition()
  Positioner-->>Tooltip: {x,y}
  Tooltip->>Tooltip: set isPositioned = true (opacity 0 -> 1)
  User->>HoverTarget: mouseleave
  HoverTarget->>Tooltip: set isVisible = false
  Tooltip->>Tooltip: set isPositioned = false (opacity 1 -> 0)
Loading
sequenceDiagram
  autonumber
  participant UI as PreviewBuy/PreviewSell/Sell/Search
  participant BC as blockchain.utils
  participant NUM as number.utils

  UI->>BC: formatNativeTokenAddress(address)
  BC-->>UI: normalizedAddress
  UI->>UI: truncate & render normalizedAddress

  UI->>NUM: formatExponentialSmallNumber(limitDigitsNumber(value))
  NUM-->>UI: formattedString
  UI->>UI: render price / balance / usdValue / propagated amounts
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

Suggested reviewers

  • IAmKio
  • vignesha22

Poem

I nibbled tiny numbers, chased e-ghosts away,
Tucked native addresses tidy, no slices astray.
Tooltips now blush in after they land,
UI hops crisper, neat in my hand. 🥕🐇

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Description Check ⚠️ Warning The PR description is just the repository template with placeholder "-" entries and lacks a meaningful summary of what changed, no testing details, and no screenshots; only the "Bug fix" checkbox is marked. Because it does not describe the specific UI changes, the testing performed, or any visual evidence, reviewers cannot assess scope or QA coverage. Therefore the description check fails the repository's template completeness expectations. Please update the PR description to include a concise summary of the actual changes (e.g., address formatting for native tokens, numeric formatting changes, tooltip positioning/fade, and test expectation updates), list how it was tested (unit tests run, manual QA steps, environment/browsers), and attach screenshots or notes for visual changes; also ensure the "Types of changes" section accurately reflects the change. Adding test commands, CI results, and any migration notes will help reviewers validate and merge the PR more quickly.
✅ Passed checks (2 passed)
Check name Status Explanation
Title Check ✅ Passed The title "ui fixes after QA review - PRO-3679/pulse-preview-screen" communicates that the PR contains UI fixes and includes the ticket/branch reference, which aligns with the changeset focused on presentation tweaks (address formatting, numeric formatting, tooltip fade, and related test updates) across Pulse components. It is concise and directly related to the main change, making it useful for quick scanning. It could be slightly more specific about the exact screens affected but is acceptable as-is.
Docstring Coverage ✅ Passed No functions found in the changes. Docstring coverage check skipped.
✨ Finishing touches
  • 📝 Generate Docstrings
🧪 Generate unit tests
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch PRO-3679/pulse-preview-screen

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@cloudflare-workers-and-pages
Copy link

cloudflare-workers-and-pages bot commented Sep 19, 2025

Deploying x with  Cloudflare Pages  Cloudflare Pages

Latest commit: bdacf08
Status: ✅  Deploy successful!
Preview URL: https://93419b86.x-e62.pages.dev
Branch Preview URL: https://pro-3679-pulse-preview-scree.x-e62.pages.dev

View logs

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (1)
src/utils/number.tsx (1)

1-1: Fix global property shadowing.

The import is shadowing global properties isNaN and parseInt. Consider using aliases to avoid confusion.

Apply this diff to resolve the shadowing:

-import { isNaN, parseInt, parseInt as parseIntLodash } from 'lodash';
+import { isNaN as isNaNLodash, parseInt as parseIntLodash } from 'lodash';

Also update line 126 to use the alias:

-  if (isNaN(numValue)) return '0';
+  if (isNaNLodash(numValue)) return '0';
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 5218b94 and ba91d31.

📒 Files selected for processing (8)
  • src/apps/pulse/components/Buy/PreviewBuy.tsx (2 hunks)
  • src/apps/pulse/components/Misc/Tooltip.tsx (4 hunks)
  • src/apps/pulse/components/Search/PortfolioTokenList.tsx (2 hunks)
  • src/apps/pulse/components/Search/Search.tsx (4 hunks)
  • src/apps/pulse/components/Sell/PreviewSell.tsx (2 hunks)
  • src/apps/pulse/components/Sell/Sell.tsx (4 hunks)
  • src/apps/pulse/utils/blockchain.ts (1 hunks)
  • src/utils/number.tsx (2 hunks)
🧰 Additional context used
🧠 Learnings (2)
📚 Learning: 2025-08-12T07:42:24.656Z
Learnt from: IAmKio
PR: pillarwallet/x#351
File: src/apps/pulse/utils/intent.ts:44-53
Timestamp: 2025-08-12T07:42:24.656Z
Learning: In the Pulse app's intent utilities (src/apps/pulse/utils/intent.ts), the team has chosen to use floating-point arithmetic for token amount calculations despite potential precision issues, accepting JavaScript's decimal place limitations as a valid trade-off for their use case.

Applied to files:

  • src/apps/pulse/components/Sell/Sell.tsx
  • src/apps/pulse/components/Search/Search.tsx
  • src/apps/pulse/components/Search/PortfolioTokenList.tsx
📚 Learning: 2025-09-09T12:40:15.629Z
Learnt from: RanaBug
PR: pillarwallet/x#391
File: src/apps/pulse/components/Sell/Sell.tsx:113-130
Timestamp: 2025-09-09T12:40:15.629Z
Learning: In the Pulse app Sell component, when a user changes/switches tokens, the input amount automatically resets to 0, which means liquidity validation state doesn't become stale when tokens change.

Applied to files:

  • src/apps/pulse/components/Sell/Sell.tsx
  • src/apps/pulse/components/Sell/PreviewSell.tsx
  • src/apps/pulse/components/Buy/PreviewBuy.tsx
🧬 Code graph analysis (5)
src/apps/pulse/components/Sell/Sell.tsx (1)
src/utils/number.tsx (2)
  • formatExponentialSmallNumber (119-149)
  • limitDigitsNumber (42-69)
src/apps/pulse/components/Sell/PreviewSell.tsx (1)
src/apps/pulse/utils/blockchain.ts (1)
  • formatNativeTokenAddress (1-9)
src/apps/pulse/components/Search/Search.tsx (1)
src/utils/number.tsx (2)
  • formatExponentialSmallNumber (119-149)
  • limitDigitsNumber (42-69)
src/apps/pulse/components/Search/PortfolioTokenList.tsx (1)
src/utils/number.tsx (2)
  • formatExponentialSmallNumber (119-149)
  • limitDigitsNumber (42-69)
src/apps/pulse/components/Buy/PreviewBuy.tsx (1)
src/apps/pulse/utils/blockchain.ts (1)
  • formatNativeTokenAddress (1-9)
🪛 Biome (2.1.2)
src/utils/number.tsx

[error] 1-1: Do not shadow the global "isNaN" property.

Consider renaming this variable. It's easy to confuse the origin of variables when they're named after a known global.

(lint/suspicious/noShadowRestrictedNames)


[error] 1-1: Do not shadow the global "parseInt" property.

Consider renaming this variable. It's easy to confuse the origin of variables when they're named after a known global.

(lint/suspicious/noShadowRestrictedNames)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: unit-tests
  • GitHub Check: lint
  • GitHub Check: build
🔇 Additional comments (15)
src/apps/pulse/utils/blockchain.ts (1)

1-9: LGTM!

The address formatting utility is well-implemented and serves a clear purpose - normalizing the ETH placeholder address to the zero address for consistent display.

src/apps/pulse/components/Sell/PreviewSell.tsx (2)

8-8: Consistent address formatting implementation.

The import of formatNativeTokenAddress aligns with the PR's goal of standardizing address display across components.


483-490: Enhanced token display with consistent formatting.

The changes improve the UI by:

  • Displaying token name and symbol inline with proper styling
  • Using formatNativeTokenAddress to normalize addresses before truncation

This ensures consistent address formatting across buy/sell previews.

src/apps/pulse/components/Buy/PreviewBuy.tsx (2)

16-16: Consistent with the PR's address formatting pattern.

The import follows the same pattern as PreviewSell.tsx, ensuring consistent address handling across components.


421-427: Dynamic token label with proper address formatting.

The changes improve the UI by:

  • Using dynamic buyToken.name instead of hard-coded "USD Coin"
  • Applying formatNativeTokenAddress before truncation for consistent display

This matches the pattern used in PreviewSell.tsx for consistent UX.

src/apps/pulse/components/Misc/Tooltip.tsx (3)

10-10: Improved tooltip fade-in behavior.

The addition of isPositioned state creates a smooth fade-in effect by ensuring the tooltip is positioned before becoming visible. This prevents the flash of incorrectly positioned content.

Also applies to: 67-67, 76-76


80-83: Simplified positioning logic.

The removal of the setTimeout delay in favor of immediate position calculation when isVisible && tooltipRef.current is present improves responsiveness while maintaining correct positioning.


104-106: Clean fade transition implementation.

The inline opacity and transition styles create a polished fade effect that enhances the user experience.

src/apps/pulse/components/Search/Search.tsx (2)

18-21: Updated import for consistent numeric formatting.

The import change to include formatExponentialSmallNumber supports the PR's goal of standardizing numeric displays across the application.


213-215: Consistent numeric formatting across buy/sell flows.

The replacement of direct limitDigitsNumber usage with formatExponentialSmallNumber(limitDigitsNumber(...)) ensures consistent formatting of USD values, preventing scientific notation display for small numbers.

Also applies to: 227-229, 241-243

src/apps/pulse/components/Search/PortfolioTokenList.tsx (2)

13-16: Import aligns with numeric formatting standardization.

The addition of formatExponentialSmallNumber to the imports supports consistent number display formatting.


201-206: Enhanced numeric formatting for better readability.

The implementation improves the UI by:

  • Using formatExponentialSmallNumber to prevent scientific notation in price/balance displays
  • Rendering the dollar sign as a separate element for cleaner formatting
  • Maintaining the '0.00' fallback for missing prices

Also applies to: 214-214, 217-219

src/utils/number.tsx (1)

119-149: Well-implemented small number formatter.

The formatExponentialSmallNumber function effectively handles the common issue of scientific notation in JavaScript number displays. The implementation:

  • Properly handles edge cases (zero, NaN, falsy values)
  • Uses appropriate threshold (0.0001) for switching to custom formatting
  • Correctly reconstructs decimal strings from scientific notation
  • Provides reasonable default for maxDecimals
Based on the search results, I can see that the `formatExponentialSmallNumber` implementation follows established best practices for handling JavaScript's scientific notation issues. The approach of using `toFixed()` and manual reconstruction is a well-documented solution for preventing scientific notation display, and the solution handles both very large and very small numbers appropriately.
src/apps/pulse/components/Sell/Sell.tsx (2)

16-19: Updated import for consistent numeric formatting.

The import change supports the PR's standardization of numeric displays across the application, replacing direct limitDigitsNumber usage with enhanced formatting.


212-212: Comprehensive numeric formatting improvements.

The changes enhance user experience by:

  • Using formatExponentialSmallNumber for token USD values and balances to prevent scientific notation
  • Applying consistent formatting to percentage/MAX button calculations before state updates
  • Ensuring formatted strings are properly propagated to parent components

This provides a consistent, user-friendly numeric display throughout the sell interface.

Also applies to: 300-306, 342-345, 351-354

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
src/apps/pulse/components/Sell/tests/PreviewSell.test.tsx (1)

305-313: Make the assertion resilient to markup changes

Counting exactly 6 nodes for this composite text is brittle. Prefer a semantic or threshold-based check, or scope via a stable container/testid to avoid incidental duplicates.

Apply this minimal, more resilient change:

-      expect(
-        screen.getAllByText((content, element) => {
-          return !!(
-            element?.textContent?.includes('10.500000') &&
-            element?.textContent?.includes('TEST')
-          );
-        })
-      ).toHaveLength(6);
+      const matches = screen.getAllByText((_, element) =>
+        Boolean(
+          element?.textContent?.includes('10.500000') &&
+          element?.textContent?.includes('TEST')
+        )
+      );
+      expect(matches.length).toBeGreaterThanOrEqual(5);

If possible, add stable testids to the key, user-visible instances (e.g., sell amount row, summary tile) and assert those explicitly to avoid count-based assertions altogether.

src/apps/pulse/components/Buy/tests/PreviewBuy.test.tsx (2)

87-87: Make the assertion resilient to copy changes.

Prefer referencing the fixture to avoid hard‑coded strings.

-      expect(screen.getAllByText('USD Coin')).toHaveLength(1);
+      expect(screen.getAllByText(mockPayingToken.name)).toHaveLength(1);

83-93: Also assert the presence of the dynamic buy token name.

This locks in the intended switch from hard‑coded to dynamic labeling.

       render(<PreviewBuy {...mockProps} />);
 
       expect(screen.getByText('Confirm Transaction')).toBeInTheDocument();
       expect(screen.getAllByText('USD Coin')).toHaveLength(1);
+      expect(screen.getByText(mockToken.name)).toBeInTheDocument();
       expect(screen.getAllByText('TEST')).toHaveLength(2);
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between ba91d31 and bdacf08.

⛔ Files ignored due to path filters (3)
  • src/apps/pulse/components/Buy/tests/__snapshots__/PreviewBuy.test.tsx.snap is excluded by !**/*.snap
  • src/apps/pulse/components/Sell/tests/__snapshots__/PreviewSell.test.tsx.snap is excluded by !**/*.snap
  • src/apps/pulse/components/Sell/tests/__snapshots__/Sell.test.tsx.snap is excluded by !**/*.snap
📒 Files selected for processing (3)
  • src/apps/pulse/components/Buy/tests/PreviewBuy.test.tsx (1 hunks)
  • src/apps/pulse/components/Sell/tests/PreviewSell.test.tsx (1 hunks)
  • src/apps/pulse/components/Sell/tests/Sell.test.tsx (2 hunks)
✅ Files skipped from review due to trivial changes (1)
  • src/apps/pulse/components/Sell/tests/Sell.test.tsx
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: lint
  • GitHub Check: unit-tests
  • GitHub Check: build
🔇 Additional comments (2)
src/apps/pulse/components/Buy/tests/PreviewBuy.test.tsx (2)

87-87: LGTM: count reduced to 1 matches the new dynamic buyToken label.

Now that the bought token label uses buyToken.name, "USD Coin" should only appear for the paying token.


22-24: Add a mock for formatNativeTokenAddress (keep the existing getLogoForChainId mock)

PreviewBuy imports getLogoForChainId from '../../../../utils/blockchain' (already mocked) and formatNativeTokenAddress from '../../utils/blockchain'. The test mock only covers getLogoForChainId — add a mock for '../../utils/blockchain' in src/apps/pulse/components/Buy/tests/PreviewBuy.test.tsx, e.g.

vi.mock('../../utils/blockchain', () => ({ formatNativeTokenAddress: (addr: string) => addr }));

Likely an incorrect or invalid review comment.

Copy link
Collaborator

@IAmKio IAmKio left a comment

Choose a reason for hiding this comment

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

LGTM

@RanaBug RanaBug merged commit 821b0fe into staging Sep 19, 2025
6 checks passed
@coderabbitai coderabbitai bot mentioned this pull request Sep 22, 2025
3 tasks
@coderabbitai coderabbitai bot mentioned this pull request Dec 16, 2025
3 tasks
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.

2 participants