diff --git a/bun.lockb b/bun.lockb index 78471b8a..355de7c9 100755 Binary files a/bun.lockb and b/bun.lockb differ diff --git a/components/3js/animatedAsterisk.tsx b/components/3js/animatedAsterisk.tsx index 3c3eab15..def58b9c 100644 --- a/components/3js/animatedAsterisk.tsx +++ b/components/3js/animatedAsterisk.tsx @@ -208,11 +208,9 @@ export default function AnimatedAsterisk({ onLoad }: { onLoad?: () => void }) { style={{ position: 'absolute', top: 0, left: 0, width: '100%', height: '100%' }} camera={{ position: [0, 0, 10] }} > - - {meshes} - + ); diff --git a/components/3js/animatedMesh.tsx b/components/3js/animatedMesh.tsx index 3450bb20..b536b478 100644 --- a/components/3js/animatedMesh.tsx +++ b/components/3js/animatedMesh.tsx @@ -174,11 +174,9 @@ export default function AnimatedShape({ style={{ position: 'absolute', top: 0, left: 0, width: '100%', height: '100%' }} camera={{ position: [0, 0, 10] }} > - - {meshes} - + diff --git a/components/3js/pennRoseTriangleScene.tsx b/components/3js/pennRoseTriangleScene.tsx index 1acf79c9..f4a4fc6c 100644 --- a/components/3js/pennRoseTriangleScene.tsx +++ b/components/3js/pennRoseTriangleScene.tsx @@ -148,7 +148,6 @@ function PenroseTriangleScene({ onLoad }: { onLoad: () => void }) { {/* Lighting */} - {/* Suspense for async loading */} @@ -156,7 +155,7 @@ function PenroseTriangleScene({ onLoad }: { onLoad: () => void }) { {/* Environment */} - + {/* Adjust the plane to be closer to the Penrose Triangle */} diff --git a/components/bank/forms/sendForm.tsx b/components/bank/forms/sendForm.tsx index a634990c..b1155dce 100644 --- a/components/bank/forms/sendForm.tsx +++ b/components/bank/forms/sendForm.tsx @@ -136,7 +136,6 @@ export default function SendForm({ amount: [{ denom: values.selectedToken.coreDenom, amount: amountInBaseUnits }], }); - console.log('Estimating fee for address:', address); const fee = await estimateFee(address, [msg]); await tx([msg], { @@ -150,7 +149,6 @@ export default function SendForm({ }); } catch (error) { console.error('Error during sending:', error); - // You might want to show this error to the user through a toast or alert } finally { setIsSending(false); } diff --git a/components/groups/modals/memberManagementModal.tsx b/components/groups/modals/memberManagementModal.tsx index 7502075d..8766683e 100644 --- a/components/groups/modals/memberManagementModal.tsx +++ b/components/groups/modals/memberManagementModal.tsx @@ -128,8 +128,6 @@ export function MemberManagementModal({ weight: member.markedForDeletion ? '0' : member.weight || '1', })); - console.log('Member updates:', memberUpdates); - const msg = updateGroupMembers({ admin: groupAdmin, groupId: BigInt(groupId), diff --git a/components/react/modal.tsx b/components/react/modal.tsx index 145a235a..474960f4 100644 --- a/components/react/modal.tsx +++ b/components/react/modal.tsx @@ -3,9 +3,20 @@ import type { ChainWalletBase, WalletModalProps } from 'cosmos-kit'; import { WalletStatus } from 'cosmos-kit'; import React, { useCallback, Fragment, useState, useMemo, useEffect } from 'react'; import { Dialog, Transition, Portal } from '@headlessui/react'; -import { Connected, Connecting, Error, NotExist, QRCode, WalletList, Contacts } from './views'; +import { + Connected, + Connecting, + Error, + NotExist, + QRCode, + WalletList, + Contacts, + EmailInput, + SMSInput, +} from './views'; import { useRouter } from 'next/router'; import { ToastProvider } from '@/contexts/toastContext'; +import { Web3AuthClient, Web3AuthWallet } from '@cosmos-kit/web3auth'; import { useDeviceDetect } from '@/hooks'; export enum ModalView { WalletList, @@ -15,6 +26,8 @@ export enum ModalView { Error, NotExist, Contacts, + EmailInput, + SMSInput, } export const TailwindModal: React.FC< @@ -79,17 +92,29 @@ export const TailwindModal: React.FC< const onWalletClicked = useCallback( (name: string) => { + const wallet = walletRepo?.getWallet(name); + if (wallet?.walletInfo.prettyName === 'Email') { + setCurrentView(ModalView.EmailInput); + return; + } + if (wallet?.walletInfo.prettyName === 'SMS') { + setCurrentView(ModalView.SMSInput); + return; + } + walletRepo?.connect(name); - // 1ms timeout prevents _render from determining the view to show first setTimeout(() => { - const wallet = walletRepo?.getWallet(name); - - if (wallet?.isWalletNotExist) { + if ( + wallet?.walletInfo.name === 'cosmos-extension-metamask' && + wallet.message?.includes("Cannot read properties of undefined (reading 'request')") + ) { setCurrentView(ModalView.NotExist); setSelectedWallet(wallet); - } - if (wallet?.walletInfo.mode === 'wallet-connect') { + } else if (wallet?.isWalletNotExist) { + setCurrentView(ModalView.NotExist); + setSelectedWallet(wallet); + } else if (wallet?.walletInfo.mode === 'wallet-connect') { setCurrentView(isMobile ? ModalView.Connecting : ModalView.QRCode); setQRWallet(wallet); } @@ -112,6 +137,48 @@ export const TailwindModal: React.FC< wallets={walletRepo?.wallets || []} /> ); + case ModalView.EmailInput: + return ( + setCurrentView(ModalView.WalletList)} + onSubmit={async email => { + try { + const emailWallet = walletRepo?.wallets.find( + w => w.walletInfo.prettyName === 'Email' + ) as Web3AuthWallet | undefined; + + if (emailWallet?.client instanceof Web3AuthClient) { + emailWallet.client.setLoginHint(email); + await walletRepo?.connect(emailWallet.walletInfo.name); + } else { + console.error('Email wallet or client not found'); + } + } catch (error) { + console.error('Email login error:', error); + // Handle the error appropriately in your UI + } + }} + /> + ); + + case ModalView.SMSInput: + return ( + setCurrentView(ModalView.WalletList)} + onSubmit={phone => { + const smsWallet = walletRepo?.wallets.find(w => w.walletInfo.prettyName === 'SMS') as + | Web3AuthWallet + | undefined; + + if (smsWallet?.client instanceof Web3AuthClient) { + smsWallet.client.setLoginHint(phone); + walletRepo?.connect(smsWallet.walletInfo.name); + } + }} + /> + ); case ModalView.Connected: return ( { if (address) { @@ -50,7 +49,7 @@ export const Connected = ({
diff --git a/components/react/views/EmailInput.tsx b/components/react/views/EmailInput.tsx new file mode 100644 index 00000000..f8c13f0c --- /dev/null +++ b/components/react/views/EmailInput.tsx @@ -0,0 +1,85 @@ +import { XMarkIcon, ArrowLeftIcon, ChevronLeftIcon } from '@heroicons/react/24/outline'; +import { Formik, Form } from 'formik'; +import * as Yup from 'yup'; +import { TextInput } from '../inputs/TextInput'; +import { Dialog } from '@headlessui/react'; +import Image from 'next/image'; +import { getRealLogo } from '@/utils'; + +const validationSchema = Yup.object({ + email: Yup.string() + .matches(/^[a-zA-Z0-9._-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/, 'Please enter a valid email address') + .required('Email is required') + .max(254, 'Email is too long') + .trim(), +}); + +export const EmailInput = ({ + onClose, + onReturn, + onSubmit, +}: { + onClose: () => void; + onReturn: () => void; + onSubmit: (email: string) => void; +}) => { + const isDarkMode = document.documentElement.classList.contains('dark'); + return ( +
+
+ +
+ Email + + Email + +
+ +
+
+ onSubmit(values.email)} + > + {({ isValid, dirty }) => ( +
+ + + + + )} +
+
+
+ ); +}; diff --git a/components/react/views/Error.tsx b/components/react/views/Error.tsx index d32482a8..f59961f6 100644 --- a/components/react/views/Error.tsx +++ b/components/react/views/Error.tsx @@ -25,7 +25,7 @@ export const Error = ({
- {name} + {name === 'Cosmos MetaMask Extension' ? 'Metamask' : name}
{name} -

Install {name}

+

+ Install {name === 'Cosmos MetaMask Extension' ? 'Metamask' : name} +

- To connect your {name} wallet, install the browser extension. + To connect your {name === 'Cosmos MetaMask Extension' ? 'Metamask' : name} wallet, install + the browser extension.

diff --git a/components/react/views/QRCode.tsx b/components/react/views/QRCode.tsx index 2fbb86a4..5a04faac 100644 --- a/components/react/views/QRCode.tsx +++ b/components/react/views/QRCode.tsx @@ -21,7 +21,7 @@ export const QRCode = ({
+
+ SMS + + SMS + +
+ +
+
+ { + const fullNumber = `${selectedCountryCode}-${values.phoneNumber}`; + onSubmit(fullNumber); + }} + enableReinitialize + > + {({ isValid, dirty }) => ( +
+
+
+ +
+ + {isDropdownOpen && ( +
    + {countryCodes.map(({ code, FlagComponent, country }) => ( +
  • + +
  • + ))} +
+ )} +
+
+
+ } + /> +
+
+ +
+ Enter your phone number without country code +
+ + +
+ )} +
+
+ + ); +}; diff --git a/components/react/views/WalletList.tsx b/components/react/views/WalletList.tsx index 05923551..026f7bdd 100644 --- a/components/react/views/WalletList.tsx +++ b/components/react/views/WalletList.tsx @@ -13,17 +13,17 @@ export const WalletList = ({ onWalletClicked: (name: string) => void; wallets: ChainWalletBase[]; }) => { - // Can't use `useTheme` here because it's not wrapped in a ThemeProvider const isDarkMode = document.documentElement.classList.contains('dark'); const social = wallets.filter(wallet => - ['Google', 'Twitter', 'Apple', 'Discord', 'GitHub', 'Reddit'].includes( + ['Google', 'Twitter', 'Apple', 'Discord', 'GitHub', 'Reddit', 'Email', 'SMS'].includes( wallet.walletInfo.prettyName ) ); - const browser = wallets.filter(wallet => - ['Keplr', 'Cosmostation', 'Leap', 'Station', 'Ledger'].includes(wallet.walletInfo.prettyName) + ['Keplr', 'Cosmostation', 'Leap', 'Station', 'Cosmos MetaMask Extension', 'Ledger'].includes( + wallet.walletInfo.prettyName + ) ); const mobile = wallets.filter(wallet => @@ -37,13 +37,13 @@ export const WalletList = ({

Connect Wallet

- {/* Browser and Social sections - browaer hidden on mobile/tablet */} + {/* Browser and Social sections - browser hidden on mobile/tablet */}
{browser.map(({ walletInfo: { name, prettyName, logo } }) => ( @@ -53,11 +53,17 @@ export const WalletList = ({ className="flex items-center w-full p-3 rounded-lg dark:bg-[#ffffff0c] bg-[#f0f0ff5c] dark:hover:bg-[#0000004c] hover:bg-[#a8a8a84c] transition" > {prettyName} - {prettyName} + + {prettyName === 'Cosmos MetaMask Extension' ? 'MetaMask' : prettyName} + ))}
diff --git a/components/react/views/index.ts b/components/react/views/index.ts index 05da9053..ee968026 100644 --- a/components/react/views/index.ts +++ b/components/react/views/index.ts @@ -5,3 +5,5 @@ export * from './NotExist'; export * from './QRCode'; export * from './WalletList'; export * from './Contacts'; +export * from './EmailInput'; +export * from './SMSInput'; diff --git a/components/toast.tsx b/components/toast.tsx index 8bd93d24..a5624f16 100644 --- a/components/toast.tsx +++ b/components/toast.tsx @@ -97,7 +97,7 @@ export const Toast: React.FC = ({ toastMessage, setToastMessage }) = )}