@trustwallet/connect-react 0.0.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 (112) hide show
  1. package/LICENSE.md +76 -0
  2. package/README.md +567 -0
  3. package/cli.js +144 -0
  4. package/dist/global-NUJAOJRO.css +132 -0
  5. package/dist/index.d.ts +13 -0
  6. package/dist/index.js +705 -0
  7. package/dist/styles.module-27BC6Q35.module.css +7 -0
  8. package/dist/styles.module-2IXPYHX5.module.css +33 -0
  9. package/dist/styles.module-4I5UVTXZ.module.css +34 -0
  10. package/dist/styles.module-4QHLSLTJ.module.css +9 -0
  11. package/dist/styles.module-5C4YIUDE.module.css +26 -0
  12. package/dist/styles.module-5FM5SDSC.module.css +8 -0
  13. package/dist/styles.module-5L4UXGVZ.module.css +62 -0
  14. package/dist/styles.module-5S7A3MI3.module.css +6 -0
  15. package/dist/styles.module-5TDOAM3X.module.css +5 -0
  16. package/dist/styles.module-BH6BB6HX.module.css +23 -0
  17. package/dist/styles.module-FMH4FUT5.module.css +35 -0
  18. package/dist/styles.module-GCRMKZIZ.module.css +9 -0
  19. package/dist/styles.module-GSNHG7ET.module.css +92 -0
  20. package/dist/styles.module-HR3VQZUH.module.css +44 -0
  21. package/dist/styles.module-IZSJLNB4.module.css +9 -0
  22. package/dist/styles.module-JFMC6A5G.module.css +6 -0
  23. package/dist/styles.module-KIOD6JAJ.module.css +5 -0
  24. package/dist/styles.module-NDDQJHO2.module.css +21 -0
  25. package/dist/styles.module-PXUDS327.module.css +7 -0
  26. package/dist/styles.module-RKS6GYHN.module.css +6 -0
  27. package/dist/styles.module-U5TRY5PT.module.css +123 -0
  28. package/dist/styles.module-U6N4VKTA.module.css +72 -0
  29. package/dist/styles.module-VWMJAIVE.module.css +20 -0
  30. package/dist/styles.module-WGWNXHEK.module.css +5 -0
  31. package/dist/styles.module-Y3MUWEOL.module.css +5 -0
  32. package/dist/styles.module-YJSZIZTZ.module.css +32 -0
  33. package/dist/styles.module-ZISFY5AO.module.css +15 -0
  34. package/dist/styles.module-ZPYBUUD6.module.css +8 -0
  35. package/package.json +53 -0
  36. package/src/context/index.tsx +25 -0
  37. package/src/index.ts +9 -0
  38. package/src/styles/global.css +132 -0
  39. package/src/types/css-modules.d.ts +4 -0
  40. package/src/ui/TrustModal.tsx +31 -0
  41. package/src/ui/buttons/GetTrustButton/components/GetTrustMessage/index.tsx +10 -0
  42. package/src/ui/buttons/GetTrustButton/components/GetTrustMessage/styles.module.css +7 -0
  43. package/src/ui/buttons/GetTrustButton/components/GetTrustWrapper/index.tsx +10 -0
  44. package/src/ui/buttons/GetTrustButton/components/GetTrustWrapper/styles.module.css +5 -0
  45. package/src/ui/buttons/GetTrustButton/index.tsx +21 -0
  46. package/src/ui/buttons/NamespaceButton/index.tsx +62 -0
  47. package/src/ui/buttons/NamespaceButton/styles.module.css +72 -0
  48. package/src/ui/buttons/WalletButton/index.tsx +76 -0
  49. package/src/ui/buttons/WalletButton/styles.module.css +123 -0
  50. package/src/ui/buttons/WalletConnectButton/components/WCGrid/index.tsx +10 -0
  51. package/src/ui/buttons/WalletConnectButton/components/WCGrid/styles.module.css +5 -0
  52. package/src/ui/buttons/WalletConnectButton/components/WCTitle/index.tsx +5 -0
  53. package/src/ui/buttons/WalletConnectButton/components/WCTitle/styles.module.css +8 -0
  54. package/src/ui/buttons/WalletConnectButton/index.tsx +16 -0
  55. package/src/ui/components/Footer/components/FooterDescription/index.tsx +10 -0
  56. package/src/ui/components/Footer/components/FooterDescription/styles.module.css +6 -0
  57. package/src/ui/components/Footer/components/FooterLink/index.tsx +15 -0
  58. package/src/ui/components/Footer/components/FooterLink/styles.module.css +20 -0
  59. package/src/ui/components/Footer/components/FooterWrapper/index.tsx +10 -0
  60. package/src/ui/components/Footer/components/FooterWrapper/styles.module.css +21 -0
  61. package/src/ui/components/Footer/index.tsx +16 -0
  62. package/src/ui/icons/BackIcon.tsx +14 -0
  63. package/src/ui/icons/CheckIcon.tsx +17 -0
  64. package/src/ui/icons/ClearIcon.tsx +13 -0
  65. package/src/ui/icons/CloseIcon.tsx +14 -0
  66. package/src/ui/icons/CopyIcon.tsx +16 -0
  67. package/src/ui/icons/SearchIcon.tsx +20 -0
  68. package/src/ui/icons/Spinner.tsx +7 -0
  69. package/src/ui/inputs/SearchBar/index.tsx +44 -0
  70. package/src/ui/inputs/SearchBar/styles.module.css +62 -0
  71. package/src/ui/layout/ModalBody/index.tsx +15 -0
  72. package/src/ui/layout/ModalBody/styles.module.css +15 -0
  73. package/src/ui/layout/ModalError/index.tsx +9 -0
  74. package/src/ui/layout/ModalError/styles.module.css +9 -0
  75. package/src/ui/layout/ModalHeader/index.tsx +26 -0
  76. package/src/ui/layout/ModalHeader/styles.module.css +92 -0
  77. package/src/ui/layout/ModalOverlay/index.tsx +15 -0
  78. package/src/ui/layout/ModalOverlay/styles.module.css +33 -0
  79. package/src/ui/layout/ModalWrapper/index.tsx +23 -0
  80. package/src/ui/layout/ModalWrapper/styles.module.css +26 -0
  81. package/src/ui/views/MobileWalletsView/components/MobileEmptyState/index.tsx +13 -0
  82. package/src/ui/views/MobileWalletsView/components/MobileEmptyState/styles.module.css +9 -0
  83. package/src/ui/views/MobileWalletsView/components/MobileLoading/index.tsx +5 -0
  84. package/src/ui/views/MobileWalletsView/components/MobileLoading/styles.module.css +9 -0
  85. package/src/ui/views/MobileWalletsView/components/MobileSearch/index.tsx +36 -0
  86. package/src/ui/views/MobileWalletsView/components/MobileSearch/styles.module.css +44 -0
  87. package/src/ui/views/MobileWalletsView/components/MobileWalletsList/index.tsx +46 -0
  88. package/src/ui/views/MobileWalletsView/components/MobileWalletsList/styles.module.css +35 -0
  89. package/src/ui/views/MobileWalletsView/components/MobileWrapper/index.tsx +10 -0
  90. package/src/ui/views/MobileWalletsView/components/MobileWrapper/styles.module.css +6 -0
  91. package/src/ui/views/MobileWalletsView/index.tsx +22 -0
  92. package/src/ui/views/NamespaceView/components/NamespaceGrid/index.tsx +10 -0
  93. package/src/ui/views/NamespaceView/components/NamespaceGrid/styles.module.css +5 -0
  94. package/src/ui/views/NamespaceView/components/NamespaceHeader/index.tsx +20 -0
  95. package/src/ui/views/NamespaceView/components/NamespaceHeader/styles.module.css +34 -0
  96. package/src/ui/views/NamespaceView/index.tsx +16 -0
  97. package/src/ui/views/QRView/components/QRActions/index.tsx +11 -0
  98. package/src/ui/views/QRView/components/QRActions/styles.module.css +8 -0
  99. package/src/ui/views/QRView/components/QRButton/index.tsx +15 -0
  100. package/src/ui/views/QRView/components/QRButton/styles.module.css +32 -0
  101. package/src/ui/views/QRView/components/QRError/index.tsx +9 -0
  102. package/src/ui/views/QRView/components/QRError/styles.module.css +5 -0
  103. package/src/ui/views/QRView/components/QRPlaceholder/index.tsx +10 -0
  104. package/src/ui/views/QRView/components/QRPlaceholder/styles.module.css +7 -0
  105. package/src/ui/views/QRView/components/QRWrapper/index.tsx +14 -0
  106. package/src/ui/views/QRView/components/QRWrapper/styles.module.css +23 -0
  107. package/src/ui/views/QRView/index.tsx +24 -0
  108. package/src/ui/views/WalletsView/components/WalletsGrid/index.tsx +10 -0
  109. package/src/ui/views/WalletsView/components/WalletsGrid/styles.module.css +5 -0
  110. package/src/ui/views/WalletsView/components/WalletsHeader/index.tsx +9 -0
  111. package/src/ui/views/WalletsView/components/WalletsHeader/styles.module.css +6 -0
  112. package/src/ui/views/WalletsView/index.tsx +20 -0
