aegis-swap-widget 0.8.0 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. package/CHANGELOG.md +68 -0
  2. package/DESIGN.md +2 -1
  3. package/README.md +150 -45
  4. package/dist/aegis-swap-widget.js +18270 -11493
  5. package/dist/components/Slider.d.ts +6 -2
  6. package/dist/components/icons.d.ts +2 -0
  7. package/dist/errors.d.ts +2 -3
  8. package/dist/format.d.ts +2 -0
  9. package/dist/hooks/useLatest.d.ts +2 -0
  10. package/dist/hooks/useRetryOnRefocus.d.ts +11 -0
  11. package/dist/hooks/useTokenAllowance.d.ts +2 -0
  12. package/dist/index.d.ts +4 -1
  13. package/dist/styles.css +1 -1
  14. package/dist/toast/useSwipeDismiss.d.ts +6 -1
  15. package/dist/widget/AegisLeverageWidget.d.ts +8 -0
  16. package/dist/widget/EngineAmountBox.d.ts +6 -1
  17. package/dist/widget/SwapWidgetShell.d.ts +3 -1
  18. package/dist/widget/TokenPriceHistoryStrip.d.ts +8 -2
  19. package/dist/widget/engine-controller/displayCache.d.ts +7 -1
  20. package/dist/widget/engine-controller/engineActionExpiry.d.ts +9 -1
  21. package/dist/widget/engine-controller/engineActionState.d.ts +22 -2
  22. package/dist/widget/engine-controller/engineCtaLabel.d.ts +12 -7
  23. package/dist/widget/engine-controller/engineDisplay.d.ts +8 -0
  24. package/dist/widget/engine-controller/engineOptions.d.ts +13 -1
  25. package/dist/widget/engine-controller/enginePermissionFamilies.d.ts +94 -0
  26. package/dist/widget/engine-controller/enginePositionBook.d.ts +66 -0
  27. package/dist/widget/engine-controller/enginePositionManageCopy.d.ts +51 -0
  28. package/dist/widget/engine-controller/engineQuoteFetch.d.ts +27 -6
  29. package/dist/widget/engine-controller/engineTokenPull.d.ts +13 -0
  30. package/dist/widget/engine-controller/engineTradePositionStorage.d.ts +9 -0
  31. package/dist/widget/engine-controller/engineTransactionProgress.d.ts +11 -2
  32. package/dist/widget/engine-controller/engineTransactionView.d.ts +10 -1
  33. package/dist/widget/engine-controller/useEngineActionDrafts.d.ts +3 -3
  34. package/dist/widget/engine-controller/useEngineActivity.d.ts +1 -1
  35. package/dist/widget/engine-controller/useEngineAuthorizationPlan.d.ts +44 -0
  36. package/dist/widget/engine-controller/useEngineMarketMarks.d.ts +18 -0
  37. package/dist/widget/engine-controller/useEnginePermissionSetup.d.ts +34 -0
  38. package/dist/widget/engine-controller/useEnginePositionActions.d.ts +24 -1
  39. package/dist/widget/engine-controller/useEnginePositionStrategies.d.ts +20 -0
  40. package/dist/widget/engine-controller/useEnginePositions.d.ts +35 -5
  41. package/dist/widget/engine-controller/useEngineSubmit.d.ts +6 -3
  42. package/dist/widget/engine-controller/useEngineTradePermissions.d.ts +81 -0
  43. package/dist/widget/engine-controller/useEngineTradeSubmit.d.ts +49 -0
  44. package/dist/widget/engine-ui/EngineBodySkeleton.d.ts +4 -0
  45. package/dist/widget/engine-ui/EngineCollateralRow.d.ts +8 -0
  46. package/dist/widget/engine-ui/EngineCollateralRowSkeleton.d.ts +3 -0
  47. package/dist/widget/engine-ui/EngineDetailsBreakdown.d.ts +7 -0
  48. package/dist/widget/engine-ui/EngineEstimateReveal.d.ts +4 -0
  49. package/dist/widget/engine-ui/EngineLeverageControl.d.ts +22 -0
  50. package/dist/widget/engine-ui/EngineNotice.d.ts +15 -0
  51. package/dist/widget/engine-ui/EngineOnboardingActivePermissions.d.ts +9 -0
  52. package/dist/widget/engine-ui/EngineOnboardingAuthorize.d.ts +18 -0
  53. package/dist/widget/engine-ui/EngineOnboardingFooter.d.ts +20 -0
  54. package/dist/widget/engine-ui/EngineOnboardingProgress.d.ts +12 -0
  55. package/dist/widget/engine-ui/EngineOnboardingReview.d.ts +19 -0
  56. package/dist/widget/engine-ui/EngineOnboardingSuccess.d.ts +15 -0
  57. package/dist/widget/engine-ui/EngineOverlaySheet.d.ts +18 -0
  58. package/dist/widget/engine-ui/EnginePartnerContext.d.ts +43 -0
  59. package/dist/widget/engine-ui/EnginePermissionRail.d.ts +21 -0
  60. package/dist/widget/engine-ui/EnginePermissionRailRow.d.ts +42 -0
  61. package/dist/widget/engine-ui/EnginePositionBookFacts.d.ts +5 -0
  62. package/dist/widget/engine-ui/EnginePositionManageDialog.d.ts +9 -2
  63. package/dist/widget/engine-ui/EnginePositionsPanel.d.ts +5 -3
  64. package/dist/widget/engine-ui/EngineQuotePending.d.ts +1 -0
  65. package/dist/widget/engine-ui/EngineReservedShell.d.ts +16 -0
  66. package/dist/widget/engine-ui/EngineRiskMeter.d.ts +7 -7
  67. package/dist/widget/engine-ui/EngineSegmentedControl.d.ts +12 -0
  68. package/dist/widget/engine-ui/EngineStepStateIcon.d.ts +5 -0
  69. package/dist/widget/engine-ui/EngineTradeEstimate.d.ts +11 -0
  70. package/dist/widget/engine-ui/EngineTradeOnboarding.d.ts +49 -0
  71. package/dist/widget/engine-ui/EngineTradePermissions.d.ts +44 -0
  72. package/dist/widget/engine-ui/EngineTradePermissionsPanels.d.ts +62 -0
  73. package/dist/widget/engine-ui/EngineTxDetailsPending.d.ts +1 -0
  74. package/dist/widget/engine-ui/TokenPairMark.d.ts +3 -3
  75. package/dist/widget/engine-ui/engineOnboardingPanelTypes.d.ts +6 -0
  76. package/dist/widget/engine-ui/enginePermissionCopy.d.ts +19 -0
  77. package/dist/widget/engine-ui/enginePermissionRailGeometry.d.ts +28 -0
  78. package/dist/widget/engine-ui/useEngineTradeEducation.d.ts +22 -0
  79. package/dist/widget/engine-ui/useOverlayClose.d.ts +1 -0
  80. package/dist/widget/engineTradeViewModel.d.ts +21 -0
  81. package/dist/widget/focusTrap.d.ts +1 -1
  82. package/dist/widget/types.d.ts +159 -6
  83. package/dist/widget/useEngineController.d.ts +3213 -2
  84. package/dist/widget/useSheetEntrance.d.ts +1 -1
  85. package/dist/widget/useSwapController.d.ts +1 -1
  86. package/dist/widget/useWidgetStyle.d.ts +2 -1
  87. package/dist/widget/viewState.d.ts +15 -1
  88. package/package.json +2 -2
  89. package/dist/encoding.d.ts +0 -2
  90. package/dist/quote/aggregatedSwapQuote.d.ts +0 -1
  91. package/dist/services/kyberSwap.d.ts +0 -2
