@b3dotfun/sdk 0.0.29-alpha.3 → 0.0.29-alpha.4

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 (35) hide show
  1. package/dist/cjs/anyspend/react/components/AnyspendDepositHype.js +3 -1
  2. package/dist/cjs/anyspend/react/components/common/ConnectWalletPayment.js +9 -1
  3. package/dist/cjs/anyspend/react/components/common/CryptoPaymentMethod.js +130 -41
  4. package/dist/cjs/anyspend/react/components/common/OrderDetails.js +3 -3
  5. package/dist/cjs/anyspend/react/components/common/PaySection.js +6 -4
  6. package/dist/cjs/anyspend/react/hooks/useAnyspendFlow.js +29 -0
  7. package/dist/cjs/anyspend/react/hooks/useSigMint.d.ts +1 -1
  8. package/dist/cjs/global-account/react/hooks/useUnifiedChainSwitchAndExecute.d.ts +1 -0
  9. package/dist/cjs/global-account/react/hooks/useUnifiedChainSwitchAndExecute.js +1 -0
  10. package/dist/cjs/shared/constants/chains/b3Chain.d.ts +2 -2
  11. package/dist/cjs/shared/constants/chains/supported.d.ts +4 -4
  12. package/dist/esm/anyspend/react/components/AnyspendDepositHype.js +3 -1
  13. package/dist/esm/anyspend/react/components/common/ConnectWalletPayment.js +6 -1
  14. package/dist/esm/anyspend/react/components/common/CryptoPaymentMethod.js +133 -44
  15. package/dist/esm/anyspend/react/components/common/OrderDetails.js +3 -3
  16. package/dist/esm/anyspend/react/components/common/PaySection.js +7 -5
  17. package/dist/esm/anyspend/react/hooks/useAnyspendFlow.js +30 -1
  18. package/dist/esm/anyspend/react/hooks/useSigMint.d.ts +1 -1
  19. package/dist/esm/global-account/react/hooks/useUnifiedChainSwitchAndExecute.d.ts +1 -0
  20. package/dist/esm/global-account/react/hooks/useUnifiedChainSwitchAndExecute.js +1 -0
  21. package/dist/esm/shared/constants/chains/b3Chain.d.ts +2 -2
  22. package/dist/esm/shared/constants/chains/supported.d.ts +4 -4
  23. package/dist/styles/index.css +1 -1
  24. package/dist/types/anyspend/react/hooks/useSigMint.d.ts +1 -1
  25. package/dist/types/global-account/react/hooks/useUnifiedChainSwitchAndExecute.d.ts +1 -0
  26. package/dist/types/shared/constants/chains/b3Chain.d.ts +2 -2
  27. package/dist/types/shared/constants/chains/supported.d.ts +4 -4
  28. package/package.json +1 -1
  29. package/src/anyspend/react/components/AnyspendDepositHype.tsx +4 -0
  30. package/src/anyspend/react/components/common/ConnectWalletPayment.tsx +9 -0
  31. package/src/anyspend/react/components/common/CryptoPaymentMethod.tsx +289 -103
  32. package/src/anyspend/react/components/common/OrderDetails.tsx +3 -3
  33. package/src/anyspend/react/components/common/PaySection.tsx +9 -7
  34. package/src/anyspend/react/hooks/useAnyspendFlow.ts +33 -1
  35. package/src/global-account/react/hooks/useUnifiedChainSwitchAndExecute.ts +1 -0
@@ -1,17 +1,13 @@
1
1
  "use client";
2
2
 
3
3
  import { useAccountWallet } from "@b3dotfun/sdk/global-account/react";
4
- import { thirdwebB3Mainnet } from "@b3dotfun/sdk/shared/constants/chains/b3Chain";
5
4
  import { cn } from "@b3dotfun/sdk/shared/utils/cn";
6
5
  import { shortenAddress } from "@b3dotfun/sdk/shared/utils/formatAddress";
7
- import { client } from "@b3dotfun/sdk/shared/utils/thirdweb";
8
- import { ChevronLeft, ChevronRightCircle, Wallet, X } from "lucide-react";
6
+ import { ChevronLeft, ChevronRightCircle, Wallet, X, ZapIcon } from "lucide-react";
9
7
  import { useState } from "react";