@@ -0,0 +1,32 @@
1
+ .button {
2
+ border: none;
3
+ background: var(--tcui-connect-bg);
4
+ color: var(--tcui-connect-text);
5
+ border-radius: var(--tcui-radius-full);
6
+ padding: 0 16px;
7
+ height: 36px;
8
+ font-weight: 600;
9
+ font-size: 14px;
10
+ cursor: pointer;
11
+ display: inline-flex;
12
+ align-items: center;
13
+ justify-content: center;
14
+ gap: 6px;
15
+ transition: all 0.15s ease;
16
+ white-space: nowrap;
17
+ font-family: inherit;
18
+ width: 85%;
19
+ }
20
+
21
+ .button:hover:not(:disabled) {
22
+ background: var(--tcui-connect-hover);
23
+ }
24
+
25
+ .button:active:not(:disabled) {
26
+ transform: scale(0.98);
27
+ }
28
+
29
+ .button:disabled {
30
+ opacity: 0.5;
31
+ cursor: not-allowed;
32
+ }
@@ -0,0 +1,15 @@
1
+ .body {
2
+ padding: 20px;
3
+ overflow-y: auto;
4
+ display: flex;
5
+ flex-direction: column;
6
+ gap: 16px;
7
+ }
8
+
9
+ /* Mobile styles */
10
+ @media (max-width: 768px) {
11
+ .body {
12
+ padding: 20px;
13
+ flex: 1;
14
+ }
15
+ }
@@ -0,0 +1,8 @@
1
+ .actions {
2
+ display: flex;
3
+ flex-direction: column;
4
+ justify-content: center;
5
+ align-items: center;
6
+ width: 100%;
7
+ gap: 12px;
8
+ }
package/package.json ADDED
@@ -0,0 +1,53 @@
1
+ {
2
+ "name": "@trustwallet/connect-react",
3
+ "version": "0.0.0",
4
+ "description": "React modal UI for TrustConnect SDK",
5
+ "type": "module",
6
+ "main": "./dist/index.js",
7
+ "types": "./dist/index.d.ts",
8
+ "sideEffects": false,
9
+ "exports": {
10
+ ".": {
11
+ "types": "./dist/index.d.ts",
12
+ "import": "./dist/index.js"
13
+ }
14
+ },
15
+ "bin": {
16
+ "connect-ui": "./cli.js"
17
+ },
18
+ "files": [
19
+ "dist",
20
+ "src",
21
+ "cli.js",
22
+ "README.md"
23
+ ],
24
+ "keywords": [
25
+ "trust",
26
+ "connect",
27
+ "sdk",
28
+ "react",
29
+ "modal"
30
+ ],
31
+ "author": "",
32
+ "license": "Apache-2.0",
33
+ "peerDependencies": {
34
+ "react": "^18.0.0 || ^19.0.0",
35
+ "react-dom": "^18.0.0 || ^19.0.0"
36
+ },
37
+ "dependencies": {
38
+ "cuer": "0.0.3",
39
+ "@trustwallet/connect-ui-logic": "0.0.0"
40
+ },
41
+ "devDependencies": {
42
+ "@types/react": "19.2.7",
43
+ "@types/react-dom": "19.2.3",
44
+ "react": "19.2.3",
45
+ "react-dom": "19.2.3",
46
+ "tsup": "8.5.1"
47
+ },
48
+ "scripts": {
49
+ "build": "tsup",
50
+ "dev": "tsup --watch",
51
+ "clean": "rm -rf dist"
52
+ }
53
+ }
@@ -0,0 +1,25 @@
1
+ import {
2
+ TrustModalProvider,
3
+ type Theme,
4
+ TrustConnectProvider as _TrustConnectProvider,
5
+ TrustConnectOptions,
6
+ } from '@trustwallet/connect-ui-logic'
7
+ import { TrustModal } from '../ui/TrustModal'
8
+ import { ReactNode } from 'react'
9
+
10
+ export type TrustConnectProviderProps = {
11
+ children: ReactNode
12
+ config: TrustConnectOptions
13
+ theme?: Theme
14
+ }
15
+
16
+ export function TrustConnectProvider({ children, config, theme }: TrustConnectProviderProps) {
17
+ return (
18
+ <_TrustConnectProvider config={config}>
19
+ <TrustModalProvider theme={theme}>
20
+ {children}
21
+ <TrustModal />
22
+ </TrustModalProvider>
23
+ </_TrustConnectProvider>
24
+ )
25
+ }
package/src/index.ts ADDED
@@ -0,0 +1,9 @@
1
+ export {
2
+ useTrustModal,
3
+ useTheme,
4
+ useConnection,
5
+ useConnections,
6
+ useConnect,
7
+ } from '@trustwallet/connect-ui-logic'
8
+ export type { Theme, ResolvedTheme, NamespaceId, Connections, RpcUrls } from '@trustwallet/connect-ui-logic'
9
+ export { TrustConnectProvider } from './context'
@@ -0,0 +1,132 @@
1
+ :root,
2
+ [data-tcui-theme='light'] {
3
+ --tcui-font-family: Inter, system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
4
+ --tcui-bg: #f9fafb;
5
+ --tcui-bg-secondary: #f3f4f6;
6
+ --tcui-card: #ffffff;
7
+ --tcui-card-hover: #f9fafb;
8
+ --tcui-text: #111827;
9
+ --tcui-text-secondary: #6b7280;
10
+ --tcui-accent: #0500FF;
11
+ --tcui-border: #e5e7eb;
12
+ --tcui-success: #22c55e;
13
+ --tcui-danger: #dc2626;
14
+ --tcui-connect-bg: #eef2ff;
15
+ --tcui-connect-text: #0500FF;
16
+ --tcui-connect-hover: #e0e7ff;
17
+ --tcui-disconnect-bg: #f3f4f6;
18
+ --tcui-disconnect-text: #6b7280;
19
+ --tcui-disconnect-hover: #e5e7eb;
20
+ --tcui-radius: 14px;
21
+ --tcui-radius-sm: 8px;
22
+ --tcui-radius-lg: 20px;
23
+ --tcui-radius-full: 999px;
24
+ --tcui-shadow-lg: 0 10px 30px rgba(0, 0, 0, 0.08);
25
+ --tcui-primary: #0500FF;
26
+ }
27
+
28
+ [data-tcui-theme='dark'] {
29
+ --tcui-bg: #121213;
30
+ --tcui-bg-secondary: #18181a;
31
+ --tcui-card: #161618;
32
+ --tcui-card-hover: #1f1f23;
33
+ --tcui-text: #eef5ef;
34
+ --tcui-text-secondary: #b3c1b6;
35
+ --tcui-accent: #48ff91;
36
+ --tcui-border: #2a2a2e;
37
+ --tcui-success: #48ff91;
38
+ --tcui-danger: #ff7d7d;
39
+ --tcui-connect-bg: rgba(72, 255, 145, 0.12);
40
+ --tcui-connect-text: #48ff91;
41
+ --tcui-connect-hover: rgba(72, 255, 145, 0.18);
42
+ --tcui-disconnect-bg: #242427;
43
+ --tcui-disconnect-text: #9ca4a2;
44
+ --tcui-disconnect-hover: #2e2e33;
45
+ --tcui-radius: 14px;
46
+ --tcui-radius-sm: 8px;
47
+ --tcui-radius-lg: 20px;
48
+ --tcui-radius-full: 999px;
49
+ --tcui-shadow-lg: 0 20px 40px rgba(0, 0, 0, 0.6);
50
+ --tcui-primary: #48ff91;
51
+ }
52
+
53
+ * {
54
+ box-sizing: border-box;
55
+ }
56
+
57
+ /* Shared utility classes for components that still need them */
58
+ .tcui-button {
59
+ border: none;
60
+ border-radius: var(--tcui-radius-full);
61
+ padding: 0 16px;
62
+ height: 36px;
63
+ font-weight: 600;
64
+ font-size: 14px;
65
+ cursor: pointer;
66
+ display: inline-flex;
67
+ align-items: center;
68
+ justify-content: center;
69
+ gap: 6px;
70
+ transition: all 0.15s ease;
71
+ white-space: nowrap;
72
+ font-family: inherit;
73
+ min-width: fit-content;
74
+ background: var(--tcui-disconnect-bg);
75
+ color: var(--tcui-disconnect-text);
76
+ }
77
+
78
+ .tcui-button[data-loading='true'] {
79
+ min-width: 90px;
80
+ padding: 0;
81
+ }
82
+
83
+ .tcui-button:hover:not(:disabled) {
84
+ background: var(--tcui-disconnect-hover);
85
+ }
86
+
87
+ .tcui-button:active:not(:disabled) {
88
+ transform: scale(0.98);
89
+ }
90
+
91
+ .tcui-button:disabled {
92
+ opacity: 0.5;
93
+ cursor: not-allowed;
94
+ }
95
+
96
+ .tcui-button-primary {
97
+ background: var(--tcui-connect-bg);
98
+ color: var(--tcui-connect-text);
99
+ }
100
+
101
+ .tcui-button-primary:hover:not(:disabled) {
102
+ background: var(--tcui-connect-hover);
103
+ }
104
+
105
+ .tcui-check-icon {
106
+ width: 14px;
107
+ height: 14px;
108
+ color: var(--tcui-success);
109
+ flex-shrink: 0;
110
+ }
111
+
112
+ [data-tcui-theme='light'] .tcui-check-icon {
113
+ color: var(--tcui-connect-text);
114
+ }
115
+
116
+ .tcui-spinner {
117
+ width: 16px;
118
+ height: 16px;
119
+ border-radius: 50%;
120
+ border: 2px solid var(--tcui-border);
121
+ border-top-color: var(--tcui-accent);
122
+ animation: tcui-spin 0.7s linear infinite;
123
+ }
124
+
125
+ @keyframes tcui-spin {
126
+ from {
127
+ transform: rotate(0deg);
128
+ }
129
+ to {
130
+ transform: rotate(360deg);
131
+ }
132
+ }
@@ -0,0 +1,4 @@
1
+ declare module '*.module.css' {
2
+ const classes: { [key: string]: string }
3
+ export default classes
4
+ }
@@ -0,0 +1,31 @@
1
+ import '../styles/global.css'
2
+ import { TrustModalLogic } from '@trustwallet/connect-ui-logic'
3
+ import { MobileWalletsView } from './views/MobileWalletsView'
4
+ import { WalletsView } from './views/WalletsView'
5
+ import { NamespaceView } from './views/NamespaceView'
6
+ import { QRView } from './views/QRView'
7
+ import { ModalOverlay } from './layout/ModalOverlay'
8
+ import { ModalWrapper } from './layout/ModalWrapper'
9
+ import { ModalHeader } from './layout/ModalHeader'
10
+ import { ModalBody } from './layout/ModalBody'
11
+ import { ModalError } from './layout/ModalError'
12
+
13
+ export function TrustModal() {
14
+ return (
15
+ <TrustModalLogic
16
+ layout={{
17
+ overlay: ModalOverlay,
18
+ wrapper: ModalWrapper,
19
+ header: ModalHeader,
20
+ body: ModalBody,
21
+ error: ModalError,
22
+ }}
23
+ views={[
24
+ { title: 'Connect a wallet', tag: 'wallets', node: WalletsView },
25
+ { title: 'Select a network', tag: 'networks', node: NamespaceView },
26
+ { title: 'Scan with mobile wallet', tag: 'qr', node: QRView },
27
+ ]}
28
+ mobileViews={[{ title: 'Connect a wallet', tag: 'wallets', node: MobileWalletsView }]}
29
+ />
30
+ )
31
+ }
@@ -0,0 +1,10 @@
1
+ import { ReactNode } from 'react'
2
+ import styles from './styles.module.css'
3
+
4
+ interface GetTrustMessageProps {
5
+ children: ReactNode
6
+ }
7
+
8
+ export function GetTrustMessage({ children }: GetTrustMessageProps) {
9
+ return <div className={styles.message}>{children}</div>
10
+ }
@@ -0,0 +1,7 @@
1
+ .message {
2
+ color: var(--tcui-text-secondary);
3
+ font-size: 14px;
4
+ line-height: 1.5;
5
+ text-align: center;
6
+ padding: 0 16px;
7
+ }
@@ -0,0 +1,10 @@
1
+ import { ReactNode } from 'react'
2
+ import styles from './styles.module.css'
3
+
4
+ interface GetTrustWrapperProps {
5
+ children: ReactNode
6
+ }
7
+
8
+ export function GetTrustWrapper({ children }: GetTrustWrapperProps) {
9
+ return <div className={styles.container}>{children}</div>
10
+ }
@@ -0,0 +1,5 @@
1
+ .container {
2
+ display: flex;
3
+ flex-direction: column;
4
+ gap: 16px;
5
+ }
@@ -0,0 +1,21 @@
1
+ import { GetTrustButtonLogic } from '@trustwallet/connect-ui-logic'
2
+ import { GetTrustWrapper } from './components/GetTrustWrapper'
3
+ import { GetTrustMessage } from './components/GetTrustMessage'
4
+ import { WalletButton } from '../WalletButton'
5
+
6
+ interface GetTrustButtonProps {
7
+ message?: string
8
+ }
9
+
10
+ export function GetTrustButton({ message }: GetTrustButtonProps) {
11
+ return (
12
+ <GetTrustButtonLogic
13
+ message={message}
14
+ components={{
15
+ wrapper: GetTrustWrapper,
16
+ message: GetTrustMessage,
17
+ walletButton: WalletButton,
18
+ }}
19
+ />
20
+ )
21
+ }
@@ -0,0 +1,62 @@
1
+ import type { KeyboardEvent as ReactKeyboardEvent } from 'react'
2
+ import styles from './styles.module.css'
3
+ import { Spinner } from '../../icons/Spinner'
4
+
5
+ type NamespaceButtonProps = {
6
+ label: string
7
+ icon: string
8
+ onClick?: () => void
9
+ actionLabel?: string
10
+ loading?: boolean
11
+ disabled?: boolean
12
+ connectedWallet?: { id: string; name: string; icon: string } | null
13
+ }
14
+
15
+ export function NamespaceButton({
16
+ icon,
17
+ label,
18
+ onClick,
19
+ actionLabel,
20
+ loading,
21
+ disabled,
22
+ connectedWallet,
23
+ }: NamespaceButtonProps) {
24
+ const handleClick = () => {
25
+ if (!disabled && !loading) {
26
+ onClick?.()
27
+ }
28
+ }
29
+
30
+ return (
31
+ <div
32
+ className={styles.namespaceButton}
33
+ role="button"
34
+ tabIndex={0}
35
+ onClick={handleClick}
36
+ onKeyDown={(event: ReactKeyboardEvent<HTMLDivElement>) => {
37
+ if (event.key === 'Enter' || event.key === ' ') {
38
+ event.preventDefault()
39
+ handleClick()
40
+ }
41
+ }}
42
+ data-disabled={disabled}
43
+ data-loading={loading}
44
+ >
45
+ <img width={28} src={icon} />
46
+ <span className={styles.meta}>
47
+ <span className={styles.name}>{label}</span>
48
+ {connectedWallet && (
49
+ <span className={styles.connectedWith}>
50
+ <img src={connectedWallet.icon} alt="" className={styles.connectedWalletIcon} />
51
+ {connectedWallet.name}
52
+ </span>
53
+ )}
54
+ </span>
55
+ {actionLabel && (
56
+ <span className="tcui-button tcui-button-primary" data-loading={loading}>
57
+ {loading ? <Spinner /> : actionLabel}
58
+ </span>
59
+ )}
60
+ </div>
61
+ )
62
+ }
@@ -0,0 +1,72 @@
1
+ .namespaceButton {
2
+ background: var(--tcui-card);
3
+ border: 1px solid var(--tcui-border);
4
+ border-radius: var(--tcui-radius);
5
+ padding: 12px 14px;
6
+ height: 64px;
7
+ display: flex;
8
+ align-items: center;
9
+ gap: 12px;
10
+ cursor: pointer;
11
+ transition: all 0.15s ease;
12
+ position: relative;
13
+ }
14
+
15
+ .namespaceButton:hover {
16
+ background: var(--tcui-card-hover);
17
+ }
18
+
19
+ .namespaceButton:active {
20
+ transform: scale(0.99);
21
+ }
22
+
23
+ .icon {
24
+ width: 40px;
25
+ height: 40px;
26
+ border-radius: 50%;
27
+ background: var(--tcui-bg-secondary);
28
+ display: inline-flex;
29
+ align-items: center;
30
+ justify-content: center;
31
+ overflow: hidden;
32
+ flex-shrink: 0;
33
+ font-weight: 700;
34
+ font-size: 16px;
35
+ color: var(--tcui-accent);
36
+ text-transform: uppercase;
37
+ }
38
+
39
+ .meta {
40
+ display: flex;
41
+ flex-direction: column;
42
+ gap: 2px;
43
+ flex: 1;
44
+ min-width: 0;
45
+ }
46
+
47
+ .name {
48
+ font-weight: 600;
49
+ font-size: 15px;
50
+ line-height: 1.4;
51
+ display: flex;
52
+ align-items: center;
53
+ gap: 6px;
54
+ }
55
+
56
+ .connectedWith {
57
+ font-size: 12px;
58
+ color: var(--tcui-text-secondary);
59
+ display: flex;
60
+ align-items: center;
61
+ gap: 4px;
62
+ }
63
+
64
+ .connectedWalletIcon {
65
+ width: 14px;
66
+ height: 14px;
67
+ border-radius: 50%;
68
+ }
69
+
70
+ .namespaceBar:hover :global(.tcui-button-primary) {
71
+ background: var(--tcui-connect-hover);
72
+ }
@@ -0,0 +1,76 @@
1
+ import { type KeyboardEvent as ReactKeyboardEvent } from 'react'
2
+ import styles from './styles.module.css'
3
+ import { CheckIcon } from '../../icons/CheckIcon'
4
+ import { Spinner } from '../../icons/Spinner'
5
+
6
+ type WalletButtonProps = {
7
+ name: string
8
+ icon: string
9
+ variant?: 'default' | 'walletconnect'
10
+ active?: boolean
11
+ actionLabel?: string
12
+ onClick?: () => void
13
+ disabled?: boolean
14
+ loading?: boolean
15
+ error?: string
16
+ supportedNamespaceIcons?: string[]
17
+ }
18
+
19
+ export function WalletButton({
20
+ name,
21
+ icon,
22
+ variant = 'default',
23
+ active = false,
24
+ actionLabel = 'Connect',
25
+ onClick,
26
+ disabled,
27
+ loading,
28
+ error,
29
+ supportedNamespaceIcons,
30
+ }: WalletButtonProps) {
31
+ const handleClick = () => {
32
+ if (!disabled && !loading) {
33
+ onClick?.()
34
+ }
35
+ }
36
+
37
+ return (
38
+ <div
39
+ className={styles.walletButton}
40
+ data-variant={variant}
41
+ data-active={active}
42
+ data-disabled={disabled}
43
+ data-loading={loading}
44
+ role="button"
45
+ tabIndex={0}
46
+ onClick={handleClick}
47
+ onKeyDown={(event: ReactKeyboardEvent<HTMLDivElement>) => {
48
+ if (event.key === 'Enter' || event.key === ' ') {
49
+ event.preventDefault()
50
+ handleClick()
51
+ }
52
+ }}
53
+ >
54
+ <span className={styles.icon} aria-hidden>
55
+ <img src={icon} alt={name} />
56
+ </span>
57
+ <span className={styles.meta}>
58
+ <span className={styles.name}>
59
+ {name}
60
+ {active && <CheckIcon />}
61
+ </span>
62
+ {supportedNamespaceIcons && supportedNamespaceIcons.length > 0 && (
63
+ <span className={styles.namespaces}>
64
+ {supportedNamespaceIcons.map((nsIcon, i) => (
65
+ <img key={i} src={nsIcon} alt="" />
66
+ ))}
67
+ </span>
68
+ )}
69
+ {error && <span className={styles.error}>{error}</span>}
70
+ </span>
71
+ <span className={`tcui-button ${active ? '' : 'tcui-button-primary'}`} data-loading={loading}>
72
+ {loading ? <Spinner /> : actionLabel}
73
+ </span>
74
+ </div>
75
+ )
76
+ }