package/CHANGELOG.md CHANGED
@@ -1,5 +1,73 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.9.0
4
+
5
+ ### Minor Changes
6
+
7
+ - c76ba41: Add Engine Long/Short trading.
8
+
9
+ Core sizes a directional position against one block-pinned Engine state and v4
10
+ route, then opens it in a single atomic router call. The swap settles inside the
11
+ transaction, so the wallet signs only the authorizations it must.
12
+
13
+ The widget gains an opt-in `'trade'` surface and a dedicated one-view
14
+ `AegisLeverageWidget`. Leverage limits come from the quote, alongside the
15
+ trader-facing risk facts for the position. Authorization reports its request
16
+ count per chain, and a review step is mandatory before submission but stays
17
+ customizable. Permissions are granted in sequence, each with its own checkpoint;
18
+ after a partial failure the revoke guidance for what was already granted stays
19
+ on screen. A successful open links through to Positions.
20
+
21
+ Position identity survives a reload: the strategy is reconstructed from indexed
22
+ opening actions, with optional bounded persistence of the reviewed target
23
+ scenario.
24
+
25
+ - 1e7a963: Keep the Leverage Positions surface trader-first and evidence-backed.
26
+
27
+ Only positions with strict indexed Long/Short evidence appear in the Leverage
28
+ widget. Ordinary borrow vaults remain in the portfolio presentation and are no
29
+ longer relabelled as trades while classification loads or fails. Stored opening
30
+ intents enrich matching indexed strategies but never classify a vault alone.
31
+
32
+ The collapsed trade row removes the borrow-rate runway, LTV bar, and
33
+ credit-product language. It shows direction, pair, opening-plan leverage, and a
34
+ signed underlying price move only while a fresh on-chain pool mark is available.
35
+ It does not call that move PnL or return. The detail keeps the reviewed
36
+ entry→target plan, and live debt/equity use the Engine liquidity-debt valuation
37
+ instead of deriving dollars or leverage from the protocol LTV ratio.
38
+ When NFT/LP collateral is attached and cannot be valued from the live idle
39
+ balances, the widget omits total equity rather than presenting a partial value.
40
+
41
+ "Last activity" now appears only when something actually happened after the
42
+ open. On an untouched lot it restated the opening date the collapsed row already
43
+ carries — one fact wearing two formats.
44
+
45
+ ### Patch Changes
46
+
47
+ - 1e7a963: Unify the failure taxonomy and remove dead-end error states.
48
+
49
+ Core now owns one error classifier: `classifyError` returns curated copy plus a
50
+ failure `kind` and `retryable` flag, `UserFacingError` accepts both, and
51
+ `errorMessage` stays as a message-only compat wrapper. Wallet-cancelled sends
52
+ and not-ready Engine markets keep their curated copy instead of collapsing to a
53
+ generic fallback, and a not-ready market is marked non-retryable so retry CTAs
54
+ suppress.
55
+
56
+ The widget re-exports the core classifier (removing its diverged fork), catches
57
+ core's `TransactionReceiptTimeoutError` (hash included, explorer-link
58
+ messaging) instead of viem's unreachable timeout, retries failed Engine market
59
+ discovery via a Try again button and on refocus, turns a failed allowance check
60
+ into an enabled Try again CTA, labels fallback-served Engine data as
61
+ "last known" with a retry, derives inline errors from one precedence object
62
+ (submit failures outrank background quote failures), and keeps raw backend
63
+ error text out of the inline alert (widget log only).
64
+
65
+ - 1e7a963: Hug Engine onboarding sheets to their content and end leverage opens on a trading success screen with See position and Open another.
66
+ - Updated dependencies [1e7a963]
67
+ - Updated dependencies [c76ba41]
68
+ - Updated dependencies [1e7a963]
69
+ - @aegis-engine/core@0.5.0
70
+
3
71
  ## 0.8.0