10
8
  import { createPortal } from "react-dom";
11
9
  import { toast } from "sonner";
12
- import { ConnectEmbed, lightTheme, useActiveWallet, useDisconnect as useThirdwebDisconnect } from "thirdweb/react";
13
- import { createWallet } from "thirdweb/wallets";
14
- import { useDisconnect } from "wagmi";
10
+ import { useAccount, useConnect, useDisconnect, useWalletClient } from "wagmi";
15
11
 
16
12
  export enum CryptoPaymentMethodType {
17
13
  NONE = "none",
@@ -41,20 +37,107 @@ export function CryptoPaymentMethod({
41
37
  onSelectPaymentMethod,
42
38
  }: CryptoPaymentMethodProps) {
43
39
  const { wallet: globalWallet } = useAccountWallet();
44
- const activeWallet = useActiveWallet();
40
+ const { address, isConnected, connector } = useAccount();
41
+ const { connect, connectors, isPending } = useConnect();
45
42
  const { disconnect } = useDisconnect();
46
- const { disconnect: disconnectThirdweb } = useThirdwebDisconnect();
43
+ const { data: walletClient } = useWalletClient();
47
44
  const [showWalletModal, setShowWalletModal] = useState(false);
45
+ const [selectedWalletConnector, setSelectedWalletConnector] = useState<any>(null);
46
+ const [modalStep, setModalStep] = useState<"wallet-selection" | "account-selection">("wallet-selection");
48
47
 
49
- // Define available wallets for the modal
50
- const availableWallets = [
51
- createWallet("io.metamask"),
52
- // createWallet("com.coinbase.wallet"),
53
- createWallet("me.rainbow"),
54
- createWallet("walletConnect"),
55
- createWallet("io.rabby"),
56
- createWallet("app.phantom"),
57
- ];
48
+ // Define available wallet connectors
49
+ const availableConnectors = connectors.filter(connector =>
50
+ ["MetaMask", "WalletConnect", "Coinbase Wallet", "Rainbow"].includes(connector.name),
51
+ );
52
+
53
+ // Define wallet options with icons and info
54
+ const walletOptions = [
55
+ {
56
+ id: "metamask",
57
+ name: "MetaMask",
58
+ icon: "🦊",
59
+ description: "Connect using MetaMask browser extension",
60
+ connector: availableConnectors.find(c => c.name === "MetaMask"),
61
+ },
62
+ {
63
+ id: "coinbase",
64
+ name: "Coinbase Wallet",
65
+ icon: "🔵",
66
+ description: "Connect using Coinbase Wallet",
67
+ connector: availableConnectors.find(c => c.name === "Coinbase Wallet"),
68
+ },
69
+ {
70
+ id: "rainbow",
71
+ name: "Rainbow",
72
+ icon: "🌈",
73
+ description: "Connect using Rainbow wallet",
74
+ connector: availableConnectors.find(c => c.name === "Rainbow"),
75
+ },
76
+ {
77
+ id: "walletconnect",
78
+ name: "WalletConnect",
79
+ icon: "🔗",
80
+ description: "Connect using WalletConnect protocol",
81
+ connector: availableConnectors.find(c => c.name === "WalletConnect"),
82
+ },
83
+ ].filter(wallet => wallet.connector); // Only show wallets that have available connectors
84
+
85
+ // Reset modal state when closing
86
+ const handleCloseModal = () => {
87
+ setShowWalletModal(false);
88
+ setModalStep("wallet-selection");
89
+ setSelectedWalletConnector(null);
90
+ };
91
+
92
+ // Function to request wallet permissions for specific wallet
93
+ const requestWalletPermissions = async (walletConnector?: any) => {
94
+ try {
95
+ // If a specific wallet connector is provided and it's different from current
96
+ if (walletConnector && connector?.name !== walletConnector.name) {
97
+ // Disconnect current and connect to the selected wallet
98
+ // if (isConnected) {
99
+ // disconnect();
100
+ // // Small delay to ensure disconnection
101
+ // await new Promise(resolve => setTimeout(resolve, 100));
102
+ // }
103
+ await connect({ connector: walletConnector });
104
+ setSelectedPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
105
+ onSelectPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
106
+ toast.success(`Connected to ${walletConnector.name}`);
107
+ return;
108
+ }
109
+
110
+ // If same wallet or no specific wallet, request permissions for account switching
111
+ if (walletClient && "request" in walletClient) {
112
+ await walletClient.request({
113
+ method: "wallet_requestPermissions",
114
+ params: [{ eth_accounts: {} }],
115
+ });
116
+ toast.success("Account selection completed");
117
+ setSelectedPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
118
+ onSelectPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
119
+ } else {
120
+ // Fallback: show modal for manual wallet selection
121
+ setShowWalletModal(true);
122
+ }
123
+ } catch (error) {
124
+ console.error("Failed to request wallet permissions:", error);
125
+ if (error && typeof error === "object" && "message" in error) {
126
+ const errorMessage = (error as any).message.toLowerCase();
127
+ if (
128
+ errorMessage.includes("rejected") ||
129
+ errorMessage.includes("denied") ||
130
+ errorMessage.includes("cancelled")
131
+ ) {
132
+ toast.error("Account selection cancelled");
133
+ } else {
134
+ toast.error("Failed to open account selection");
135
+ }
136
+ } else {
137
+ toast.error("Failed to open account selection");
138
+ }
139
+ }
140
+ };
58
141
 
59
142
  return (
60
143
  <div className="crypto-payment-method mx-auto h-fit w-[460px] max-w-full">
@@ -68,78 +151,32 @@ export function CryptoPaymentMethod({
68
151
  </button>
69
152
  <div className="flex items-center justify-around gap-4">
70
153
  <div className="flex-1 text-center">
71
- <h2 className="text-as-primary text-lg font-semibold">Choose payment method</h2>
154
+ <h2 className="text-as-primary text-lg font-semibold">Select a payment method</h2>
72
155
  </div>
73
156
  </div>
74
157
 
75
158
  {/* Payment Methods */}
76
- <div className="crypto-payment-methods flex flex-col gap-3">
77
- {/* Connect Wallet Option */}
78
- {!activeWallet ? (
79
- // Not connected - show single connect button
80
- <button
81
- onClick={() => setShowWalletModal(true)}
82
- className="crypto-payment-method-connect-wallet bg-as-surface-primary border-as-border-secondary hover:border-as-secondary/80 group flex w-full items-center justify-between gap-4 rounded-xl border px-4 py-3.5 transition-all duration-200 hover:shadow-md"
83
- >
84
- <div className="flex items-center gap-3">
85
- <div className="wallet-icon flex h-8 w-8 items-center justify-center rounded-full bg-blue-100">
86
- <Wallet className="h-4 w-4 text-blue-600" />
87
- </div>
88
- <div className="flex flex-col items-start text-left">
89
- <h4 className="text-as-primary font-semibold">Connect wallet</h4>
90
- <p className="text-as-primary/60 text-sm">Choose from multiple wallet options</p>
91
- </div>
159
+ <div className="crypto-payment-methods flex flex-col gap-6">
160
+ {/* Connect Wallet Section */}
161
+ <button
162
+ onClick={() => {
163
+ // Always show wallet selection modal first
164
+ setShowWalletModal(true);
165
+ }}
166
+ className="crypto-payment-method-connect-wallet bg-as-surface-primary border-as-border-secondary hover:border-as-secondary/80 group flex w-full items-center justify-between gap-4 rounded-xl border px-4 py-3.5 transition-all duration-200 hover:shadow-md"
167
+ >
168
+ <div className="flex items-center gap-3">
169
+ <div className="wallet-icon flex h-8 w-8 items-center justify-center rounded-full bg-blue-100">
170
+ <Wallet className="h-4 w-4 text-blue-600" />
92
171
  </div>
93
- <ChevronRightCircle className="text-as-primary/40 group-hover:text-as-primary/60 h-5 w-5 transition-colors" />
94
- </button>
95
- ) : (
96
- // Connected - show wallet info
97
- <div className="crypto-payment-method-connect-wallet wallet-connected bg-as-surface-primary border-as-border-secondary rounded-xl border">
98
- <div className="flex items-center justify-between p-4">
99
- <div className="flex items-center gap-3">
100
- {globalWallet?.meta?.icon ? (
101
- <img src={globalWallet.meta.icon} alt="Connected Wallet" className="h-8 w-8 rounded-full" />
102
- ) : (
103
- <div className="wallet-icon flex h-8 w-8 items-center justify-center rounded-full bg-green-100">
104
- <Wallet className="h-4 w-4 text-green-600" />
105
- </div>
106
- )}
107
- <div className="flex flex-col">
108
- <span className="text-as-primary font-semibold">Connected Wallet</span>
109
- <span className="text-as-primary/60 text-sm">
110
- {shortenAddress(activeWallet.getAccount()?.address || "")}
111
- </span>
112
- </div>
113
- </div>
114
- <div className="flex items-center gap-2">
115
- <button
116
- onClick={() => {
117
- setSelectedPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
118
- onSelectPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
119
- }}
120
- className="bg-as-brand hover:bg-as-brand/90 rounded-lg px-3 py-1.5 text-sm font-medium text-white transition-colors"
121
- >
122
- Use Wallet
123
- </button>
124
- <button
125
- onClick={async () => {
126
- disconnect();
127
- disconnectThirdweb(activeWallet);
128
- toast.success("Wallet disconnected");
129
- if (selectedPaymentMethod === CryptoPaymentMethodType.CONNECT_WALLET) {
130
- setSelectedPaymentMethod(CryptoPaymentMethodType.NONE);
131
- }
132
- }}
133
- className="text-as-primary/60 hover:text-as-primary/80 rounded-lg p-1.5 transition-colors"
134
- >
135
- <X className="h-4 w-4" />
136
- </button>
137
- </div>
172
+ <div className="flex flex-col items-start text-left">
173
+ <h4 className="text-as-primary font-semibold">Connect wallet</h4>
138
174
  </div>
139
175
  </div>
140
- )}
176
+ <ChevronRightCircle className="text-as-primary/40 group-hover:text-as-primary/60 h-5 w-5 transition-colors" />
177
+ </button>
141
178
 
142
- {/* Transfer Crypto Option */}
179
+ {/* Transfer Crypto Section */}
143
180
  <button
144
181
  onClick={() => {
145
182
  setSelectedPaymentMethod(CryptoPaymentMethodType.TRANSFER_CRYPTO);
@@ -148,11 +185,73 @@ export function CryptoPaymentMethod({
148
185
  disabled={isCreatingOrder}
149
186
  className="crypto-payment-method-transfer bg-as-surface-primary border-as-border-secondary hover:border-as-secondary/80 group flex w-full items-center justify-between gap-4 rounded-xl border px-4 py-3.5 transition-all duration-200 hover:shadow-md"
150
187
  >
151
- <div className="flex flex-col items-start text-left">
152
- <h4 className="text-as-primary font-semibold">Transfer crypto</h4>
188
+ <div className="flex items-center gap-3">
189
+ <div className="wallet-icon flex h-8 w-8 items-center justify-center rounded-full bg-orange-100">
190
+ <ZapIcon className="h-4 w-4" />
191
+ </div>
192
+ <div className="flex flex-col items-start text-left">
193
+ <h4 className="text-as-primary font-semibold">Transfer crypto</h4>
194
+ </div>
153
195
  </div>
154
196
  <ChevronRightCircle className="text-as-primary/40 group-hover:text-as-primary/60 h-5 w-5 transition-colors" />
155
197
  </button>
198
+
199
+ {/* Installed Wallets Section */}
200
+ {isConnected && (
201
+ <div className="installed-wallets">
202
+ <h3 className="text-as-primary/80 mb-3 text-sm font-medium">Connected wallets</h3>
203
+ <div className="space-y-2">
204
+ {/* Current Connected Wallet */}
205
+ <button
206
+ onClick={() => {
207
+ setSelectedPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
208
+ onSelectPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
209
+ toast.success(`Selected ${connector?.name || "wallet"}`);
210
+ }}
211
+ className={cn(
212
+ "crypto-payment-method-connect-wallet w-full rounded-xl border p-4 text-left transition-all hover:shadow-md",
213
+ selectedPaymentMethod === CryptoPaymentMethodType.CONNECT_WALLET
214
+ ? "connected-wallet border-as-brand bg-as-brand/5"
215
+ : "border-as-border-secondary bg-as-surface-primary hover:border-as-secondary/80",
216
+ )}
217
+ >
218
+ <div className="flex items-center justify-between">
219
+ <div className="flex items-center gap-3">
220
+ {globalWallet?.meta?.icon ? (
221
+ <img src={globalWallet.meta.icon} alt="Wallet" className="h-10 w-10 rounded-full" />
222
+ ) : (
223
+ <div className="wallet-icon flex h-10 w-10 items-center justify-center rounded-full bg-blue-100">
224
+ <Wallet className="h-5 w-5 text-blue-600" />
225
+ </div>
226
+ )}
227
+ <div className="flex flex-col">
228
+ <span className="text-as-primary font-semibold">{connector?.name || "Connected Wallet"}</span>
229
+ <span className="text-as-primary/60 text-sm">{shortenAddress(address || "")}</span>
230
+ </div>
231
+ </div>
232
+ <div className="flex items-center gap-2">
233
+ {selectedPaymentMethod === CryptoPaymentMethodType.CONNECT_WALLET && (
234
+ <div className="h-2 w-2 rounded-full bg-green-500"></div>
235
+ )}
236
+ <button
237
+ onClick={e => {
238
+ e.stopPropagation();
239
+ disconnect();
240
+ toast.success("Wallet disconnected");
241
+ if (selectedPaymentMethod === CryptoPaymentMethodType.CONNECT_WALLET) {
242
+ setSelectedPaymentMethod(CryptoPaymentMethodType.NONE);
243
+ }
244
+ }}
245
+ className="text-as-primary/60 hover:text-as-primary/80 rounded-lg p-1.5 transition-colors"
246
+ >
247
+ <X className="h-4 w-4" />
248
+ </button>
249
+ </div>
250
+ </div>
251
+ </button>
252
+ </div>
253
+ </div>
254
+ )}
156
255
  </div>
157
256
  </div>
158
257
 
@@ -162,32 +261,119 @@ export function CryptoPaymentMethod({
162
261
  <div className="pointer-events-auto fixed inset-0 z-[9999] flex items-center justify-center bg-black/50">
163
262
  <div className="max-h-[80vh] w-[400px] max-w-[90vw] overflow-auto rounded-xl bg-white p-6 dark:bg-gray-900">
164
263
  <div className="mb-4 flex items-center justify-between">
165
- <h3 className="text-lg font-semibold text-gray-900 dark:text-white">Connect Wallet</h3>
264
+ <div className="flex items-center gap-2">
265
+ {modalStep === "account-selection" && (
266
+ <button
267
+ onClick={() => setModalStep("wallet-selection")}
268
+ className="text-gray-500 hover:text-gray-700 dark:text-gray-400 dark:hover:text-gray-200"
269
+ >
270
+ <ChevronLeft className="h-5 w-5" />
271
+ </button>
272
+ )}
273
+ <h3 className="text-lg font-semibold text-gray-900 dark:text-white">
274
+ {modalStep === "wallet-selection"
275
+ ? "Select a payment method"
276
+ : `Connect ${selectedWalletConnector?.name}`}
277
+ </h3>
278
+ </div>
166
279
  <button
167
- onClick={() => setShowWalletModal(false)}
280
+ onClick={handleCloseModal}
168
281
  className="text-gray-500 hover:text-gray-700 dark:text-gray-400 dark:hover:text-gray-200"
169
282
  >
170
283
  <X className="h-5 w-5" />
171
284
  </button>
172
285
  </div>
173
- <ConnectEmbed
174
- client={client}
175
- chain={thirdwebB3Mainnet}
176
- wallets={availableWallets}
177
- showThirdwebBranding={false}
178
- theme={lightTheme()}
179
- onConnect={async wallet => {
180
- console.log("Wallet connected:", wallet);
181
- // setShowWalletModal(false);
182
- setSelectedPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
183
- onSelectPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
184
- setShowWalletModal(false);
185
- }}
186
- style={{
187
- width: "100%",
188
- minHeight: "300px",
189
- }}
190
- />
286
+
287
+ <div className="space-y-4">
288
+ {modalStep === "wallet-selection" ? (
289
+ <>
290
+ {/* Custom wallet options */}
291
+ <div className="space-y-3">
292
+ <h4 className="text-sm font-medium text-gray-700 dark:text-gray-300">
293
+ {isConnected ? "Switch wallet or account" : "Choose wallet to connect"}
294
+ </h4>
295
+ {walletOptions.map(walletOption => {
296
+ const isCurrentWallet = isConnected && connector?.name === walletOption.connector?.name;
297
+
298
+ return (
299
+ <button
300
+ key={walletOption.id}
301
+ onClick={async () => {
302
+ setSelectedWalletConnector(walletOption.connector);
303
+ setModalStep("account-selection");
304
+ }}
305
+ disabled={isPending}
306
+ className={`w-full rounded-xl border p-4 text-left transition-all hover:shadow-md disabled:opacity-50 ${
307
+ isCurrentWallet
308
+ ? "border-blue-500 bg-blue-50 dark:bg-blue-900/20"
309
+ : "border-gray-200 bg-white hover:border-gray-300 dark:border-gray-600 dark:bg-gray-800 dark:hover:border-gray-500"
310
+ }`}
311
+ >
312
+ <div className="flex items-center justify-between">
313
+ <div className="flex items-center gap-3">
314
+ <div
315
+ className={`flex h-12 w-12 items-center justify-center rounded-xl text-xl ${
316
+ isCurrentWallet ? "bg-blue-100 dark:bg-blue-800" : "bg-gray-100 dark:bg-gray-700"
317
+ }`}
318
+ >
319
+ {walletOption.icon}
320
+ </div>
321
+ <div>
322
+ <div className="flex items-center gap-2">
323
+ <div className="text-sm font-semibold text-gray-900 dark:text-white">
324
+ {walletOption.name}
325
+ </div>
326
+ {isCurrentWallet && (
327
+ <span className="rounded-full bg-blue-100 px-2 py-0.5 text-xs font-medium text-blue-700 dark:bg-blue-800 dark:text-blue-200">
328
+ Connected
329
+ </span>
330
+ )}
331
+ </div>
332
+ <div className="text-xs text-gray-500 dark:text-gray-400">
333
+ {isCurrentWallet ? "Switch account or reconnect" : walletOption.description}
334
+ </div>
335
+ </div>
336
+ </div>
337
+ <ChevronRightCircle className="h-5 w-5 text-gray-400" />
338
+ </div>
339
+ </button>
340
+ );
341
+ })}
342
+ </div>
343
+ </>
344
+ ) : (
345
+ /* Account Selection Step */
346
+ <div className="space-y-4">
347
+ <p className="text-sm text-gray-600 dark:text-gray-400">
348
+ Connect to {selectedWalletConnector?.name} to view available accounts
349
+ </p>
350
+ <button
351
+ onClick={async () => {
352
+ handleCloseModal();
353
+ await requestWalletPermissions(selectedWalletConnector);
354
+ }}
355
+ disabled={isPending}
356
+ className="w-full rounded-lg border border-gray-200 bg-white p-4 text-center transition-all hover:border-gray-300 hover:shadow-md disabled:opacity-50 dark:border-gray-600 dark:bg-gray-800 dark:hover:border-gray-500"
357
+ >
358
+ <div className="flex items-center justify-center gap-3">
359
+ <div className="flex h-10 w-10 items-center justify-center rounded-lg bg-gray-100 dark:bg-gray-700">
360
+ <Wallet className="h-5 w-5 text-gray-600 dark:text-gray-400" />
361
+ </div>
362
+ <div>
363
+ <div className="text-sm font-medium text-gray-900 dark:text-white">
364
+ {isPending
365
+ ? `Connecting to ${selectedWalletConnector?.name}...`
366
+ : `Connect ${selectedWalletConnector?.name}`}
367
+ </div>
368
+ <div className="text-xs text-gray-500 dark:text-gray-400">
369
+ {isPending ? "Please check your wallet" : "Click to connect and select account"}
370
+ </div>
371
+ </div>
372
+ </div>
373
+ </button>
374
+ </div>
375
+ )}
376
+ </div>
191
377
  </div>
192
378
  </div>,
193
379
  typeof window !== "undefined" ? document.getElementById("b3-root") || document.body : document.body,
@@ -225,7 +225,7 @@ export const OrderDetails = memo(function OrderDetails({
225
225
  const [showQRCode, setShowQRCode] = useState(false);
226
226
  const { isLoading: txLoading, isSuccess: txSuccess } = useWaitForTransactionReceipt({ hash: txHash });
227
227
 
228
- const { switchChainAndExecute, isSwitchingOrExecuting } = useUnifiedChainSwitchAndExecute();
228
+ const { switchChainAndExecuteWithEOA, isSwitchingOrExecuting } = useUnifiedChainSwitchAndExecute();
229
229
 
230
230
  const { colorMode } = useColorMode();
231
231
 
@@ -260,12 +260,12 @@ export const OrderDetails = memo(function OrderDetails({
260
260
  value = BigInt(0);
261
261
  }
262
262
 
263
- const txHash = await switchChainAndExecute(order.srcChain, { to, data: txData, value });
263
+ const txHash = await switchChainAndExecuteWithEOA(order.srcChain, { to, data: txData, value });
264
264
 
265
265
  if (txHash) {
266
266
  setTxHash(txHash as `0x${string}`);
267
267
  }
268
- }, [order, switchChainAndExecute]);
268
+ }, [order, switchChainAndExecuteWithEOA]);
269
269
 
270
270
  // Main payment handler that triggers chain switch and payment
271
271
  const handlePayment = async () => {
@@ -1,10 +1,11 @@
1
- import { Input, useAccountWallet, useTokenData } from "@b3dotfun/sdk/global-account/react";
1
+ import { Input, useProfile, useTokenData } from "@b3dotfun/sdk/global-account/react";
2
2
  import { formatUsername } from "@b3dotfun/sdk/shared/utils";
3
3
  import { shortenAddress } from "@b3dotfun/sdk/shared/utils/formatAddress";
4
4
  import { formatDisplayNumber } from "@b3dotfun/sdk/shared/utils/number";
5
5
  import { ChevronRight } from "lucide-react";
6
6
  import { motion } from "motion/react";
7
7
  import { useEffect, useRef } from "react";
8
+ import { useAccount } from "wagmi";
8
9
  import { components } from "../../../types/api";
9
10
  import { CryptoPaymentMethodType } from "./CryptoPaymentMethod";
10
11
  import { FiatPaymentMethod } from "./FiatPaymentMethod";
@@ -45,8 +46,9 @@ export function PaySection({
45
46
  onSelectFiatPaymentMethod,
46
47
  anyspendQuote,
47
48
  }: PaySectionProps) {
48
- const { address: globalAddress, wallet: globalWallet, ensName: connectedName } = useAccountWallet();
49
- const connectedAddress = globalWallet?.address;
49
+ const { address: connectedAddress, isConnected } = useAccount();
50
+ const { data: profileData } = useProfile({ address: connectedAddress });
51
+ const connectedName = profileData?.displayName;
50
52
  const { data: srcTokenMetadata } = useTokenData(selectedSrcToken?.chainId, selectedSrcToken?.address);
51
53
 
52
54
  // Add ref to track if we've applied metadata
@@ -88,12 +90,12 @@ export function PaySection({
88
90
  <div className="text-as-primary/50 flex h-7 items-center text-sm">Pay</div>
89
91
  {paymentType === "crypto" ? (
90
92
  <button
91
- className="text-as-tertiarry flex h-7 items-center gap-2 text-sm transition-colors"
93
+ className="text-as-tertiarry flex h-7 items-center gap-2 text-sm transition-colors focus:!outline-none"
92
94
  onClick={onSelectCryptoPaymentMethod}
93
95
  >
94
96
  {selectedCryptoPaymentMethod === CryptoPaymentMethodType.CONNECT_WALLET ? (
95
97
  <>
96
- {globalAddress ? (
98
+ {isConnected ? (
97
99
  <div className="flex items-center gap-1">
98
100
  {connectedName ? formatUsername(connectedName) : shortenAddress(connectedAddress || "")}
99
101
  </div>
@@ -151,7 +153,7 @@ export function PaySection({
151
153
  {paymentType === "crypto" ? (
152
154
  <>
153
155
  <OrderTokenAmount
154
- address={globalAddress}
156
+ address={connectedAddress}
155
157
  context="from"
156
158
  inputValue={srcAmount}
157
159
  onChangeInput={value => {
@@ -172,7 +174,7 @@ export function PaySection({
172
174
  </div>
173
175
  <TokenBalance
174
176
  token={selectedSrcToken}
175
- walletAddress={globalAddress}
177
+ walletAddress={connectedAddress}
176
178
  onChangeInput={value => {
177
179
  setIsSrcInputDirty(true);
178
180
  setSrcAmount(value);
@@ -7,7 +7,7 @@ import {
7
7
  useGeoOnrampOptions,
8
8
  } from "@b3dotfun/sdk/anyspend/react";
9
9
  import { anyspendService } from "@b3dotfun/sdk/anyspend/services/anyspend";
10
- import { useAccountWallet, useProfile } from "@b3dotfun/sdk/global-account/react";
10
+ import { useAccountWallet, useProfile, useRouter, useSearchParamsSSR } from "@b3dotfun/sdk/global-account/react";
11
11
  import { formatTokenAmount, formatUnits } from "@b3dotfun/sdk/shared/utils/number";
12
12
  import { useEffect, useState } from "react";
13
13
  import { toast } from "sonner";
@@ -47,6 +47,9 @@ export function useAnyspendFlow({
47
47
  sourceTokenAddress,
48
48
  sourceTokenChainId,
49
49
  }: UseAnyspendFlowProps) {
50
+ const searchParams = useSearchParamsSSR();
51
+ const router = useRouter();
52
+
50
53
  // Panel and order state
51
54
  const [activePanel, setActivePanel] = useState<PanelView>(loadOrder ? PanelView.ORDER_DETAILS : PanelView.MAIN);
52
55
  const [orderId, setOrderId] = useState<string | undefined>(loadOrder);
@@ -82,6 +85,12 @@ export function useAnyspendFlow({
82
85
  }
83
86
  }, [selectedRecipientAddress, globalAddress]);
84
87
 
88
+ useEffect(() => {
89
+ if (paymentType === "crypto") {
90
+ setSelectedCryptoPaymentMethod(CryptoPaymentMethodType.CONNECT_WALLET);
91
+ }
92
+ }, [paymentType]);
93
+
85
94
  // Fetch specific token when sourceTokenAddress and sourceTokenChainId are provided
86
95
  useEffect(() => {
87
96
  const fetchSourceToken = async () => {
@@ -142,6 +151,17 @@ export function useAnyspendFlow({
142
151
  }
143
152
  }, [anyspendQuote]);
144
153
 
154
+ // Update useEffect for URL parameter to not override loadOrder
155
+ useEffect(() => {
156
+ if (loadOrder) return; // Skip if we have a loadOrder
157
+
158
+ const orderIdParam = searchParams.get("orderId");
159
+ if (orderIdParam) {
160
+ setOrderId(orderIdParam);
161
+ setActivePanel(PanelView.ORDER_DETAILS);
162
+ }
163
+ }, [searchParams, loadOrder]);
164
+
145
165
  // Order creation hooks
146
166
  const { createOrder, isCreatingOrder } = useAnyspendCreateOrder({
147
167
  onSuccess: data => {
@@ -149,6 +169,18 @@ export function useAnyspendFlow({
149
169
  setOrderId(newOrderId);
150
170
  setActivePanel(PanelView.ORDER_DETAILS);
151
171
  onOrderSuccess?.(newOrderId);
172
+
173
+ // Add orderId and payment method to URL for persistence
174
+ const params = new URLSearchParams(searchParams.toString()); // Preserve existing params
175
+ params.set("orderId", newOrderId);
176
+ if (selectedCryptoPaymentMethod !== CryptoPaymentMethodType.NONE) {
177
+ console.log("Setting cryptoPaymentMethod in URL:", selectedCryptoPaymentMethod);
178
+ params.set("cryptoPaymentMethod", selectedCryptoPaymentMethod);
179
+ } else {
180
+ console.log("Payment method is NONE, not setting in URL");
181
+ }
182
+ console.log("Final URL params:", params.toString());
183
+ router.push(`${window.location.pathname}?${params.toString()}`);
152
184
  },
153
185
  onError: error => {
154
186
  console.error(error);
@@ -192,6 +192,7 @@ export function useUnifiedChainSwitchAndExecute() {
192
192
 
193
193
  return {
194
194
  switchChainAndExecute,
195
+ switchChainAndExecuteWithEOA: handleEOASwitchChainAndSendTransaction,
195
196
  isSwitchingOrExecuting,
196
197
  isActiveSmartWallet,
197
198
  isActiveEOAWallet,