4
72
 
5
73
  ### Minor Changes
package/DESIGN.md CHANGED
@@ -45,7 +45,8 @@ carry across both themes. `theme="auto"` follows `prefers-color-scheme`.
45
45
 
46
46
  ## Motion
47
47
 
48
- All motion is CSS and respects `prefers-reduced-motion` automatically.
48
+ Motion uses CSS and the browser Web Animations API. No third-party animation
49
+ runtime ships with the widget, and `prefers-reduced-motion` is respected.
49
50
 
50
51
  | Token | Default | Role |
51
52
  | --- | --- | --- |
package/README.md CHANGED
@@ -54,12 +54,100 @@ export function Engine({ account, provider }) {
54
54
  defaultSurface="buy"
55
55
  showTokenPriceHistory
56
56
  showEngineMarketHistory
57
- surfaces={['buy', 'borrow', 'lend', 'positions']}
57
+ surfaces={['buy', 'trade', 'borrow', 'lend', 'positions']}
58
58
  />
59
59
  )
60
60
  }
61
61
  ```
62
62
 
63
+ ## Trade surface
64
+
65
+ `'trade'` is opt-in. The default tab set is `['buy', 'borrow', 'lend',
66
+ 'positions']`, so the tab appears only when a host lists `'trade'` in
67
+ `surfaces`.
68
+
69
+ The surface opens a directional position in one atomic Engine router call:
70
+ create a fresh vault, deposit the user's token, borrow, swap through the same
71
+ Uniswap v4 pool, redeposit the output, and lock the vault. The quote pins the
72
+ Engine state and v4 route to one block, applies the selected slippage floor, and
73
+ re-quotes after wallet authorization before submission.
74
+
75
+ The user chooses Long or Short, a deposit, and leverage inside the live range
76
+ returned by the quote. The widget shows opening LTV against the borrow limit,
77
+ gross return at the configured target, entry-to-target price, opening price
78
+ impact, and interest over the configured horizon. Engine positions do not have
79
+ a single liquidation price; interest accrual increases LTV over time.
80
+
81
+ For a separate Long/Short experience that starts without
82
+ Buy/Borrow/Lend/Positions tabs, mount `AegisLeverageWidget`:
83
+
84
+ ```tsx
85
+ import { AegisLeverageWidget } from 'aegis-swap-widget'
86
+ import 'aegis-swap-widget/styles.css'
87
+
88
+ export function LongShort({ account, provider }) {
89
+ return (
90
+ <AegisLeverageWidget
91
+ account={account}
92
+ provider={provider}
93
+ chains={engineChains}
94
+ engineDataSource={{ kind: 'rest', baseUrl: '/api/engine' }}
95
+ tradeLeverageOptions={[1.25, 1.5, 2, 3]}
96
+ defaultTradeLeverage={1.5}
97
+ onboarding={{ mode: 'guided' }}
98
+ />
99
+ )
100
+ }
101
+ ```
102
+
103
+ This is the frontend integration interface; the host does not call the Engine
104
+ SDK directly. The host still supplies wallet connectivity, chain/router
105
+ configuration, and an Engine data source or same-origin proxy. Trade offers
106
+ only markets that support borrowing and have the required trusted execution
107
+ addresses.
108
+
109
+ After a deposit is entered, the leverage slider reads the feasible minimum and
110
+ maximum from the live Engine quote. The range recalculates for the amount,
111
+ direction, market, horizon, price scenario, liquidity, and slippage. Presets
112
+ are shortcuts, not protocol limits. If a live bound moves past the selected
113
+ target, the widget shows an explicit error and does not silently clamp it.
114
+
115
+ After confirmation, Positions reconstructs Long/Short direction and executed
116
+ entry price from the indexed opening transaction returned by
117
+ `GET /v1/engine/positions/activity`. A normal Borrow swap has a final
118
+ wallet-side withdrawal and is not labeled as a trade. The Leverage Positions
119
+ tab shows only vaults whose activity proves the Long/Short recipe; ordinary
120
+ borrow vaults remain in the unified portfolio. The reviewed average
121
+ leverage and target are off-chain scenario inputs, so the widget stores only
122
+ those fields after the receipt confirms. Omit `tradePositionStorage` for
123
+ origin-local `localStorage`, pass `null` to keep only indexed facts, or provide
124
+ an authenticated async adapter for cross-device continuity. Stored metadata is
125
+ joined by chain, account, pool, and opening transaction hash; it cannot
126
+ override indexed direction or entry price. A no-swap opening has no indexed
127
+ direction signal and remains a generic position.
128
+
129
+ The success sheet retains the reviewed risk snapshot and transaction link.
130
+ `AegisLeverageWidget` then reveals a Positions entry; indexed data can take a
131
+ moment to appear.
132
+
133
+ `guided` is the default onboarding mode. It keeps optional education available
134
+ through **How it works** without opening it automatically. Set
135
+ `onboarding={{ showBeforeConnect: true }}` to open it once for a browser that
136
+ has not dismissed it. Both `guided` and `contextual` use a required review
137
+ sheet. The sheet freezes the displayed position, reads
138
+ the connected account's current vault and token permissions, and lists only
139
+ the missing wallet actions before the final open transaction. A zero-first
140
+ ERC-20 reset is shown as a separate wallet prompt. The submit path re-reads the
141
+ permissions and obtains a fresh executable quote; the review is not execution
142
+ evidence. If that fresh quote weakens a displayed swap floor or risk fact, the
143
+ widget stops before the router transaction and requires review of the updated
144
+ strategy.
145
+
146
+ Use `onboarding={{ mode: 'contextual' }}` to omit the introductory education
147
+ while retaining the required review. Hosts can override presentation copy and
148
+ persistence through `onboarding`, but contract scope, token amount, expiry,
149
+ spender, target, and revocation copy remain SDK-owned.
150
+
63
151
  ## Partner context and host action requirements
64
152
 
65
153
  Wolf Game partners can use the canonical
@@ -86,13 +174,13 @@ const partnerContext = {
86
174
  resource: {
87
175
  chainId: 1,
88
176
  address: '0x828B22c9ea1c20B551EeFC6198174C4bb7a8CBF6',
89
- symbol: 'WATER',
177
+ symbol: 'WATER'
90
178
  },
91
179
  requiredAmount: '1000',
92
180
  availableAmount: '660',
93
181
  shortfallAmount: '340',
94
- resourceUse: 'consumed',
95
- },
182
+ resourceUse: 'consumed'
183
+ }
96
184
  } satisfies PartnerContext
97
185
 
98
186
  export function GameMarket() {
@@ -277,6 +365,12 @@ Product semantics are deliberately conservative:
277
365
  before it quotes and submits add-collateral, repay, idle-withdraw, loan-close,
278
366
  and lend-redeem actions. A close that needs an idle-token rebalance asks the
279
367
  user to repay first, then re-quote the close.
368
+ - Positions identify Tap Long/Short openings from the activity ledger's exact
369
+ create/deposit/debt/internal-swap/lock order. Target price and average
370
+ leverage remain clearly labeled opening-plan metadata, not current protocol
371
+ state or an on-chain order. Leverage rows omit borrow-rate runway forecasts
372
+ and show the underlying move from entry only while a fresh same-pool mark is
373
+ available; the move is not presented as PnL or return.
280
374
  - Lender balances are indexed Engine share units, not token amounts; the widget
281
375
  does not invent a token/USD value without a current share price.
282
376
 
@@ -361,10 +455,11 @@ normalizes addresses and validates shape, but it cannot prove that a host's
361
455
  override points at the intended Aegis or Uniswap deployment. Source those values
362
456
  from your own audited config or backend, not from user input.
363
457
 
364
- `onSubmitted`, `onSuccess`, `onError`, `onQuote`, `onStatusChange`, and
365
- `onPoolChange` are the supported host signals. The in-widget "Latest tx" drawer
366
- is a session-local UI receipt for the most recent confirmed swap; it is not a
367
- transaction history API. If a host needs durable history, record
458
+ `onSubmitted`, `onSuccess`, `onError`, `onQuote`, `onStatusChange`,
459
+ `onPoolChange`, `onAuthorizationPlan`, `onAuthorizationStepChange`, and
460
+ `onOnboardingEvent` are the supported host signals. The in-widget "Latest tx"
461
+ drawer is a session-local UI receipt for the most recent confirmed swap; it is
462
+ not a transaction history API. If a host needs durable history, record
368
463
  `onSubmitted`/`onSuccess` on the host side.
369
464
 
370
465
  ## Appearance
@@ -372,11 +467,7 @@ transaction history API. If a host needs durable history, record
372
467
  Hosts can choose the widget surface and brand accent at instantiation time:
373
468
 
374
469
  ```tsx
375
- <AegisSwapWidget
376
- theme="dark"
377
- accentColor="#7c5cff"
378
- baseColor="#16121f"
379
- />
470
+ <AegisSwapWidget theme="dark" accentColor="#7c5cff" baseColor="#16121f" />
380
471
  ```
381
472
 
382
473
  `theme` supports `dark`, `light`, or `auto` (which follows the host's `prefers-color-scheme`). `accentColor` accepts any CSS color value and is used for the CTA, selected pools, focus states, links, and swap controls. The widget auto-derives a readable CTA text color from `accentColor` — for hex, `rgb()`, and `hsl()` values everywhere, and for any CSS color (named, `oklch()`, …) in the browser. `accentTextColor` overrides that and is the deterministic choice when you want an exact CTA text color (or are rendering a named/`oklch()` accent during SSR).
@@ -448,7 +539,7 @@ The general Ethereum preset is exported for hosts that want the standard list:
448
539
  import { AegisAggregatedSwapWidget } from 'aegis-swap-widget'
449
540
  import {
450
541
  AGGREGATED_SWAP_DEFAULT_TOKEN_LIST,
451
- AGGREGATED_SWAP_WOLFGAME_TOKEN_LIST,
542
+ AGGREGATED_SWAP_WOLFGAME_TOKEN_LIST
452
543
  } from '@aegis-engine/core'
453
544
 
454
545
  export function WolfGameSwap() {
@@ -525,7 +616,7 @@ import { AegisSwapWidget } from 'aegis-swap-widget'
525
616
  import {
526
617
  AEGIS_DYNAMIC_FEE_FLAG,
527
618
  AEGIS_SWAP_HOOK,
528
- type AegisSwapPoolConfig,
619
+ type AegisSwapPoolConfig
529
620
  } from '@aegis-engine/core'
530
621
 
531
622
  const pools: AegisSwapPoolConfig[] = [
@@ -537,14 +628,14 @@ const pools: AegisSwapPoolConfig[] = [
537
628
  currency1: '0xYourTokenAddress',
538
629
  fee: AEGIS_DYNAMIC_FEE_FLAG,
539
630
  tickSpacing: 60,
540
- hooks: AEGIS_SWAP_HOOK,
631
+ hooks: AEGIS_SWAP_HOOK
541
632
  },
542
633
  counterToken: {
543
634
  chainId: 1,
544
635
  address: '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48',
545
636
  name: 'USD Coin',
546
637
  symbol: 'USDC',
547
- decimals: 6,
638
+ decimals: 6
548
639
  },
549
640
  token: {
550
641
  chainId: 1,
@@ -552,9 +643,9 @@ const pools: AegisSwapPoolConfig[] = [
552
643
  name: 'Example Token',
553
644
  symbol: 'EXAMPLE',
554
645
  decimals: 18,
555
- iconUrl: 'https://example.com/token.svg',
556
- },
557
- },
646
+ iconUrl: 'https://example.com/token.svg'
647
+ }
648
+ }
558
649
  ]
559
650
 
560
651
  export function Swap() {
@@ -571,13 +662,13 @@ The default chain is Ethereum mainnet. You can override mainnet RPCs or provide
571
662
  ```tsx
572
663
  import { mainnet } from 'viem/chains'
573
664
 
574
- <AegisSwapWidget
665
+ ;<AegisSwapWidget
575
666
  chainId={1}
576
667
  chains={{
577
668
  1: {
578
669
  chain: mainnet,
579
- rpcUrls: ['https://your-mainnet-rpc.example'],
580
- },
670
+ rpcUrls: ['https://your-mainnet-rpc.example']
671
+ }
581
672
  }}
582
673
  pools={pools}
583
674
  />
@@ -593,15 +684,15 @@ import { base } from 'viem/chains'
593
684
  import { AegisSwapWidget } from 'aegis-swap-widget'
594
685
  import { UNISWAP_V4_CONTRACTS_BY_CHAIN } from '@aegis-engine/core'
595
686
 
596
- <AegisSwapWidget
687
+ ;<AegisSwapWidget
597
688
  chainId={8453}
598
689
  chains={{
599
690
  8453: {
600
691
  chain: base,
601
692
  router: '0xYourAegisRouter',
602
693
  rpcUrls: ['https://your-base-rpc.example'],
603
- v4Contracts: UNISWAP_V4_CONTRACTS_BY_CHAIN[8453],
604
- },
694
+ v4Contracts: UNISWAP_V4_CONTRACTS_BY_CHAIN[8453]
695
+ }
605
696
  }}
606
697
  pools={pools}
607
698
  />
@@ -619,10 +710,7 @@ The widget fetches token icons by address using the metadata IDs from the Aegis
619
710
  `evm_${chainId}_${tokenAddressLowercase}`.
620
711
 
621
712
  ```tsx
622
- <AegisSwapWidget
623
- metadataEndpoint="/graphql/meta"
624
- pools={pools}
625
- />
713
+ <AegisSwapWidget metadataEndpoint="/graphql/meta" pools={pools} />
626
714
  ```
627
715
 
628
716
  Use `metadataEndpoint={null}` to disable backend icon hydration. It does not
@@ -662,7 +750,7 @@ host connect modal creates the provider during the button click:
662
750
  const connection = await openWallet()
663
751
  return {
664
752
  provider: connection.provider,
665
- account: connection.account,
753
+ account: connection.account
666
754
  }
667
755
  }}
668
756
  />
@@ -842,12 +930,12 @@ same viewport — a plain function, no hooks or context:
842
930
  ```tsx
843
931
  import { aegisToast } from 'aegis-swap-widget'
844
932
 
845
- aegisToast('Copied') // info
933
+ aegisToast('Copied') // info
846
934
  aegisToast.success('Saved', { description: 'Order #1204' })
847
935
  aegisToast.error('Could not save', { duration: 8000 })
848
936
 
849
- const id = aegisToast.loading('Uploading…') // sticky until updated
850
- aegisToast.success('Uploaded', { id }) // reusing an id morphs in place
937
+ const id = aegisToast.loading('Uploading…') // sticky until updated
938
+ aegisToast.success('Uploaded', { id }) // reusing an id morphs in place
851
939
 
852
940
  aegisToast.promise(save(), {
853
941
  loading: 'Saving…',
@@ -867,8 +955,9 @@ package keep two independent toast stores (and two viewports).
867
955
 
868
956
  Switching pools or the approval mode glides a single active pill between the
869
957
  options (iOS-segmented-control style), and the Sell/Buy token pills cross-fade
870
- when a switch retargets them. It is all CSS — no animation library — and every
871
- animation respects `prefers-reduced-motion` automatically.
958
+ when a switch retargets them. Motion uses CSS plus the browser Web Animations
959
+ API for the bottom-sheet entrance; no third-party animation runtime ships with
960
+ the widget. Every animation respects `prefers-reduced-motion` automatically.
872
961
 
873
962
  Hosts tune or disable the switch motion through CSS tokens on the `style` prop:
874
963
 
@@ -886,13 +975,13 @@ Hosts tune or disable the switch motion through CSS tokens on the `style` prop:
886
975
  0.3.0 removes the props that were deprecated in 0.2.x. The replacements are
887
976
  drop-in:
888
977
 
889
- | Removed | Use instead |
890
- | --- | --- |
891
- | `targets={[...]}` | `poolIds={[...]}` (same `string[]`) |
892
- | `markets={map}` | `pools={Object.values(map)}` |
893
- | `defaultDirection="intoTarget"` | `defaultDirection="buy"` |
894
- | `defaultDirection="outOfTarget"` | `defaultDirection="sell"` |
895
- | `showApprovalModeControl` | `showApprovalMode` |
978
+ | Removed | Use instead |
979
+ | -------------------------------- | ----------------------------------- |
980
+ | `targets={[...]}` | `poolIds={[...]}` (same `string[]`) |
981
+ | `markets={map}` | `pools={Object.values(map)}` |
982
+ | `defaultDirection="intoTarget"` | `defaultDirection="buy"` |
983
+ | `defaultDirection="outOfTarget"` | `defaultDirection="sell"` |
984
+ | `showApprovalModeControl` | `showApprovalMode` |
896
985
 
897
986
  No other props changed. See the [CHANGELOG](./CHANGELOG.md) for the full entry.
898
987
 
@@ -932,8 +1021,22 @@ No other props changed. See the [CHANGELOG](./CHANGELOG.md) for the full entry.
932
1021
  - `style`: optional root style object, useful for host layout constraints or CSS variables.
933
1022
  - `title`: optional widget heading. Swap and Engine default to empty for compact embedded chrome.
934
1023
  - `showNetworkSelector`: Engine header-network visibility: `'never'` (default), `'auto'`, or `'always'`. Cross-chain markets and tokens remain available in the full selectors when the header rail is hidden.
935
- - `onSurfaceChange`: Engine callback fired when the active unified tab changes (`'buy'`, `'borrow'`, `'lend'`, or `'positions'`).
1024
+ - `onSurfaceChange`: Engine callback fired when the active unified tab changes (`'buy'`, `'trade'`, `'borrow'`, `'lend'`, or `'positions'`).
936
1025
  - `marketResource`: controlled Lend/Borrow market locator (`chainId`, token `address`, and `symbol`). On the active chain, the widget resolves one eligible Engine market, hides its picker, and fails closed on missing or ambiguous matches. It does not lock token direction. Use `marketId` only as an optional disambiguator for the same resource.
1026
+ - `surfaces`: Engine tabs to expose. Defaults to `['buy', 'borrow', 'lend', 'positions']`. Add `'trade'` to opt into the Long/Short surface (see Trade surface).
1027
+ - `tradeDirections`: directions offered on the Trade surface. Defaults to `['long', 'short']`.
1028
+ - `defaultTradeDirection`: initial Trade direction. Defaults to the first `tradeDirections` entry.
1029
+ - `tradeDirectionSelector`: Long/Short selector visibility — `'auto'` (default) hides it when `tradeDirections` resolves to a single entry, `'always'`, or `'never'`.
1030
+ - `tradeLeverageOptions`: shortcuts shown below the quote-driven leverage slider. Defaults to `[2]`, with a separate live `Max` shortcut; preset values must be above `1` and no greater than `5`. The live Engine quote, not this list, sets the actual minimum and maximum.
1031
+ - `defaultTradeLeverage`: initial Trade leverage. Defaults to `1.5` and does not need to match a shortcut.
1032
+ - `tradeHorizonDays`: horizon used to size the directional position and estimate interest. Defaults to `30`.
1033
+ - `tradePriceMovePercent`: target-price move used to measure average leverage and gross target return. Defaults to `20`.
1034
+ - `tradePositionStorage`: optional async `load`/`save` adapter for confirmed Long/Short opening intent. Omit for origin-local browser persistence, pass `null` to disable off-chain persistence, or provide a host service for cross-device continuity. Host operations receive an optional `{ signal }`, use `timeoutMs` (default `10000`), and must treat `(chainId, account, txHash)` as an idempotent upsert key. Return newest-first records; the widget validates and reads at most 64. Timed-out operations fail softly and are not retried. Indexed actions always own direction and entry price.
1035
+ - `onboarding`: Long/Short education and review options. `mode` is `'guided'` (default) or `'contextual'`; required transaction review cannot be disabled. `motion: 'reduce'` forces the no-travel variant; `storage`, `storageKey`, and safe presentation `copy` overrides support host customization. `howItWorks: false` hides the education link and sheet. `showBeforeConnect: true` opens education once on first view; it stays closed by default. `permissionsWalkthrough: 'auto'` opens setup when a positive deposit still needs wallet access.
1036
+ - `permissionRailColor`: optional Engine permission-step rail color. It defaults to `accentColor` and derives readable rail ink automatically.
1037
+ - `onAuthorizationPlan`: called after the widget reads the connected account's live Long/Short authorization plan.
1038
+ - `onAuthorizationStepChange`: called with `requesting` and `confirmed` progress for each required vault, token, Permit2, and final-open action.
1039
+ - `onOnboardingEvent`: product lifecycle callback for education, review, authorization start, and confirmed-position events.
937
1040
  - `buySwapConfig`: optional host overrides for the nested Engine Buy surface only. Use it to constrain Buy to a chain, pool set, or controlled `poolId` without changing Engine market discovery or the Lend/Borrow/Positions surfaces.
938
1041
  - `showBuySettings`: show the Engine Buy surface's slippage-settings control. Defaults to `false`.
939
1042
  - `showAmountSlider`: amount-slider visibility on the Engine lend/borrow amount boxes: `'auto'` (default) shows sliders on the borrow surface only, sized against the wallet's borrowing limit; `'always'` adds the lend deposit slider; `'never'` hides every amount slider.
@@ -944,7 +1047,9 @@ No other props changed. See the [CHANGELOG](./CHANGELOG.md) for the full entry.
944
1047
  - `accentTextColor`: optional CTA text color for contrast with the chosen accent.
945
1048
  - `baseColor`: CSS base surface color; derives the full neutral ramp (background, panels, borders, text, card gradient) in OKLCH for the active theme with contrast enforced (see Appearance).
946
1049
  - `defaultApprovalMode`: `exact` approves only the current quote spend by default; `max` opts into the old unlimited ERC-20 to Permit2 approval behavior.
947
- - `showApprovalMode`: whether the details drawer exposes the Exact/Max approval toggle. Defaults to `true`.
1050
+ - `showApprovalMode`: whether to show the approval-amount control. On Swap it appears in the details drawer; on Engine Long/Short it appears on the Permit spending-limit row. Defaults to `true`.
1051
+ - `approvalMode`: controlled Engine approval mode (`'exact'` or `'max'`). Omit it to initialize internal state from `defaultApprovalMode`.
1052
+ - `onApprovalModeChange`: fired when the Engine approval mode changes. A controlled host must update `approvalMode` in response.
948
1053
  - `showExecutionDetails`: whether to render the collapsible drawer for trade details and, after a confirmed swap, the session-local Latest tx receipt. Defaults to `true`.
949
1054
  - `defaultExecutionDetailsOpen`: whether that settings drawer starts expanded. Defaults to `false`.
950
1055
  - `executionDetailsOpen`: controlled open state for the Trade details drawer. Omit this for the widget's internal open/closed state.