From 297ea8f1b2db8a56da9abadbc5698e5de5179bd8 Mon Sep 17 00:00:00 2001 From: Hugo Montenegro Date: Thu, 17 Aug 2023 12:16:37 +0200 Subject: [PATCH 1/3] fixed navbar padding --- package.json | 2 +- src/components/global/header/header.tsx | 8 +- yarn.lock | 1962 ++++++++++++----------- 3 files changed, 994 insertions(+), 978 deletions(-) diff --git a/package.json b/package.json index a2cbdbde4..76e6f4bb8 100644 --- a/package.json +++ b/package.json @@ -9,8 +9,8 @@ "lint": "next lint" }, "dependencies": { + "@squirrel-labs/peanut-sdk": "*", "@socket.tech/socket-v2-sdk": "^1.21.8", - "@squirrel-labs/peanut-sdk": "0.0.76", "@types/node": "20.4.2", "@types/react": "18.2.15", "@types/react-dom": "18.2.7", diff --git a/src/components/global/header/header.tsx b/src/components/global/header/header.tsx index ee9e1c386..d3bdbb5b4 100644 --- a/src/components/global/header/header.tsx +++ b/src/components/global/header/header.tsx @@ -16,10 +16,10 @@ export function Header({ showMarquee = true }: { showMarquee?: boolean }) { return (
-
- ); + return ( +
+ + +
+
+

+ Hey there! This is how we treat ur data. +

+

+ 404: Not Found. +

+ +
+ Hit us up on{' '} + + Discord + + ! +
+
+
+ +
+
+
+
+ +
+ ) } diff --git a/src/app/page.tsx b/src/app/page.tsx index a75914e82..8ff831207 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -1,11 +1,11 @@ -"use client"; -import * as global_components from "@/components/global"; -import * as components from "@/components"; +'use client' +import * as global_components from '@/components/global' +import * as components from '@/components' export default function Home() { - return ( - - - - ); + return ( + + + + ) } diff --git a/src/app/privacy/page.tsx b/src/app/privacy/page.tsx index 9e1579c06..bb912d922 100644 --- a/src/app/privacy/page.tsx +++ b/src/app/privacy/page.tsx @@ -1,11 +1,11 @@ -"use client"; -import * as global_components from "@/components/global"; -import * as components from "@/components"; +'use client' +import * as global_components from '@/components/global' +import * as components from '@/components' export default function PrivacyPage() { - return ( - - - - ); + return ( + + + + ) } diff --git a/src/app/terms/page.tsx b/src/app/terms/page.tsx index 22545bbdc..76d47056c 100644 --- a/src/app/terms/page.tsx +++ b/src/app/terms/page.tsx @@ -1,11 +1,11 @@ -"use client"; -import * as global_components from "@/components/global"; -import * as components from "@/components"; +'use client' +import * as global_components from '@/components/global' +import * as components from '@/components' export default function TermsPage() { - return ( - - - - ); + return ( + + + + ) } diff --git a/src/components/about/about.tsx b/src/components/about/about.tsx index 6227782dc..9dfccf6cc 100644 --- a/src/components/about/about.tsx +++ b/src/components/about/about.tsx @@ -1,178 +1,139 @@ -import * as global_components from "@/components/global"; -import smiley from "@/assets/smiley.svg"; -import hugo_png from "@/assets/people/hugo0-no-bg.png"; -import konrad_png from "@/assets/people/kkonrad-no-bg.png"; -import peanutman_cheering from "@/assets/peanutman-cheering.svg"; +import * as global_components from '@/components/global' +import smiley from '@/assets/smiley.svg' +import hugo_png from '@/assets/people/hugo0-no-bg.png' +import konrad_png from '@/assets/people/kkonrad-no-bg.png' +import peanutman_cheering from '@/assets/peanutman-cheering.svg' export function About() { - return ( -
-
-
-

-

WE MAKE TRANSFERS MAGIC

-

-
-
- - <> -
- Hugo -
- logo -
- Konrad -
- logo - -
+ return ( +
+
+
+

+

WE MAKE TRANSFERS MAGIC

+

+
+
+ + <> +
+ Hugo +
+ logo +
+ Konrad +
+ logo + +
-
-
-
-
- picture of bearded man +
+
+
+
+ picture of bearded man -

- Hugo Montenegro -

-

Tech Nut

-

- Did ML and worked with NLP. Studied CS at Harvard. Main - interests lie in decentralized systems and how incentives affect - them. Also in AI and allied with our AI overlords, and - increasing healthspan. -

-

- He's also very tall and, yes, he likes to play basketball. He's - currently doing a keto diet. [Edit: Not anymore.] -

-
+

Hugo Montenegro

+

Tech Nut

+

+ Did ML and worked with NLP. Studied CS at Harvard. Main interests lie in decentralized + systems and how incentives affect them. Also in AI and allied with our AI overlords, and + increasing healthspan. +

+

+ He's also very tall and, yes, he likes to play basketball. He's currently doing a keto + diet. [Edit: Not anymore.] +

+
-
-

- - Twitter - {" "} - |{" "} - - Lens - {" "} - |{" "} - - www - -

-
-
+
+

+ + Twitter + {' '} + |{' '} + + Lens + {' '} + |{' '} + + www + +

+
+
-
-
- handsome polish man +
+
+ handsome polish man -

- Konrad Urban -

-

Biz Nut

-

- Does biz and design. Did academic philosophy at St Andrews but - escaped to build stuff.{" "} -

+

Konrad Urban

+

Biz Nut

+

+ Does biz and design. Did academic philosophy at St Andrews but escaped to build stuff.{' '} +

-

- {" "} - Likes to climb and then ski untouched mountains. At night you - can find him your local juke joints swing & blues dancing. -

-
-
-

- - Twitter - {" "} - |{" "} - - Lens - {" "} - |{" "} - - www - -

-
-
+

+ {' '} + Likes to climb and then ski untouched mountains. At night you can find him your local + juke joints swing & blues dancing. +

+
+
+

+ + Twitter + {' '} + |{' '} + + Lens + {' '} + |{' '} + + www + +

+
+
-
-
- Very handsome and happy peanut man +
+
+ Very handsome and happy peanut man -

- ______ ______ -

-

____ Nut

-

Does ____ and ____. Did ____ but _______.

+

______ ______

+

____ Nut

+

Does ____ and ____. Did ____ but _______.

-

Likes to ______. Sometimes also __________.

-

- {" "} - Got this job after seeing the /about page and then DMing Konrad - and Hugo. -

-
+

Likes to ______. Sometimes also __________.

+

Got this job after seeing the /about page and then DMing Konrad and Hugo.

+
-
-

- - dm us - {" "} - |{" "} - - jobs - -

+
+

+ + dm us + {' '} + |{' '} + + jobs + +

+
+
+
-
-
-
- ); + ) } diff --git a/src/components/about/index.ts b/src/components/about/index.ts index d918644c2..31d6e9616 100644 --- a/src/components/about/index.ts +++ b/src/components/about/index.ts @@ -1 +1 @@ -export * from "./about"; +export * from './about' diff --git a/src/components/blog/blog.tsx b/src/components/blog/blog.tsx index 39bd92114..6bfb6cc6c 100644 --- a/src/components/blog/blog.tsx +++ b/src/components/blog/blog.tsx @@ -1,16 +1,14 @@ -import peanutman_sad from "@/assets/peanutman-sad.svg"; +import peanutman_sad from '@/assets/peanutman-sad.svg' export function Blog() { - return ( -
-
- -
-
- - {"<"} No blog posts yet! Check back later! - -
-
- ); + return ( +
+
+ +
+
+ {'<'} No blog posts yet! Check back later! +
+
+ ) } diff --git a/src/components/blog/index.ts b/src/components/blog/index.ts index 62026ee7b..44764543b 100644 --- a/src/components/blog/index.ts +++ b/src/components/blog/index.ts @@ -1 +1 @@ -export * from "./blog"; +export * from './blog' diff --git a/src/components/claim/claim.consts.ts b/src/components/claim/claim.consts.ts index 4845c0ba1..f22195d55 100644 --- a/src/components/claim/claim.consts.ts +++ b/src/components/claim/claim.consts.ts @@ -1,41 +1,41 @@ -import * as views from "./views"; -import * as interfaces from "@/interfaces"; -export type linkState = "CLAIM" | "NOT_FOUND" | "ALREADY_CLAIMED" | "LOADING"; +import * as views from './views' +import * as interfaces from '@/interfaces' +export type linkState = 'CLAIM' | 'NOT_FOUND' | 'ALREADY_CLAIMED' | 'LOADING' -export type ClaimScreens = "INITIAL" | "SUCCESS"; +export type ClaimScreens = 'INITIAL' | 'SUCCESS' export interface IClaimScreenState { - screen: ClaimScreens; - idx: number; + screen: ClaimScreens + idx: number } export interface IClaimDetails { - tokenAddress: string; - amount: number; - decimals: number; - chainId: number; + tokenAddress: string + amount: number + decimals: number + chainId: number } export interface IClaimScreenProps { - onNextScreen: () => void; - onCustomScreen: (screen: ClaimScreens) => void; - claimLink: string; - setClaimLink: (claimLink: string) => void; - claimDetails: interfaces.ILinkDetails; - txHash: string; - setTxHash: (txHash: string) => void; + onNextScreen: () => void + onCustomScreen: (screen: ClaimScreens) => void + claimLink: string + setClaimLink: (claimLink: string) => void + claimDetails: interfaces.ILinkDetails + txHash: string + setTxHash: (txHash: string) => void } export const INIT_VIEW: IClaimScreenState = { - screen: "INITIAL", - idx: 0, -}; + screen: 'INITIAL', + idx: 0, +} -export const CLAIM_SCREEN_FLOW: ClaimScreens[] = ["INITIAL", "SUCCESS"]; +export const CLAIM_SCREEN_FLOW: ClaimScreens[] = ['INITIAL', 'SUCCESS'] export const CLAIM_SCREEN_MAP: { - [key in ClaimScreens]: { comp: React.FC }; + [key in ClaimScreens]: { comp: React.FC } } = { - INITIAL: { comp: views.ClaimView }, - SUCCESS: { comp: views.ClaimSuccessView }, -}; + INITIAL: { comp: views.ClaimView }, + SUCCESS: { comp: views.ClaimSuccessView }, +} diff --git a/src/components/claim/claim.tsx b/src/components/claim/claim.tsx index eb44e9278..0bf8d7c3f 100644 --- a/src/components/claim/claim.tsx +++ b/src/components/claim/claim.tsx @@ -1,128 +1,124 @@ -import * as global_components from "@/components/global"; -import * as views from "./views"; -import * as _consts from "./claim.consts"; -import * as interfaces from "@/interfaces"; -import { createElement, useEffect, useState } from "react"; -import { ReadonlyURLSearchParams } from "next/navigation"; -import { getPublicClient, PublicClient } from "@wagmi/core"; -import { providers } from "ethers"; -import { HttpTransport } from "viem"; -import { useAccount } from "wagmi"; -const peanut = require("@squirrel-labs/peanut-sdk"); +import * as global_components from '@/components/global' +import * as views from './views' +import * as _consts from './claim.consts' +import * as interfaces from '@/interfaces' +import { createElement, useEffect, useState } from 'react' +import { ReadonlyURLSearchParams } from 'next/navigation' +import { getPublicClient, PublicClient } from '@wagmi/core' +import { providers } from 'ethers' +import { HttpTransport } from 'viem' +import { useAccount } from 'wagmi' +const peanut = require('@squirrel-labs/peanut-sdk') export function Claim({ link }: { link: ReadonlyURLSearchParams }) { - const { address, isConnected } = useAccount(); - const [linkState, setLinkState] = useState<_consts.linkState>("LOADING"); - const [claimScreen, setClaimScreen] = useState<_consts.IClaimScreenState>( - _consts.INIT_VIEW - ); - const [claimLink, setClaimLink] = useState(""); - const [claimDetails, setClaimDetails] = useState< - interfaces.ILinkDetails | undefined - >(undefined); - const [txHash, setTxHash] = useState(""); + const { address, isConnected } = useAccount() + const [linkState, setLinkState] = useState<_consts.linkState>('LOADING') + const [claimScreen, setClaimScreen] = useState<_consts.IClaimScreenState>(_consts.INIT_VIEW) + const [claimLink, setClaimLink] = useState('') + const [claimDetails, setClaimDetails] = useState(undefined) + const [txHash, setTxHash] = useState('') - const handleOnNext = () => { - const newIdx = claimScreen.idx + 1; - setClaimScreen(() => ({ - screen: _consts.CLAIM_SCREEN_FLOW[newIdx], - idx: newIdx, - })); - }; + const handleOnNext = () => { + const newIdx = claimScreen.idx + 1 + setClaimScreen(() => ({ + screen: _consts.CLAIM_SCREEN_FLOW[newIdx], + idx: newIdx, + })) + } - const handleOnCustom = (screen: _consts.ClaimScreens) => { - setClaimScreen(() => ({ - screen: screen, - idx: _consts.CLAIM_SCREEN_FLOW.indexOf(screen), - })); - }; + const handleOnCustom = (screen: _consts.ClaimScreens) => { + setClaimScreen(() => ({ + screen: screen, + idx: _consts.CLAIM_SCREEN_FLOW.indexOf(screen), + })) + } - function publicClientToProvider(publicClient: PublicClient) { - const { chain, transport } = publicClient; - const network = { - chainId: chain.id, - name: chain.name, - ensAddress: chain.contracts?.ensRegistry?.address, - }; + function publicClientToProvider(publicClient: PublicClient) { + const { chain, transport } = publicClient + const network = { + chainId: chain.id, + name: chain.name, + ensAddress: chain.contracts?.ensRegistry?.address, + } - if (transport.type === "fallback") - return new providers.FallbackProvider( - (transport.transports as ReturnType[]).map( - ({ value }) => new providers.JsonRpcProvider(value?.url, network) - ) - ); - return new providers.JsonRpcProvider(transport.url, network); - } + if (transport.type === 'fallback') + return new providers.FallbackProvider( + (transport.transports as ReturnType[]).map( + ({ value }) => new providers.JsonRpcProvider(value?.url, network) + ) + ) + return new providers.JsonRpcProvider(transport.url, network) + } - function getEthersProvider({ chainId }: { chainId?: number } = {}) { - const publicClient = getPublicClient({ chainId }); - return publicClientToProvider(publicClient); - } + function getEthersProvider({ chainId }: { chainId?: number } = {}) { + const publicClient = getPublicClient({ chainId }) + return publicClientToProvider(publicClient) + } - const checkLink = async (link: ReadonlyURLSearchParams) => { - const linkChainId = link.get("c"); - const _link = link.toString(); - setClaimLink(_link); - const provider = getEthersProvider({ chainId: Number(linkChainId) }); + const checkLink = async (link: ReadonlyURLSearchParams) => { + const linkChainId = link.get('c') + const _link = link.toString() + setClaimLink(_link) + const provider = getEthersProvider({ chainId: Number(linkChainId) }) - try { - const linkDetails: interfaces.ILinkDetails = await peanut.getLinkDetails( - provider, - "https://peanut.to/claim?" + _link - ); + try { + const linkDetails: interfaces.ILinkDetails = await peanut.getLinkDetails( + provider, + 'https://peanut.to/claim?' + _link + ) - if (Number(linkDetails.tokenAmount) <= 0) { - setLinkState("ALREADY_CLAIMED"); - } else { - setClaimDetails(linkDetails); - setLinkState("CLAIM"); - } - } catch (error) { - setLinkState("NOT_FOUND"); + if (Number(linkDetails.tokenAmount) <= 0) { + setLinkState('ALREADY_CLAIMED') + } else { + setClaimDetails(linkDetails) + setLinkState('CLAIM') + } + } catch (error) { + setLinkState('NOT_FOUND') + } } - }; - useEffect(() => { - if (link) { - checkLink(link); - } - }, [link]); + useEffect(() => { + if (link) { + checkLink(link) + } + }, [link]) - return ( - - {linkState === "LOADING" && ( -
- - Loading... -
- )} - {linkState === "NOT_FOUND" && } - {linkState === "ALREADY_CLAIMED" && } - {linkState === "CLAIM" && - createElement(_consts.CLAIM_SCREEN_MAP[claimScreen.screen].comp, { - onNextScreen: handleOnNext, - onCustomScreen: handleOnCustom, - claimLink, - setClaimLink, - claimDetails, - txHash, - setTxHash, - } as _consts.IClaimScreenProps)} -
- ); + return ( + + {linkState === 'LOADING' && ( +
+ + Loading... +
+ )} + {linkState === 'NOT_FOUND' && } + {linkState === 'ALREADY_CLAIMED' && } + {linkState === 'CLAIM' && + createElement(_consts.CLAIM_SCREEN_MAP[claimScreen.screen].comp, { + onNextScreen: handleOnNext, + onCustomScreen: handleOnCustom, + claimLink, + setClaimLink, + claimDetails, + txHash, + setTxHash, + } as _consts.IClaimScreenProps)} +
+ ) } diff --git a/src/components/claim/index.ts b/src/components/claim/index.ts index 2898b45ce..2531cb369 100644 --- a/src/components/claim/index.ts +++ b/src/components/claim/index.ts @@ -1 +1 @@ -export * from "./claim"; +export * from './claim' diff --git a/src/components/claim/views/claim.view.tsx b/src/components/claim/views/claim.view.tsx index 7f22e4fdd..4e6f4dbb6 100644 --- a/src/components/claim/views/claim.view.tsx +++ b/src/components/claim/views/claim.view.tsx @@ -1,298 +1,256 @@ -import { useWeb3Modal } from "@web3modal/react"; -import { useEffect, useMemo, useState } from "react"; -import { WalletClient, useAccount, useNetwork } from "wagmi"; -import { useAtom } from "jotai"; -import { getWalletClient, switchNetwork } from "@wagmi/core"; -const peanut = require("@squirrel-labs/peanut-sdk"); -import { providers } from "ethers"; -import { useForm } from "react-hook-form"; +import { useWeb3Modal } from '@web3modal/react' +import { useEffect, useMemo, useState } from 'react' +import { WalletClient, useAccount, useNetwork } from 'wagmi' +import { useAtom } from 'jotai' +import { getWalletClient, switchNetwork } from '@wagmi/core' +const peanut = require('@squirrel-labs/peanut-sdk') +import { providers } from 'ethers' +import { useForm } from 'react-hook-form' -import * as global_components from "@/components/global"; -import * as _consts from "../claim.consts"; -import * as utils from "@/utils"; -import * as store from "@/store"; -import * as consts from "@/consts"; -import dropdown_svg from "@/assets/dropdown.svg"; +import * as global_components from '@/components/global' +import * as _consts from '../claim.consts' +import * as utils from '@/utils' +import * as store from '@/store' +import * as consts from '@/consts' +import dropdown_svg from '@/assets/dropdown.svg' -export function ClaimView({ - onNextScreen, - claimDetails, - claimLink, - setTxHash, -}: _consts.IClaimScreenProps) { - const { isConnected, address } = useAccount(); - const { open } = useWeb3Modal(); - const [isDropdownOpen, setIsDropdownOpen] = useState(false); - const [chainDetails] = useAtom(store.defaultChainDetailsAtom); - const { chain: currentChain } = useNetwork(); - const [tokenDetails] = useAtom(store.defaultTokenDetailsAtom); +export function ClaimView({ onNextScreen, claimDetails, claimLink, setTxHash }: _consts.IClaimScreenProps) { + const { isConnected, address } = useAccount() + const { open } = useWeb3Modal() + const [isDropdownOpen, setIsDropdownOpen] = useState(false) + const [chainDetails] = useAtom(store.defaultChainDetailsAtom) + const { chain: currentChain } = useNetwork() + const [tokenDetails] = useAtom(store.defaultTokenDetailsAtom) - const [loadingStates, setLoadingStates] = - useState("idle"); - const isLoading = useMemo(() => loadingStates !== "idle", [loadingStates]); - const [errorState, setErrorState] = useState<{ - showError: boolean; - errorMessage: string; - }>({ showError: false, errorMessage: "" }); - const [signer, setSigner] = useState( - undefined - ); + const [loadingStates, setLoadingStates] = useState('idle') + const isLoading = useMemo(() => loadingStates !== 'idle', [loadingStates]) + const [errorState, setErrorState] = useState<{ + showError: boolean + errorMessage: string + }>({ showError: false, errorMessage: '' }) + const [signer, setSigner] = useState(undefined) - const manualForm = useForm<{ address: string; addressExists: boolean }>({ - mode: "onChange", - reValidateMode: "onChange", - defaultValues: { - address: "", - addressExists: false, - }, - }); + const manualForm = useForm<{ address: string; addressExists: boolean }>({ + mode: 'onChange', + reValidateMode: 'onChange', + defaultValues: { + address: '', + addressExists: false, + }, + }) - function walletClientToSigner(walletClient: WalletClient) { - const { account, chain, transport } = walletClient; - const network = { - chainId: chain.id, - name: chain.name, - ensAddress: chain.contracts?.ensRegistry?.address, - }; - const provider = new providers.Web3Provider(transport, network); - const signer = provider.getSigner(account.address); - return signer; - } - - const getWalletClientAndUpdateSigner = async ({ - chainId, - }: { - chainId: number; - }) => { - const walletClient = await getWalletClient({ chainId: Number(chainId) }); - if (walletClient) { - const signer = walletClientToSigner(walletClient); - setSigner(signer); + function walletClientToSigner(walletClient: WalletClient) { + const { account, chain, transport } = walletClient + const network = { + chainId: chain.id, + name: chain.name, + ensAddress: chain.contracts?.ensRegistry?.address, + } + const provider = new providers.Web3Provider(transport, network) + const signer = provider.getSigner(account.address) + return signer } - }; - - const claim = async () => { - try { - if (claimLink && address) { - setLoadingStates("executing transaction..."); - console.log("claiming link: https://peanut.to/claim?" + claimLink); - const claimTx = await peanut.claimLinkGasless( - "https://peanut.to/claim?" + claimLink, - address, - process.env.PEANUT_API_KEY - ); - console.log(claimTx); - setTxHash( - claimTx.tx_hash ?? claimTx.transactionHash ?? claimTx.hash ?? "" - ); - onNextScreen(); - } - // setLoadingStates("checking signer..."); - // if (!signer) { - // await getWalletClientAndUpdateSigner({ chainId: claimDetails.chainId }); - // } - // //check if the user is on the correct chain - // if (currentChain?.id.toString() !== claimDetails.chainId.toString()) { - // setLoadingStates("allow network switch..."); - // toast("Please allow the switch to the correct network in your wallet", { - // position: "bottom-right", - // }); - // await utils - // .waitForPromise( - // switchNetwork({ chainId: Number(claimDetails.chainId) }) - // ) - // .catch((error) => { - // toast("Something went wrong while switching networks", { - // position: "bottom-right", - // }); - // return; - // }); - // setLoadingStates("switching network..."); - // await new Promise((resolve) => setTimeout(resolve, 1500)); // wait a sec after switching chain before making other deeplink - // setLoadingStates("loading..."); - // } - // if (claimLink) { - // setLoadingStates("executing transaction..."); - // console.log("claiming link: https://peanut.to/claim?" + claimLink); - // const claimTx = await peanut.claimLink({ - // signer, - // link: "https://peanut.to/claim?" + claimLink, - // }); - // setTxHash(claimTx.hash ?? claimTx.transactionHash); - // onNextScreen(); - // } - } catch (error) { - setErrorState({ - showError: true, - errorMessage: "Something went wrong while claiming", - }); - console.error(error); - } finally { - setLoadingStates("idle"); + const getWalletClientAndUpdateSigner = async ({ chainId }: { chainId: number }) => { + const walletClient = await getWalletClient({ chainId: Number(chainId) }) + if (walletClient) { + const signer = walletClientToSigner(walletClient) + setSigner(signer) + } } - }; - const manualClaim = async (data: { - address: string; - addressExists: boolean; - }) => { - try { - if (!data.addressExists) { - setErrorState({ - showError: true, - errorMessage: - "Please check the box to confirm that the address exists on the chain", - }); - return; - } - setLoadingStates("executing transaction..."); - if (claimLink && data.address) { - console.log("claiming link: https://peanut.to/claim?" + claimLink); - const claimTx = await peanut.claimLinkGasless( - "https://peanut.to/claim?" + claimLink, - data.address, - process.env.PEANUT_API_KEY - ); + const claim = async () => { + try { + if (claimLink && address) { + setLoadingStates('executing transaction...') + console.log('claiming link: https://peanut.to/claim?' + claimLink) + const claimTx = await peanut.claimLinkGasless( + 'https://peanut.to/claim?' + claimLink, + address, + process.env.PEANUT_API_KEY + ) + console.log(claimTx) + setTxHash(claimTx.tx_hash ?? claimTx.transactionHash ?? claimTx.hash ?? '') + onNextScreen() + } + // setLoadingStates("checking signer..."); + // if (!signer) { + // await getWalletClientAndUpdateSigner({ chainId: claimDetails.chainId }); + // } + // //check if the user is on the correct chain + // if (currentChain?.id.toString() !== claimDetails.chainId.toString()) { + // setLoadingStates("allow network switch..."); + // toast("Please allow the switch to the correct network in your wallet", { + // position: "bottom-right", + // }); - setTxHash( - claimTx.tx_hash ?? claimTx.transactionHash ?? claimTx.hash ?? "" - ); - onNextScreen(); - } - } catch (error) { - setErrorState({ - showError: true, - errorMessage: "Something went wrong while claiming", - }); - console.error(error); - } finally { - setLoadingStates("idle"); + // await utils + // .waitForPromise( + // switchNetwork({ chainId: Number(claimDetails.chainId) }) + // ) + // .catch((error) => { + // toast("Something went wrong while switching networks", { + // position: "bottom-right", + // }); + // return; + // }); + // setLoadingStates("switching network..."); + // await new Promise((resolve) => setTimeout(resolve, 1500)); // wait a sec after switching chain before making other deeplink + // setLoadingStates("loading..."); + // } + // if (claimLink) { + // setLoadingStates("executing transaction..."); + // console.log("claiming link: https://peanut.to/claim?" + claimLink); + // const claimTx = await peanut.claimLink({ + // signer, + // link: "https://peanut.to/claim?" + claimLink, + // }); + // setTxHash(claimTx.hash ?? claimTx.transactionHash); + // onNextScreen(); + // } + } catch (error) { + setErrorState({ + showError: true, + errorMessage: 'Something went wrong while claiming', + }) + console.error(error) + } finally { + setLoadingStates('idle') + } } - }; - useEffect(() => { - if (isConnected) { - //wait for the wallet to connect - setTimeout(() => { - getWalletClientAndUpdateSigner({ chainId: claimDetails.chainId }); - }, 1000); + const manualClaim = async (data: { address: string; addressExists: boolean }) => { + try { + if (!data.addressExists) { + setErrorState({ + showError: true, + errorMessage: 'Please check the box to confirm that the address exists on the chain', + }) + return + } + setLoadingStates('executing transaction...') + if (claimLink && data.address) { + console.log('claiming link: https://peanut.to/claim?' + claimLink) + const claimTx = await peanut.claimLinkGasless( + 'https://peanut.to/claim?' + claimLink, + data.address, + process.env.PEANUT_API_KEY + ) + + setTxHash(claimTx.tx_hash ?? claimTx.transactionHash ?? claimTx.hash ?? '') + onNextScreen() + } + } catch (error) { + setErrorState({ + showError: true, + errorMessage: 'Something went wrong while claiming', + }) + console.error(error) + } finally { + setLoadingStates('idle') + } } - }, [isConnected]); - return ( - <> -

- Claim {utils.formatTokenAmount(Number(claimDetails.tokenAmount))}{" "} - {claimDetails.tokenSymbol} -

-

- {chainDetails && - chainDetails.find((chain) => chain.chainId == claimDetails.chainId) - ?.name} -

- -
{ - setIsDropdownOpen(!isDropdownOpen); - }} - > -
- manually enter address -
- -
- {isDropdownOpen && ( - - + useEffect(() => { + if (isConnected) { + //wait for the wallet to connect + setTimeout(() => { + getWalletClientAndUpdateSigner({ chainId: claimDetails.chainId }) + }, 1000) + } + }, [isConnected]) -
-
- -
- {isLoading ? ( -
- - Claiming... - -
- ) : ( - - )} -
+ return ( + <> +

+ Claim {utils.formatTokenAmount(Number(claimDetails.tokenAmount))} {claimDetails.tokenSymbol} +

+

+ {chainDetails && chainDetails.find((chain) => chain.chainId == claimDetails.chainId)?.name} +

+ +
{ + setIsDropdownOpen(!isDropdownOpen) + }} + > +
manually enter address
+
-
- - -
- - - )} - {errorState.showError && ( -
- -
- )} -

- Thoughts? Feedback? Use cases? Memes? Hit us up on{" "} - - Discord - - ! -

+ {isDropdownOpen && ( + + + +
+
+ +
+ {isLoading ? ( +
+ + Claiming... + +
+ ) : ( + + )} +
+
+
+ + +
+
+
+ )} + {errorState.showError && ( +
+ +
+ )} +

+ Thoughts? Feedback? Use cases? Memes? Hit us up on{' '} + + Discord + + ! +

- - - ); + + + ) } diff --git a/src/components/claim/views/index.ts b/src/components/claim/views/index.ts index 294e14165..755698ec5 100644 --- a/src/components/claim/views/index.ts +++ b/src/components/claim/views/index.ts @@ -1,4 +1,4 @@ -export * from "./claim.view"; -export * from "./success.view"; -export * from "./linkAlreadyClaimed.view"; -export * from "./linkNotFound.view"; +export * from './claim.view' +export * from './success.view' +export * from './linkAlreadyClaimed.view' +export * from './linkNotFound.view' diff --git a/src/components/claim/views/linkAlreadyClaimed.view.tsx b/src/components/claim/views/linkAlreadyClaimed.view.tsx index 46746acf6..deb90b18b 100644 --- a/src/components/claim/views/linkAlreadyClaimed.view.tsx +++ b/src/components/claim/views/linkAlreadyClaimed.view.tsx @@ -1,46 +1,40 @@ -import { useRouter } from "next/navigation"; -import { useEffect } from "react"; -import * as global_components from "@/components/global"; +import { useRouter } from 'next/navigation' +import { useEffect } from 'react' +import * as global_components from '@/components/global' export function ClaimLinkAlreadyClaimedView() { - const router = useRouter(); + const router = useRouter() - useEffect(() => { - router.prefetch("/"); - }, []); + useEffect(() => { + router.prefetch('/') + }, []) - return ( - <> -

- Sorry, this link has been claimed already. -

+ return ( + <> +

+ Sorry, this link has been claimed already. +

-

- Generate a payment link yourself to see how it works! -

+

Generate a payment link yourself to see how it works!

- + -

- Thoughts? Feedback? Use cases? Memes? Hit us up on{" "} - - Discord - - ! -

+

+ Thoughts? Feedback? Use cases? Memes? Hit us up on{' '} + + Discord + + ! +

- - - ); + + + ) } diff --git a/src/components/claim/views/linkNotFound.view.tsx b/src/components/claim/views/linkNotFound.view.tsx index f6aa99a6c..06b631e6f 100644 --- a/src/components/claim/views/linkNotFound.view.tsx +++ b/src/components/claim/views/linkNotFound.view.tsx @@ -1,46 +1,38 @@ -import { useRouter } from "next/navigation"; -import { useEffect } from "react"; -import * as global_components from "@/components/global"; +import { useRouter } from 'next/navigation' +import { useEffect } from 'react' +import * as global_components from '@/components/global' export function ClaimLinkNotFoundView() { - const router = useRouter(); + const router = useRouter() - useEffect(() => { - router.prefetch("/"); - }, []); - return ( - <> -

- Hey there! Sorrrry. -

+ useEffect(() => { + router.prefetch('/') + }, []) + return ( + <> +

Hey there! Sorrrry.

-

- Deposit not found. Are you sure your claiming link is correct? -

+

Deposit not found. Are you sure your claiming link is correct?

- + -

- Thoughts? Feedback? Use cases? Memes? Hit us up on{" "} - - Discord - - ! -

+

+ Thoughts? Feedback? Use cases? Memes? Hit us up on{' '} + + Discord + + ! +

- - - ); + + + ) } diff --git a/src/components/claim/views/success.view.tsx b/src/components/claim/views/success.view.tsx index 640307f2f..7bccce045 100644 --- a/src/components/claim/views/success.view.tsx +++ b/src/components/claim/views/success.view.tsx @@ -1,106 +1,86 @@ -import { useEffect, useMemo, useState } from "react"; -import { useAtom } from "jotai"; +import { useEffect, useMemo, useState } from 'react' +import { useAtom } from 'jotai' -import * as _consts from "../claim.consts"; -import * as store from "@/store/"; -import * as global_components from "@/components/global"; +import * as _consts from '../claim.consts' +import * as store from '@/store/' +import * as global_components from '@/components/global' -import dropdown_svg from "@/assets/dropdown.svg"; -import { useRouter } from "next/navigation"; +import dropdown_svg from '@/assets/dropdown.svg' +import { useRouter } from 'next/navigation' -export function ClaimSuccessView({ - txHash, - claimDetails, -}: _consts.IClaimScreenProps) { - const router = useRouter(); +export function ClaimSuccessView({ txHash, claimDetails }: _consts.IClaimScreenProps) { + const router = useRouter() - const [isDropdownOpen, setIsDropdownOpen] = useState(false); - const [chainDetails] = useAtom(store.defaultChainDetailsAtom); + const [isDropdownOpen, setIsDropdownOpen] = useState(false) + const [chainDetails] = useAtom(store.defaultChainDetailsAtom) - const explorerUrlWithTx = useMemo( - () => - chainDetails.find((detail) => detail.chainId === claimDetails.chainId) - ?.explorers[0].url + - "/tx/" + - txHash, - [txHash, chainDetails] - ); + const explorerUrlWithTx = useMemo( + () => + chainDetails.find((detail) => detail.chainId === claimDetails.chainId)?.explorers[0].url + '/tx/' + txHash, + [txHash, chainDetails] + ) - useEffect(() => { - router.prefetch("/"); - }, []); + useEffect(() => { + router.prefetch('/') + }, []) - return ( - <> -

- Congratulations! -

-

- You have successfully claimed your funds. -

-
{ - setIsDropdownOpen(!isDropdownOpen); - }} - > -
- Check Transaction{" "} -
- -
- {isDropdownOpen && ( -
- - {txHash} - -

- - Click the confirmation above and check Internal Txs. It - might be slow. - -

-

- - If you don't see the funds in your wallet, make sure you are on - the right chain. - -

-
- )} - -

- Thoughts? Feedback? Use cases? Memes? Hit us up on{" "} - - Discord - - ! -

+ return ( + <> +

Congratulations!

+

You have successfully claimed your funds.

+
{ + setIsDropdownOpen(!isDropdownOpen) + }} + > +
Check Transaction
+ +
+ {isDropdownOpen && ( +
+ + {txHash} + +

+ + Click the confirmation above and check Internal Txs. It might be slow. + +

+

+ If you don't see the funds in your wallet, make sure you are on the right chain. +

+
+ )} + +

+ Thoughts? Feedback? Use cases? Memes? Hit us up on{' '} + + Discord + + ! +

- - - ); + + + ) } diff --git a/src/components/dashboard/dashboard.tsx b/src/components/dashboard/dashboard.tsx index ad428e468..df0c5e713 100644 --- a/src/components/dashboard/dashboard.tsx +++ b/src/components/dashboard/dashboard.tsx @@ -1,99 +1,93 @@ -import { useEffect, useState } from "react"; -import { useAccount } from "wagmi"; +import { useEffect, useState } from 'react' +import { useAccount } from 'wagmi' -import * as global_components from "@/components/global"; -import * as utils from "@/utils"; -import * as interfaces from "@/interfaces"; -import * as store from "@/store"; -import { useAtom } from "jotai"; -import { useRouter } from "next/navigation"; +import * as global_components from '@/components/global' +import * as utils from '@/utils' +import * as interfaces from '@/interfaces' +import * as store from '@/store' +import { useAtom } from 'jotai' +import { useRouter } from 'next/navigation' export function Dashboard() { - const [chainDetails] = useAtom(store.defaultChainDetailsAtom); - const { address, isConnected } = useAccount(); - const router = useRouter(); - const [localStorageData, setLocalStorageData] = useState< - interfaces.ILocalStorageItem[] - >([]); + const [chainDetails] = useAtom(store.defaultChainDetailsAtom) + const { address, isConnected } = useAccount() + const router = useRouter() + const [localStorageData, setLocalStorageData] = useState([]) - useEffect(() => { - if (address) { - const data = utils.getAllLinksFromLocalStorage({ - address: address.toString(), - }); - data && setLocalStorageData(data); - } - router.prefetch("/"); - }, []); - return ( - -
-
-
- A list of all the links you have created. -
-
- -
-
- {isConnected ? ( - - - - - - - - - {localStorageData.map((item) => ( - - + useEffect(() => { + if (address) { + const data = utils.getAllLinksFromLocalStorage({ + address: address.toString(), + }) + data && setLocalStorageData(data) + } + router.prefetch('/') + }, []) + return ( + +
+
+
A list of all the links you have created.
+
+ +
+
+ {isConnected ? ( +
ChainLink
- { - chainDetails.find( - (chain) => - chain.chainId.toString() === - item.link.match(/c=(\d+)/)?.[1] - )?.name - } -
+ + + + + + + + {localStorageData.map((item) => ( + + - - - ))} - -
ChainLink
+ { + chainDetails.find( + (chain) => chain.chainId.toString() === item.link.match(/c=(\d+)/)?.[1] + )?.name + } + { - navigator.clipboard.writeText(item.link); - }} - > - {item.link} -
- ) : ( - "Connect your wallet to view your deposits" - )} -
-
- ); + { + navigator.clipboard.writeText(item.link) + }} + > + {item.link} + + + ))} + + + ) : ( + 'Connect your wallet to view your deposits' + )} +
+
+ ) } diff --git a/src/components/dashboard/index.ts b/src/components/dashboard/index.ts index e578baa93..142cf96c3 100644 --- a/src/components/dashboard/index.ts +++ b/src/components/dashboard/index.ts @@ -1 +1 @@ -export * from "./dashboard"; +export * from './dashboard' diff --git a/src/components/global/cardWrapper/cardWrapper.tsx b/src/components/global/cardWrapper/cardWrapper.tsx index 2c947ee4c..f1309ddc0 100644 --- a/src/components/global/cardWrapper/cardWrapper.tsx +++ b/src/components/global/cardWrapper/cardWrapper.tsx @@ -1,19 +1,13 @@ -export function CardWrapper({ - children, - mb = " mb-48", -}: { - children: React.ReactNode; - mb?: string; -}) { - return ( -
- {" "} - {children} -
- ); +export function CardWrapper({ children, mb = ' mb-48' }: { children: React.ReactNode; mb?: string }) { + return ( +
+ {' '} + {children} +
+ ) } diff --git a/src/components/global/cardWrapper/index.ts b/src/components/global/cardWrapper/index.ts index 031a7d97e..453a1dd77 100644 --- a/src/components/global/cardWrapper/index.ts +++ b/src/components/global/cardWrapper/index.ts @@ -1 +1 @@ -export * from "./cardWrapper"; +export * from './cardWrapper' diff --git a/src/components/global/footer/footer.consts.ts b/src/components/global/footer/footer.consts.ts index 4fd3a065b..8c8b917ee 100644 --- a/src/components/global/footer/footer.consts.ts +++ b/src/components/global/footer/footer.consts.ts @@ -1,42 +1,42 @@ -import twitter_logo from "@/assets/twitter-logo.svg"; -import discord_logo from "@/assets/discord-logo.svg"; +import twitter_logo from '@/assets/twitter-logo.svg' +import discord_logo from '@/assets/discord-logo.svg' export const SOCIALS = [ - { - name: "twitter", - url: "https://twitter.com/peanutprotocol", - logoSrc: twitter_logo.src, - }, - { - name: "discord", - url: "https://discord.gg/BX9Ak7AW28", - logoSrc: discord_logo.src, - }, -]; + { + name: 'twitter', + url: 'https://twitter.com/peanutprotocol', + logoSrc: twitter_logo.src, + }, + { + name: 'discord', + url: 'https://discord.gg/BX9Ak7AW28', + logoSrc: discord_logo.src, + }, +] export const LINKS = [ - { - name: "Docs", - url: "https://peanutprotocol.notion.site/Peanut-Protocol-5776ec3a97de4e5d972ae3f6ba7f4f04", - }, - { - name: "About", - url: "/about", - }, - { - name: "Blog", - url: "/blog", - }, - { - name: "Privacy", - url: "/privacy", - }, - { - name: "Terms", - url: "/terms", - }, - { - name: "Jobs", - url: "/jobs", - }, -]; + { + name: 'Docs', + url: 'https://peanutprotocol.notion.site/Peanut-Protocol-5776ec3a97de4e5d972ae3f6ba7f4f04', + }, + { + name: 'About', + url: '/about', + }, + { + name: 'Blog', + url: '/blog', + }, + { + name: 'Privacy', + url: '/privacy', + }, + { + name: 'Terms', + url: '/terms', + }, + { + name: 'Jobs', + url: '/jobs', + }, +] diff --git a/src/components/global/footer/footer.tsx b/src/components/global/footer/footer.tsx index d4087f9d0..ce330c4d1 100644 --- a/src/components/global/footer/footer.tsx +++ b/src/components/global/footer/footer.tsx @@ -1,14 +1,14 @@ -import Link from "next/link"; -import smiley from "@/assets/smiley.svg"; +import Link from 'next/link' +import smiley from '@/assets/smiley.svg' -import * as global_components from "@/components/global"; +import * as global_components from '@/components/global' // You can find all social and other links in this const file. -import * as _consts from "./footer.consts"; +import * as _consts from './footer.consts' export function Footer({ showMarquee = false }: { showMarquee?: boolean }) { - return ( -
- {/* {showMarquee && ( + return ( +
+ {/* {showMarquee && (
smiles @@ -17,32 +17,32 @@ export function Footer({ showMarquee = false }: { showMarquee?: boolean }) { )} */} -
-
-
- {_consts.SOCIALS.map((social) => { - return ( - - twitter - - ); - })} -
-
- {_consts.LINKS.map((link) => { - return ( - - {link.name} - - ); - })} -
+
+
+
+ {_consts.SOCIALS.map((social) => { + return ( + + twitter + + ) + })} +
+
+ {_consts.LINKS.map((link) => { + return ( + + {link.name} + + ) + })} +
+
+
-
-
- ); + ) } diff --git a/src/components/global/footer/index.ts b/src/components/global/footer/index.ts index 0df22f521..0b481ccaf 100644 --- a/src/components/global/footer/index.ts +++ b/src/components/global/footer/index.ts @@ -1 +1 @@ -export * from "./footer"; +export * from './footer' diff --git a/src/components/global/header/header.tsx b/src/components/global/header/header.tsx index d3bdbb5b4..9ff43f840 100644 --- a/src/components/global/header/header.tsx +++ b/src/components/global/header/header.tsx @@ -1,83 +1,83 @@ -"use client"; -import Link from "next/link"; -import { useWeb3Modal } from "@web3modal/react"; -import { useAccount } from "wagmi"; +'use client' +import Link from 'next/link' +import { useWeb3Modal } from '@web3modal/react' +import { useAccount } from 'wagmi' -import * as global_components from "@/components/global"; -import * as utils from "@/utils"; +import * as global_components from '@/components/global' +import * as utils from '@/utils' -import peanut_logo from "@/assets/peanutman-logo.svg"; -import smiley from "@/assets/smiley.svg"; +import peanut_logo from '@/assets/peanutman-logo.svg' +import smiley from '@/assets/smiley.svg' export function Header({ showMarquee = true }: { showMarquee?: boolean }) { - const { address, isConnected } = useAccount(); + const { address, isConnected } = useAccount() - const { open } = useWeb3Modal(); + const { open } = useWeb3Modal() - return ( -
- - {showMarquee && ( - { - window.open( - "https://peanutprotocol.notion.site/Send-Tokens-via-Link-Peanut-Link-SDK-1-0-9a89ea726b754a1c9f7e012125a01a85" - ); - }} - > - <> -
- new sdk -
- logo -
- click here -
- logo - -
- )} -
- ); + ) } diff --git a/src/components/global/header/index.ts b/src/components/global/header/index.ts index 49ac70fe2..c73f6da40 100644 --- a/src/components/global/header/index.ts +++ b/src/components/global/header/index.ts @@ -1 +1 @@ -export * from "./header"; +export * from './header' diff --git a/src/components/global/index.ts b/src/components/global/index.ts index dd50365c1..d7505adbf 100644 --- a/src/components/global/index.ts +++ b/src/components/global/index.ts @@ -1,6 +1,6 @@ -export * from "./footer"; -export * from "./header"; -export * from "./pageWrapper"; -export * from "./marqueeWrapper"; -export * from "./cardWrapper"; -export * from "./peanutMan"; +export * from './footer' +export * from './header' +export * from './pageWrapper' +export * from './marqueeWrapper' +export * from './cardWrapper' +export * from './peanutMan' diff --git a/src/components/global/marqueeWrapper/index.ts b/src/components/global/marqueeWrapper/index.ts index 7195d5181..977635d1e 100644 --- a/src/components/global/marqueeWrapper/index.ts +++ b/src/components/global/marqueeWrapper/index.ts @@ -1 +1 @@ -export * from "./marqueeWrapper"; +export * from './marqueeWrapper' diff --git a/src/components/global/marqueeWrapper/marqueeWrapper.tsx b/src/components/global/marqueeWrapper/marqueeWrapper.tsx index f56ea9bcf..aa6f1c8ad 100644 --- a/src/components/global/marqueeWrapper/marqueeWrapper.tsx +++ b/src/components/global/marqueeWrapper/marqueeWrapper.tsx @@ -1,28 +1,26 @@ -import Marquee from "react-fast-marquee"; +import Marquee from 'react-fast-marquee' export function MarqueeWrapper({ - children, - backgroundColor, - onClick, + children, + backgroundColor, + onClick, }: { - children: React.ReactNode; - backgroundColor: string; - onClick?: () => void; + children: React.ReactNode + backgroundColor: string + onClick?: () => void }) { - return ( -
- -
{children}
-
-
- ); + return ( +
+ +
{children}
+
+
+ ) } diff --git a/src/components/global/pageWrapper/index.ts b/src/components/global/pageWrapper/index.ts index 6e9fc3fa7..995fa7ac2 100644 --- a/src/components/global/pageWrapper/index.ts +++ b/src/components/global/pageWrapper/index.ts @@ -1 +1 @@ -export * from "./pageWrapper"; +export * from './pageWrapper' diff --git a/src/components/global/pageWrapper/pageWrapper.tsx b/src/components/global/pageWrapper/pageWrapper.tsx index 373ab6e97..9457b48e7 100644 --- a/src/components/global/pageWrapper/pageWrapper.tsx +++ b/src/components/global/pageWrapper/pageWrapper.tsx @@ -1,21 +1,19 @@ -import * as global_components from "@/components/global"; +import * as global_components from '@/components/global' export function PageWrapper({ - children, - bgColor = "bg-teal", - showMarquee = true, + children, + bgColor = 'bg-teal', + showMarquee = true, }: { - children: React.ReactNode; - bgColor?: string; - showMarquee?: boolean; + children: React.ReactNode + bgColor?: string + showMarquee?: boolean }) { - return ( -
- -
- {children} -
- -
- ); + return ( +
+ +
{children}
+ +
+ ) } diff --git a/src/components/global/peanutMan/index.ts b/src/components/global/peanutMan/index.ts index 268116d9c..707327cd0 100644 --- a/src/components/global/peanutMan/index.ts +++ b/src/components/global/peanutMan/index.ts @@ -1 +1 @@ -export * from "./peanutMan"; +export * from './peanutMan' diff --git a/src/components/global/peanutMan/peanutMan.tsx b/src/components/global/peanutMan/peanutMan.tsx index b02a17bd3..909903fe9 100644 --- a/src/components/global/peanutMan/peanutMan.tsx +++ b/src/components/global/peanutMan/peanutMan.tsx @@ -1,41 +1,41 @@ -import peanutman_sad from "@/assets/peanutman-sad.svg"; -import peanutman_presenting from "@/assets/peanutman-presenting.svg"; -import peanutman_cheering from "@/assets/peanutman-cheering.svg"; -import { useEffect, useState } from "react"; +import peanutman_sad from '@/assets/peanutman-sad.svg' +import peanutman_presenting from '@/assets/peanutman-presenting.svg' +import peanutman_cheering from '@/assets/peanutman-cheering.svg' +import { useEffect, useState } from 'react' export function PeanutMan({ type }: { type: string }) { - const [peanutmanSvg, setSvg] = useState(peanutman_presenting); + const [peanutmanSvg, setSvg] = useState(peanutman_presenting) - useEffect(() => { - switch (type) { - case "cheering": { - setSvg(peanutman_cheering); - break; - } - case "sad": { - setSvg(peanutman_sad); - break; - } - case "presenting": { - setSvg(peanutman_presenting); - break; - } - default: { - setSvg(peanutman_cheering); - break; - } - } - }, [type]); + useEffect(() => { + switch (type) { + case 'cheering': { + setSvg(peanutman_cheering) + break + } + case 'sad': { + setSvg(peanutman_sad) + break + } + case 'presenting': { + setSvg(peanutman_presenting) + break + } + default: { + setSvg(peanutman_cheering) + break + } + } + }, [type]) - return ( - - ); + return ( + + ) } { - /* + /* -
- -
-
-
- - {"<"} Hey there! Want to work at Peanut? - -
+ return ( +
+
+ +
+
+
+ {'<'} Hey there! Want to work at Peanut? +
-
- Check out our open{" "} - - Job Positions! - +
+ Check out our open{' '} + + Job Positions! + +
+
-
-
- ); + ) } diff --git a/src/components/privacy/index.ts b/src/components/privacy/index.ts index 5dab970d4..ef7b5060c 100644 --- a/src/components/privacy/index.ts +++ b/src/components/privacy/index.ts @@ -1 +1 @@ -export * from "./privacy"; +export * from './privacy' diff --git a/src/components/privacy/privacy.tsx b/src/components/privacy/privacy.tsx index 3721ef5c6..41d282884 100644 --- a/src/components/privacy/privacy.tsx +++ b/src/components/privacy/privacy.tsx @@ -1,43 +1,39 @@ -import peanutman_presenting from "@/assets/peanutman-presenting.svg"; +import peanutman_presenting from '@/assets/peanutman-presenting.svg' export function Privacy() { - return ( -
-
- -
-
-
- - {"<"} Hey there! This is how we treat ur data. - -
-
- Privacy Policy -
+ return ( +
+
+ +
+
+
+ {'<'} Hey there! This is how we treat ur data. +
+
Privacy Policy
-
- We are no creeps! Full terms can be found{" "} - - here - -
+
+ We are no creeps! Full terms can be found{' '} + + here + +
-
- {" "} - If you have any questions, you can always get in touch{" "} - - with us!{" "} - +
+ {' '} + If you have any questions, you can always get in touch{' '} + + with us!{' '} + +
+
-
-
- ); + ) } diff --git a/src/components/send/index.ts b/src/components/send/index.ts index 592eec5c1..82ec8734e 100644 --- a/src/components/send/index.ts +++ b/src/components/send/index.ts @@ -1 +1 @@ -export * from "./send"; +export * from './send' diff --git a/src/components/send/send.consts.ts b/src/components/send/send.consts.ts index 685530f97..cbdd268f1 100644 --- a/src/components/send/send.consts.ts +++ b/src/components/send/send.consts.ts @@ -1,35 +1,35 @@ -import React from "react"; -import * as views from "./views"; +import React from 'react' +import * as views from './views' // I always like to use consts files like these, makes it very readable and easy to change -export type SendScreens = "INITIAL" | "SUCCESS"; +export type SendScreens = 'INITIAL' | 'SUCCESS' export interface ISendScreenState { - screen: SendScreens; - idx: number; + screen: SendScreens + idx: number } export interface ISendScreenProps { - onNextScreen: () => void; - onCustomScreen: (screen: SendScreens) => void; - claimLink: string; - setClaimLink: (claimLink: string) => void; - txReceipt: any; - setTxReceipt: (txReceipt: string) => void; - chainId: number; - setChainId: (chainId: number) => void; + onNextScreen: () => void + onCustomScreen: (screen: SendScreens) => void + claimLink: string + setClaimLink: (claimLink: string) => void + txReceipt: any + setTxReceipt: (txReceipt: string) => void + chainId: number + setChainId: (chainId: number) => void } export const INIT_VIEW: ISendScreenState = { - screen: "INITIAL", - idx: 0, -}; + screen: 'INITIAL', + idx: 0, +} -export const SEND_SCREEN_FLOW: SendScreens[] = ["INITIAL", "SUCCESS"]; +export const SEND_SCREEN_FLOW: SendScreens[] = ['INITIAL', 'SUCCESS'] export const SEND_SCREEN_MAP: { - [key in SendScreens]: { comp: React.FC }; + [key in SendScreens]: { comp: React.FC } } = { - INITIAL: { comp: views.SendInitialView }, - SUCCESS: { comp: views.SendSuccessView }, -}; + INITIAL: { comp: views.SendInitialView }, + SUCCESS: { comp: views.SendSuccessView }, +} diff --git a/src/components/send/send.tsx b/src/components/send/send.tsx index 6566b8dd9..7fe60b242 100644 --- a/src/components/send/send.tsx +++ b/src/components/send/send.tsx @@ -1,81 +1,79 @@ -import { createElement, useState } from "react"; -import * as global_components from "@/components/global"; -import * as _consts from "./send.consts"; -import code_snippet from "@/assets/code_snippet.png"; +import { createElement, useState } from 'react' +import * as global_components from '@/components/global' +import * as _consts from './send.consts' +import code_snippet from '@/assets/code_snippet.png' export function Send() { - const [sendScreen, setSendScreen] = useState<_consts.ISendScreenState>( - _consts.INIT_VIEW - ); - const [claimLink, setClaimLink] = useState(""); - const [txReceipt, setTxReceipt] = useState(""); - const [chainId, setChainId] = useState(0); + const [sendScreen, setSendScreen] = useState<_consts.ISendScreenState>(_consts.INIT_VIEW) + const [claimLink, setClaimLink] = useState('') + const [txReceipt, setTxReceipt] = useState('') + const [chainId, setChainId] = useState(0) - const handleOnNext = () => { - const newIdx = sendScreen.idx + 1; - setSendScreen(() => ({ - screen: _consts.SEND_SCREEN_FLOW[newIdx], - idx: newIdx, - })); - }; + const handleOnNext = () => { + const newIdx = sendScreen.idx + 1 + setSendScreen(() => ({ + screen: _consts.SEND_SCREEN_FLOW[newIdx], + idx: newIdx, + })) + } - const handleOnCustom = (screen: _consts.SendScreens) => { - setSendScreen(() => ({ - screen: screen, - idx: _consts.SEND_SCREEN_FLOW.indexOf(screen), - })); - }; + const handleOnCustom = (screen: _consts.SendScreens) => { + setSendScreen(() => ({ + screen: screen, + idx: _consts.SEND_SCREEN_FLOW.indexOf(screen), + })) + } - return ( - <> - - {createElement(_consts.SEND_SCREEN_MAP[sendScreen.screen].comp, { - onNextScreen: handleOnNext, - onCustomScreen: handleOnCustom, - claimLink, - setClaimLink, - txReceipt, - setTxReceipt, - chainId, - setChainId, - } as _consts.ISendScreenProps)} - - {sendScreen == _consts.INIT_VIEW && ( - -
-

- Integrate Peanut Protocol -

+ return ( + <> + + {createElement(_consts.SEND_SCREEN_MAP[sendScreen.screen].comp, { + onNextScreen: handleOnNext, + onCustomScreen: handleOnCustom, + claimLink, + setClaimLink, + txReceipt, + setTxReceipt, + chainId, + setChainId, + } as _consts.ISendScreenProps)} + + {sendScreen == _consts.INIT_VIEW && ( + +
+

+ Integrate Peanut Protocol +

-

- transfer magic✨ in your own app -

+

+ transfer magic✨ in your own app +

-
- Want the peanut magic in your own dApp? Just install our{" "} - - npm - {" "} - library, and with 2 lines of code, you can create token links to - send any type of tokens or NFTs! -
- +
+ Want the peanut magic in your own dApp? Just install our{' '} + + npm + {' '} + library, and with 2 lines of code, you can create token links to send any type of tokens or + NFTs! +
+ -
- Read more{" "} - - here - -
-
-
- )} - - ); +
+ Read more{' '} + + here + +
+
+
+ )} + + ) } diff --git a/src/components/send/views/index.ts b/src/components/send/views/index.ts index 0610c8d8c..fc51cc3fd 100644 --- a/src/components/send/views/index.ts +++ b/src/components/send/views/index.ts @@ -1,2 +1,2 @@ -export * from "./initial.view"; -export * from "./succes.view"; +export * from './initial.view' +export * from './succes.view' diff --git a/src/components/send/views/initial.view.tsx b/src/components/send/views/initial.view.tsx index b121119fb..4cd9b806f 100644 --- a/src/components/send/views/initial.view.tsx +++ b/src/components/send/views/initial.view.tsx @@ -1,612 +1,551 @@ -import Link from "next/link"; -import { useEffect, useState, useCallback, useMemo } from "react"; -import { useWeb3Modal } from "@web3modal/react"; -import { useAtom } from "jotai"; -import { useAccount, useNetwork, WalletClient } from "wagmi"; -import { switchNetwork, getWalletClient } from "@wagmi/core"; -import { providers } from "ethers"; -import { useForm } from "react-hook-form"; -import Select from "react-select"; - -const peanut = require("@squirrel-labs/peanut-sdk"); - -import * as store from "@/store"; -import * as consts from "@/consts"; -import * as _consts from "../send.consts"; -import * as utils from "@/utils"; -import * as hooks from "@/hooks"; -import * as global_components from "@/components/global"; +import Link from 'next/link' +import { useEffect, useState, useCallback, useMemo } from 'react' +import { useWeb3Modal } from '@web3modal/react' +import { useAtom } from 'jotai' +import { useAccount, useNetwork, WalletClient } from 'wagmi' +import { switchNetwork, getWalletClient } from '@wagmi/core' +import { providers } from 'ethers' +import { useForm } from 'react-hook-form' +import Select from 'react-select' + +const peanut = require('@squirrel-labs/peanut-sdk') + +import * as store from '@/store' +import * as consts from '@/consts' +import * as _consts from '../send.consts' +import * as utils from '@/utils' +import * as hooks from '@/hooks' +import * as global_components from '@/components/global' interface ISendFormData { - chainId: number; - token: string; - amount: number; + chainId: number + token: string + amount: number } -export function SendInitialView({ - onNextScreen, - setClaimLink, - setTxReceipt, - setChainId, -}: _consts.ISendScreenProps) { - const { open } = useWeb3Modal(); - const { isConnected, address } = useAccount(); - const { chain: currentChain } = useNetwork(); - const [signer, setSigner] = useState( - undefined - ); - const [tokenList, setTokenList] = useState([]); - const [formHasBeenTouched, setFormHasBeenTouched] = useState(false); - const [userBalances] = useAtom(store.userBalancesAtom); - const [chainDetails] = useAtom(store.defaultChainDetailsAtom); - const [supportedChainsSocketTech] = useAtom( - store.supportedChainsSocketTechAtom - ); - const [tokenDetails] = useAtom(store.defaultTokenDetailsAtom); - const [prevChainId, setPrevChainId] = useState(undefined); - const [errorState, setErrorState] = useState<{ - showError: boolean; - errorMessage: string; - }>({ showError: false, errorMessage: "" }); - const [loadingStates, setLoadingStates] = - useState("idle"); - const isLoading = useMemo(() => loadingStates !== "idle", [loadingStates]); - - const [enableConfirmation, setEnableConfirmation] = useState(false); - - hooks.useConfirmRefresh(enableConfirmation); - - const sendForm = useForm({ - mode: "onChange", - defaultValues: { - chainId: 1, - amount: 0, - token: "", - }, - }); - const formwatch = sendForm.watch(); - interface ITokenListItem { - symbol: string; - amount: number; - chainId: number; - address: string; - decimals: number; - logo: string; - } - - function walletClientToSigner(walletClient: WalletClient) { - const { account, chain, transport } = walletClient; - const network = { - chainId: chain.id, - name: chain.name, - ensAddress: chain.contracts?.ensRegistry?.address, - }; - const provider = new providers.Web3Provider(transport, network); - const signer = provider.getSigner(account.address); - return signer; - } - - const getWalletClientAndUpdateSigner = async ({ - chainId, - }: { - chainId: number; - }) => { - const walletClient = await getWalletClient({ chainId: Number(chainId) }); - if (walletClient) { - const signer = walletClientToSigner(walletClient); - setSigner(signer); - } - }; - - const checkForm = (sendFormData: ISendFormData) => { - //check that the token and chainid are defined - if (sendFormData.chainId == null || sendFormData.token == "") { - setErrorState({ - showError: true, - errorMessage: "Please select a chain and token", - }); - return { succes: "false" }; +export function SendInitialView({ onNextScreen, setClaimLink, setTxReceipt, setChainId }: _consts.ISendScreenProps) { + const { open } = useWeb3Modal() + const { isConnected, address } = useAccount() + const { chain: currentChain } = useNetwork() + const [signer, setSigner] = useState(undefined) + const [tokenList, setTokenList] = useState([]) + const [formHasBeenTouched, setFormHasBeenTouched] = useState(false) + const [userBalances] = useAtom(store.userBalancesAtom) + const [chainDetails] = useAtom(store.defaultChainDetailsAtom) + const [supportedChainsSocketTech] = useAtom(store.supportedChainsSocketTechAtom) + const [tokenDetails] = useAtom(store.defaultTokenDetailsAtom) + const [prevChainId, setPrevChainId] = useState(undefined) + const [errorState, setErrorState] = useState<{ + showError: boolean + errorMessage: string + }>({ showError: false, errorMessage: '' }) + const [loadingStates, setLoadingStates] = useState('idle') + const isLoading = useMemo(() => loadingStates !== 'idle', [loadingStates]) + + const [enableConfirmation, setEnableConfirmation] = useState(false) + + hooks.useConfirmRefresh(enableConfirmation) + + const sendForm = useForm({ + mode: 'onChange', + defaultValues: { + chainId: 1, + amount: 0, + token: '', + }, + }) + const formwatch = sendForm.watch() + interface ITokenListItem { + symbol: string + amount: number + chainId: number + address: string + decimals: number + logo: string } - //check if the amount is less than or equal to zero - if (sendFormData.amount <= 0) { - setErrorState({ - showError: true, - errorMessage: "Please put an amount that is greater than zero", - }); - return { succes: "false" }; + function walletClientToSigner(walletClient: WalletClient) { + const { account, chain, transport } = walletClient + const network = { + chainId: chain.id, + name: chain.name, + ensAddress: chain.contracts?.ensRegistry?.address, + } + const provider = new providers.Web3Provider(transport, network) + const signer = provider.getSigner(account.address) + return signer } - //check if the token is in the userBalances - if ( - userBalances.some( - (balance) => - balance.symbol == sendFormData.token && - balance.chainId == sendFormData.chainId - ) - ) { - //check that the user has enough funds - const balance = userBalances.find( - (balance) => balance.symbol === sendFormData.token - )?.amount; - if (balance && sendFormData.amount > balance) { - setErrorState({ - showError: true, - errorMessage: "You don't have enough funds", - }); - return { succes: "false" }; - } - - if (!signer) { - getWalletClientAndUpdateSigner({ chainId: sendFormData.chainId }); - setErrorState({ - showError: true, - errorMessage: "Signer undefined, please refresh", - }); - return { succes: "false" }; - } + const getWalletClientAndUpdateSigner = async ({ chainId }: { chainId: number }) => { + const walletClient = await getWalletClient({ chainId: Number(chainId) }) + if (walletClient) { + const signer = walletClientToSigner(walletClient) + setSigner(signer) + } } - return { succes: "true" }; - }; - - const getTokenDetails = useCallback( - (sendFormData: ISendFormData) => { - let tokenAddress: string = ""; - let tokenDecimals: number = 18; - if ( - userBalances.some( - (balance) => - balance.symbol == sendFormData.token && - balance.chainId == sendFormData.chainId - ) - ) { - tokenAddress = - userBalances.find( - (balance) => - balance.chainId == sendFormData.chainId && - balance.symbol == sendFormData.token - )?.address ?? ""; - tokenDecimals = - userBalances.find( - (balance) => - balance.chainId == sendFormData.chainId && - balance.symbol == sendFormData.token - )?.decimals ?? 18; - } else { - tokenAddress = - tokenDetails - .find( - (detail) => - detail.chainId.toString() == sendFormData.chainId.toString() - ) - ?.tokens.find((token) => token.symbol == sendFormData.token) - ?.address ?? ""; - - tokenDecimals = - tokenDetails - .find( - (detail) => - detail.chainId.toString() == sendFormData.chainId.toString() - ) - ?.tokens.find((token) => token.symbol == sendFormData.token) - ?.decimals ?? 18; - } - - const tokenType = - chainDetails.find((detail) => detail.chainId == sendFormData.chainId) - ?.nativeCurrency.symbol == sendFormData.token - ? 0 - : 1; - - return { tokenAddress, tokenDecimals, tokenType }; - }, - [userBalances, tokenDetails, chainDetails] - ); - - const createLink = useCallback( - async (sendFormData: ISendFormData) => { - setErrorState({ showError: false, errorMessage: "" }); - if (isLoading) return; - try { - setLoadingStates("checking inputs..."); - - if (checkForm(sendFormData).succes === "false") { - return; + + const checkForm = (sendFormData: ISendFormData) => { + //check that the token and chainid are defined + if (sendFormData.chainId == null || sendFormData.token == '') { + setErrorState({ + showError: true, + errorMessage: 'Please select a chain and token', + }) + return { succes: 'false' } } - setEnableConfirmation(true); - - const { tokenAddress, tokenDecimals, tokenType } = - getTokenDetails(sendFormData); - - console.log( - "sending " + - sendFormData.amount + - " " + - sendFormData.token + - " on chain with id " + - sendFormData.chainId + - " with token address: " + - tokenAddress + - " with tokenType: " + - tokenType + - " with tokenDecimals: " + - tokenDecimals - ); - - setLoadingStates("allow network switch..."); - //check if the user is on the correct chain - if (currentChain?.id.toString() !== sendFormData.chainId.toString()) { - await utils - .waitForPromise( - switchNetwork({ chainId: Number(sendFormData.chainId) }) - ) - .catch((error) => { - setErrorState({ + + //check if the amount is less than or equal to zero + if (sendFormData.amount <= 0) { + setErrorState({ showError: true, - errorMessage: "Something went wrong while switching networks", - }); - return; - }); - setLoadingStates("switching network..."); - await new Promise((resolve) => setTimeout(resolve, 4000)); // wait a sec after switching chain before making other deeplink - setLoadingStates("loading..."); + errorMessage: 'Please put an amount that is greater than zero', + }) + return { succes: 'false' } } - //when the user tries to refresh, show an alert - setEnableConfirmation(true); - setLoadingStates("executing transaction..."); - - const { link, txReceipt } = await peanut.createLink({ - signer: signer, - chainId: sendFormData.chainId, - tokenAddress: tokenAddress ?? null, - tokenAmount: Number(sendFormData.amount), - tokenType: tokenType, - tokenDecimals: tokenDecimals, - verbose: true, - }); - console.log("Created link:", link); - utils.saveToLocalStorage(address + " - " + txReceipt.hash, link); - - setClaimLink(link); - setTxReceipt(txReceipt); - setChainId(sendFormData.chainId); - - onNextScreen(); - } catch (error: any) { - if (error.toString().includes("insufficient funds")) { - setErrorState({ - showError: true, - errorMessage: "You don't have enough funds", - }); - } else { - setErrorState({ - showError: true, - errorMessage: - "Something failed while creating your link. Please try again", - }); - console.error(error); + //check if the token is in the userBalances + if ( + userBalances.some( + (balance) => balance.symbol == sendFormData.token && balance.chainId == sendFormData.chainId + ) + ) { + //check that the user has enough funds + const balance = userBalances.find((balance) => balance.symbol === sendFormData.token)?.amount + if (balance && sendFormData.amount > balance) { + setErrorState({ + showError: true, + errorMessage: "You don't have enough funds", + }) + return { succes: 'false' } + } + + if (!signer) { + getWalletClientAndUpdateSigner({ chainId: sendFormData.chainId }) + setErrorState({ + showError: true, + errorMessage: 'Signer undefined, please refresh', + }) + return { succes: 'false' } + } } - } finally { - setLoadingStates("idle"); - setEnableConfirmation(false); - } - }, - [signer, currentChain, userBalances, onNextScreen, isLoading, address] - ); - - useEffect(() => { - userBalances.some((balance) => balance.chainId == formwatch.chainId) - ? setTokenList( - userBalances - .filter((balance) => balance.chainId == formwatch.chainId) - .map((balance) => { - return { - symbol: balance.symbol, - chainId: balance.chainId, - amount: balance.amount, - address: balance.address, - decimals: balance.decimals, - logo: "", - }; - }) - ) - : setTokenList([]); - }, [formwatch.chainId, userBalances, supportedChainsSocketTech]); - - // use this useEffect if you want to populate the tokendropdown with a lot of tokens. This is not recommended bc heavy af - // useEffect(() => { - // if ( - // supportedChainsSocketTech?.some( - // (chain) => chain.chainId == formwatch.chainId - // ) - // ) { - // userBalances.some((balance) => balance.chainId == formwatch.chainId) - // ? setTokenList( - // userBalances - // .filter((balance) => balance.chainId == formwatch.chainId) - // .map((balance) => { - // return { - // symbol: balance.symbol, - // chainId: balance.chainId, - // amount: balance.amount, - // address: balance.address, - // decimals: balance.decimals, - // logo: "", - // }; - // }) - // ) - // : setTokenList( - // tokenDetails - // .filter( - // (detail) => - // detail.chainId.toString() == formwatch.chainId.toString() - // )[0] - // .tokens.map((token) => { - // return { - // symbol: token.symbol, - // amount: 0, - // chainId: formwatch.chainId, - // address: token.address, - // decimals: token.decimals, - // logo: token.logoURI ?? "", - // }; - // }) - // ); - // } else { - // setTokenList( - // tokenDetails - // .filter( - // (detail) => - // detail.chainId.toString() == formwatch.chainId.toString() - // )[0] - // ?.tokens.map((token) => { - // return { - // symbol: token.symbol, - // amount: 0, - // chainId: formwatch.chainId, - // address: token.address, - // decimals: token.decimals, - // logo: token.logoURI ?? "", - // }; - // }) - // ); - // } - // }, [formwatch.chainId, userBalances, supportedChainsSocketTech]); - - const customChainOption = ({ - value, - label, - logoUri, - }: { - value: number; - label: string; - logoUri: string; - }) => ( -
- {/* */} - {label} -
- ); - - const customTokenOption = ({ - value, - label, - logoUri, - amount, - }: { - value: string; - label: string; - logoUri: string; - amount: number; - }) => ( -
- {/* */} - {value} - - {amount > 0 && " - " + Math.round(amount * 10000) / 10000} -
- ); - - useEffect(() => { - if (currentChain && !formHasBeenTouched) { - sendForm.setValue("chainId", currentChain.id); + return { succes: 'true' } } - }, [currentChain]); - useEffect(() => { - if (formwatch.chainId != prevChainId) { - setPrevChainId(formwatch.chainId); - sendForm.setValue("token", ""); + const getTokenDetails = useCallback( + (sendFormData: ISendFormData) => { + let tokenAddress: string = '' + let tokenDecimals: number = 18 + if ( + userBalances.some( + (balance) => balance.symbol == sendFormData.token && balance.chainId == sendFormData.chainId + ) + ) { + tokenAddress = + userBalances.find( + (balance) => balance.chainId == sendFormData.chainId && balance.symbol == sendFormData.token + )?.address ?? '' + tokenDecimals = + userBalances.find( + (balance) => balance.chainId == sendFormData.chainId && balance.symbol == sendFormData.token + )?.decimals ?? 18 + } else { + tokenAddress = + tokenDetails + .find((detail) => detail.chainId.toString() == sendFormData.chainId.toString()) + ?.tokens.find((token) => token.symbol == sendFormData.token)?.address ?? '' + + tokenDecimals = + tokenDetails + .find((detail) => detail.chainId.toString() == sendFormData.chainId.toString()) + ?.tokens.find((token) => token.symbol == sendFormData.token)?.decimals ?? 18 + } - //wait for the wallet to connect - setTimeout(() => { - getWalletClientAndUpdateSigner({ chainId: formwatch.chainId }); - }, 2000); - } - }, [formwatch.chainId, isConnected]); - - return ( - <> -
-

- Send crypto with a link - - BETA - -

-

- Peanut Protocol Demo -

- -
- Choose the chain, set the amount, confirm the transaction. You'll get - a trustless payment link. Send it to whomever you want. + const tokenType = + chainDetails.find((detail) => detail.chainId == sendFormData.chainId)?.nativeCurrency.symbol == + sendFormData.token + ? 0 + : 1 + + return { tokenAddress, tokenDecimals, tokenType } + }, + [userBalances, tokenDetails, chainDetails] + ) + + const createLink = useCallback( + async (sendFormData: ISendFormData) => { + setErrorState({ showError: false, errorMessage: '' }) + if (isLoading) return + try { + setLoadingStates('checking inputs...') + + if (checkForm(sendFormData).succes === 'false') { + return + } + setEnableConfirmation(true) + + const { tokenAddress, tokenDecimals, tokenType } = getTokenDetails(sendFormData) + + console.log( + 'sending ' + + sendFormData.amount + + ' ' + + sendFormData.token + + ' on chain with id ' + + sendFormData.chainId + + ' with token address: ' + + tokenAddress + + ' with tokenType: ' + + tokenType + + ' with tokenDecimals: ' + + tokenDecimals + ) + + setLoadingStates('allow network switch...') + //check if the user is on the correct chain + if (currentChain?.id.toString() !== sendFormData.chainId.toString()) { + await utils + .waitForPromise(switchNetwork({ chainId: Number(sendFormData.chainId) })) + .catch((error) => { + setErrorState({ + showError: true, + errorMessage: 'Something went wrong while switching networks', + }) + return + }) + setLoadingStates('switching network...') + await new Promise((resolve) => setTimeout(resolve, 4000)) // wait a sec after switching chain before making other deeplink + setLoadingStates('loading...') + } + + //when the user tries to refresh, show an alert + setEnableConfirmation(true) + setLoadingStates('executing transaction...') + + const { link, txReceipt } = await peanut.createLink({ + signer: signer, + chainId: sendFormData.chainId, + tokenAddress: tokenAddress ?? null, + tokenAmount: Number(sendFormData.amount), + tokenType: tokenType, + tokenDecimals: tokenDecimals, + verbose: true, + }) + console.log('Created link:', link) + utils.saveToLocalStorage(address + ' - ' + txReceipt.hash, link) + + setClaimLink(link) + setTxReceipt(txReceipt) + setChainId(sendFormData.chainId) + + onNextScreen() + } catch (error: any) { + if (error.toString().includes('insufficient funds')) { + setErrorState({ + showError: true, + errorMessage: "You don't have enough funds", + }) + } else { + setErrorState({ + showError: true, + errorMessage: 'Something failed while creating your link. Please try again', + }) + console.error(error) + } + } finally { + setLoadingStates('idle') + setEnableConfirmation(false) + } + }, + [signer, currentChain, userBalances, onNextScreen, isLoading, address] + ) + + useEffect(() => { + userBalances.some((balance) => balance.chainId == formwatch.chainId) + ? setTokenList( + userBalances + .filter((balance) => balance.chainId == formwatch.chainId) + .map((balance) => { + return { + symbol: balance.symbol, + chainId: balance.chainId, + amount: balance.amount, + address: balance.address, + decimals: balance.decimals, + logo: '', + } + }) + ) + : setTokenList([]) + }, [formwatch.chainId, userBalances, supportedChainsSocketTech]) + + // use this useEffect if you want to populate the tokendropdown with a lot of tokens. This is not recommended bc heavy af + // useEffect(() => { + // if ( + // supportedChainsSocketTech?.some( + // (chain) => chain.chainId == formwatch.chainId + // ) + // ) { + // userBalances.some((balance) => balance.chainId == formwatch.chainId) + // ? setTokenList( + // userBalances + // .filter((balance) => balance.chainId == formwatch.chainId) + // .map((balance) => { + // return { + // symbol: balance.symbol, + // chainId: balance.chainId, + // amount: balance.amount, + // address: balance.address, + // decimals: balance.decimals, + // logo: "", + // }; + // }) + // ) + // : setTokenList( + // tokenDetails + // .filter( + // (detail) => + // detail.chainId.toString() == formwatch.chainId.toString() + // )[0] + // .tokens.map((token) => { + // return { + // symbol: token.symbol, + // amount: 0, + // chainId: formwatch.chainId, + // address: token.address, + // decimals: token.decimals, + // logo: token.logoURI ?? "", + // }; + // }) + // ); + // } else { + // setTokenList( + // tokenDetails + // .filter( + // (detail) => + // detail.chainId.toString() == formwatch.chainId.toString() + // )[0] + // ?.tokens.map((token) => { + // return { + // symbol: token.symbol, + // amount: 0, + // chainId: formwatch.chainId, + // address: token.address, + // decimals: token.decimals, + // logo: token.logoURI ?? "", + // }; + // }) + // ); + // } + // }, [formwatch.chainId, userBalances, supportedChainsSocketTech]); + + const customChainOption = ({ value, label, logoUri }: { value: number; label: string; logoUri: string }) => ( +
+ {/* */} + {label} +
+ ) + + const customTokenOption = ({ + value, + label, + logoUri, + amount, + }: { + value: string + label: string + logoUri: string + amount: number + }) => ( +
+ {/* */} + {value} + + {amount > 0 && ' - ' + Math.round(amount * 10000) / 10000}
-
-
-
-
-
- "No tokens found"} - value={{ - value: formwatch.token, - label: formwatch.token, - logoUri: "", - amount: 0, - }} - placeholder="Select token..." - styles={{ - control: (provided) => ({ - ...provided, - backgroundColor: "white", - borderColor: "black !important", - borderWidth: "2px", - borderRadius: "0px", - }), - option: (provided, state) => ({ - ...provided, - backgroundColor: state.isFocused ? "black" : "white", - color: state.isFocused ? "white" : "black", - }), - }} - options={tokenList?.map((token) => { - return { - value: token.symbol, - label: token.symbol, - logoUri: token.logo, - amount: token.amount, - }; - })} - formatOptionLabel={customTokenOption} - onChange={(option) => { - setFormHasBeenTouched(true); - if (option && option.value) - sendForm.setValue("token", option.value); - }} - isSearchable={false} - /> + +
+
+
+ 'No tokens found'} + value={{ + value: formwatch.token, + label: formwatch.token, + logoUri: '', + amount: 0, + }} + placeholder="Select token..." + styles={{ + control: (provided) => ({ + ...provided, + backgroundColor: 'white', + borderColor: 'black !important', + borderWidth: '2px', + borderRadius: '0px', + }), + option: (provided, state) => ({ + ...provided, + backgroundColor: state.isFocused ? 'black' : 'white', + color: state.isFocused ? 'white' : 'black', + }), + }} + options={tokenList?.map((token) => { + return { + value: token.symbol, + label: token.symbol, + logoUri: token.logo, + amount: token.amount, + } + })} + formatOptionLabel={customTokenOption} + onChange={(option) => { + setFormHasBeenTouched(true) + if (option && option.value) sendForm.setValue('token', option.value) + }} + isSearchable={false} + /> +
+
+
+ {formwatch.token && ( +
+ + + +
+ )} + + { + sendForm.setValue('amount', Number(e.target.value)) + setFormHasBeenTouched(true) + }, + })} + /> +
+ +
+ + {errorState.showError && ( +
+ +
+ )} +
+
+ +
+

+ Hit us up on{' '} + + Discord + + ! +

-
-
- {formwatch.token && ( -
- - - -
- )} - - { - sendForm.setValue("amount", Number(e.target.value)); - setFormHasBeenTouched(true); - }, - })} - /> -
- -
- - {errorState.showError && ( -
- -
- )} -
-
- -
-

- Hit us up on{" "} - - Discord - - ! -

-
- - - - ); + + + + ) } diff --git a/src/components/send/views/succes.view.tsx b/src/components/send/views/succes.view.tsx index 40fc36153..4d82e5816 100644 --- a/src/components/send/views/succes.view.tsx +++ b/src/components/send/views/succes.view.tsx @@ -1,157 +1,141 @@ -import { useMemo, useState } from "react"; -import QRCode from "react-qr-code"; +import { useMemo, useState } from 'react' +import QRCode from 'react-qr-code' -import dropdown_svg from "@/assets/dropdown.svg"; +import dropdown_svg from '@/assets/dropdown.svg' -import * as _consts from "../send.consts"; -import { useAtom } from "jotai"; -import * as store from "@/store/store"; -import * as global_components from "@/components/global"; +import * as _consts from '../send.consts' +import { useAtom } from 'jotai' +import * as store from '@/store/store' +import * as global_components from '@/components/global' -export function SendSuccessView({ - onCustomScreen, - claimLink, - txReceipt, - chainId, -}: _consts.ISendScreenProps) { - const [isDropdownOpen, setIsDropdownOpen] = useState(false); - const [isCopied, setIsCopied] = useState(false); +export function SendSuccessView({ onCustomScreen, claimLink, txReceipt, chainId }: _consts.ISendScreenProps) { + const [isDropdownOpen, setIsDropdownOpen] = useState(false) + const [isCopied, setIsCopied] = useState(false) - const [chainDetails] = useAtom(store.defaultChainDetailsAtom); + const [chainDetails] = useAtom(store.defaultChainDetailsAtom) - const explorerUrlWithTx = useMemo( - () => - chainDetails.find((detail) => detail.chainId === chainId)?.explorers[0] - .url + - "/tx/" + - txReceipt?.hash, - [txReceipt, chainId] - ); + const explorerUrlWithTx = useMemo( + () => chainDetails.find((detail) => detail.chainId === chainId)?.explorers[0].url + '/tx/' + txReceipt?.hash, + [txReceipt, chainId] + ) - return ( - <> -
-

Yay!

-

- Send this link to your friend so they can claim their funds. -

-
-
- {claimLink} -
-
{ - navigator.clipboard.writeText(claimLink); - setIsCopied(true); - }} - > - {isCopied ? ( -
- - {" "} - copied!{" "} - -
- ) : ( - - )} -
-
+ return ( + <> +
+

Yay!

+

Send this link to your friend so they can claim their funds.

+
+
+ {claimLink} +
+
{ + navigator.clipboard.writeText(claimLink) + setIsCopied(true) + }} + > + {isCopied ? ( +
+ + {' '} + copied!{' '} + +
+ ) : ( + + )} +
+
-
{ - setIsDropdownOpen(!isDropdownOpen); - }} - > -
- More Info and QR code{" "} -
- -
- {isDropdownOpen && ( -
-
-
- -
-
-

- - Your transaction hash - -

+
{ + setIsDropdownOpen(!isDropdownOpen) + }} + > +
More Info and QR code
+ +
+ {isDropdownOpen && ( +
+
+
+ +
+
+

+ + Your transaction hash + +

- {/*

+ {/*

If you input an email address, we'll send them the link there too!

whats this? */} -
- )} +
+ )} -

- {" "} - Want to do it again? click{" "} - { - onCustomScreen("INITIAL"); - }} - target="_blank" - className="underline text-black cursor-pointer" - > - here - {" "} - to go back home! -

+

+ {' '} + Want to do it again? click{' '} + { + onCustomScreen('INITIAL') + }} + target="_blank" + className="cursor-pointer text-black underline" + > + here + {' '} + to go back home! +

-

- {" "} - Thoughts? Feedback? Use cases? Memes? Hit us up on{" "} - - Discord - - ! -

-
+

+ {' '} + Thoughts? Feedback? Use cases? Memes? Hit us up on{' '} + + Discord + + ! +

+
- - - ); + + + ) } diff --git a/src/components/terms/index.ts b/src/components/terms/index.ts index 16628bcd8..e6e54adff 100644 --- a/src/components/terms/index.ts +++ b/src/components/terms/index.ts @@ -1 +1 @@ -export * from "./terms"; +export * from './terms' diff --git a/src/components/terms/terms.tsx b/src/components/terms/terms.tsx index c0bc51aa0..02cd68871 100644 --- a/src/components/terms/terms.tsx +++ b/src/components/terms/terms.tsx @@ -1,41 +1,39 @@ -import peanutman_presenting from "@/assets/peanutman-presenting.svg"; +import peanutman_presenting from '@/assets/peanutman-presenting.svg' export function Terms() { - return ( -
-
- -
-
-
- {"<"} Hey there! These are our TOS. -
-
- Terms of Service -
+ return ( +
+
+ +
+
+
+ {'<'} Hey there! These are our TOS. +
+
Terms of Service
-
- Don't do illegal stuff pls :( Full terms can be found{" "} - - here - -
+
+ Don't do illegal stuff pls :( Full terms can be found{' '} + + here + +
-
- {" "} - If you have any questions, you can always get in touch{" "} - - with us!{" "} - +
+ {' '} + If you have any questions, you can always get in touch{' '} + + with us!{' '} + +
+
-
-
- ); + ) } diff --git a/src/config/index.ts b/src/config/index.ts index c2c255184..9a84610c6 100644 --- a/src/config/index.ts +++ b/src/config/index.ts @@ -1,2 +1,2 @@ -export * from "./wagmi.config"; -export * from "./socketTech.config"; +export * from './wagmi.config' +export * from './socketTech.config' diff --git a/src/config/socketTech.config.tsx b/src/config/socketTech.config.tsx index 574aeeefb..14a39bf35 100644 --- a/src/config/socketTech.config.tsx +++ b/src/config/socketTech.config.tsx @@ -1,8 +1,8 @@ -import * as socketTech from "@socket.tech/socket-v2-sdk"; +import * as socketTech from '@socket.tech/socket-v2-sdk' export const socket = new socketTech.Socket({ - apiKey: process.env.SOCKET_API_KEY ?? "", // add api key here - defaultQuotePreferences: { - singleTxOnly: true, - }, -}); + apiKey: process.env.SOCKET_API_KEY ?? '', // add api key here + defaultQuotePreferences: { + singleTxOnly: true, + }, +}) diff --git a/src/config/wagmi.config.tsx b/src/config/wagmi.config.tsx index 8fde71612..fb59e641c 100644 --- a/src/config/wagmi.config.tsx +++ b/src/config/wagmi.config.tsx @@ -1,23 +1,17 @@ -import { configureChains, createConfig } from "wagmi"; -import { - EthereumClient, - w3mConnectors, - w3mProvider, -} from "@web3modal/ethereum"; +import { configureChains, createConfig } from 'wagmi' +import { EthereumClient, w3mConnectors, w3mProvider } from '@web3modal/ethereum' -import * as consts from "@/consts"; +import * as consts from '@/consts' -const { publicClient } = configureChains(consts.chains, [ - w3mProvider({ projectId: process.env.WC_PROJECT_ID ?? "" }), -]); +const { publicClient } = configureChains(consts.chains, [w3mProvider({ projectId: process.env.WC_PROJECT_ID ?? '' })]) export const wagmiConfig = createConfig({ - autoConnect: true, - connectors: w3mConnectors({ - projectId: process.env.WC_PROJECT_ID ?? "", - chains: consts.chains, - }), - publicClient, -}); + autoConnect: true, + connectors: w3mConnectors({ + projectId: process.env.WC_PROJECT_ID ?? '', + chains: consts.chains, + }), + publicClient, +}) -export const ethereumClient = new EthereumClient(wagmiConfig, consts.chains); +export const ethereumClient = new EthereumClient(wagmiConfig, consts.chains) diff --git a/src/consts/chains.consts.ts b/src/consts/chains.consts.ts index 4c04a8366..2b90dfae3 100644 --- a/src/consts/chains.consts.ts +++ b/src/consts/chains.consts.ts @@ -1,45 +1,45 @@ import { - gnosis, - mainnet, - arbitrum, - polygon, - bsc, - goerli, - scrollTestnet, - optimism, - bscTestnet, - optimismGoerli, - polygonZkEvmTestnet, - mantleTestnet, - gnosisChiado, - avalancheFuji, - avalanche, - celoAlfajores, - polygonMumbai, - filecoinCalibration, - neonDevnet, -} from "@wagmi/chains"; + gnosis, + mainnet, + arbitrum, + polygon, + bsc, + goerli, + scrollTestnet, + optimism, + bscTestnet, + optimismGoerli, + polygonZkEvmTestnet, + mantleTestnet, + gnosisChiado, + avalancheFuji, + avalanche, + celoAlfajores, + polygonMumbai, + filecoinCalibration, + neonDevnet, +} from '@wagmi/chains' export const chains = [ - mainnet, - arbitrum, - polygon, - bsc, - goerli, - gnosis, - scrollTestnet, - optimism, - bscTestnet, - optimismGoerli, - polygonZkEvmTestnet, - mantleTestnet, - gnosisChiado, - avalancheFuji, - avalanche, - celoAlfajores, - polygonMumbai, - filecoinCalibration, - neonDevnet, -]; + mainnet, + arbitrum, + polygon, + bsc, + goerli, + gnosis, + scrollTestnet, + optimism, + bscTestnet, + optimismGoerli, + polygonZkEvmTestnet, + mantleTestnet, + gnosisChiado, + avalancheFuji, + avalanche, + celoAlfajores, + polygonMumbai, + filecoinCalibration, + neonDevnet, +] //have a look to make this more modular diff --git a/src/consts/index.ts b/src/consts/index.ts index 9ec8f24a7..f050afc71 100644 --- a/src/consts/index.ts +++ b/src/consts/index.ts @@ -1,2 +1,2 @@ -export * from "./chains.consts"; -export * from "./loadingStates.consts"; +export * from './chains.consts' +export * from './loadingStates.consts' diff --git a/src/consts/loadingStates.consts.ts b/src/consts/loadingStates.consts.ts index b6a0610e2..f2f7ca29f 100644 --- a/src/consts/loadingStates.consts.ts +++ b/src/consts/loadingStates.consts.ts @@ -1,8 +1,8 @@ export type LoadingStates = - | "idle" - | "loading..." - | "executing transaction..." - | "allow network switch..." - | "switching network..." - | "checking signer..." - | "checking inputs..."; + | 'idle' + | 'loading...' + | 'executing transaction...' + | 'allow network switch...' + | 'switching network...' + | 'checking signer...' + | 'checking inputs...' diff --git a/src/hooks/index.ts b/src/hooks/index.ts index b74bc6039..1a1ced522 100644 --- a/src/hooks/index.ts +++ b/src/hooks/index.ts @@ -1 +1 @@ -export * from "./useConfirmRefresh"; +export * from './useConfirmRefresh' diff --git a/src/hooks/useConfirmRefresh.ts b/src/hooks/useConfirmRefresh.ts index 77b1b3a5d..593cb5d1d 100644 --- a/src/hooks/useConfirmRefresh.ts +++ b/src/hooks/useConfirmRefresh.ts @@ -1,20 +1,20 @@ -import { useEffect } from "react"; +import { useEffect } from 'react' export const useConfirmRefresh = (enable: boolean) => { - useEffect(() => { - const handleBeforeUnload = (event: BeforeUnloadEvent) => { - event.preventDefault(); - event.returnValue = ""; // This is required for Chrome - }; + useEffect(() => { + const handleBeforeUnload = (event: BeforeUnloadEvent) => { + event.preventDefault() + event.returnValue = '' // This is required for Chrome + } - if (enable) { - window.addEventListener("beforeunload", handleBeforeUnload); - } + if (enable) { + window.addEventListener('beforeunload', handleBeforeUnload) + } - return () => { - if (enable) { - window.removeEventListener("beforeunload", handleBeforeUnload); - } - }; - }, [enable]); -}; + return () => { + if (enable) { + window.removeEventListener('beforeunload', handleBeforeUnload) + } + } + }, [enable]) +} diff --git a/src/interfaces/index.ts b/src/interfaces/index.ts index a427c734f..f1444d3ea 100644 --- a/src/interfaces/index.ts +++ b/src/interfaces/index.ts @@ -1 +1 @@ -export * from "./interfaces"; +export * from './interfaces' diff --git a/src/interfaces/interfaces.ts b/src/interfaces/interfaces.ts index 1ebbcbd58..52bc283e7 100644 --- a/src/interfaces/interfaces.ts +++ b/src/interfaces/interfaces.ts @@ -1,75 +1,75 @@ export interface IUserBalance { - chainId: number; - address: string; - name: string; - symbol: string; - decimals: number; - price: number; - amount: number; - currency: string; + chainId: number + address: string + name: string + symbol: string + decimals: number + price: number + amount: number + currency: string } export interface IPeanutChainDetails { - name: string; - chain: string; - icon: { - url: string; - width: number; - height: number; - format: string; - }[]; - rpc: string[]; - features: { - name: string; - }[]; - faucets: string[]; - nativeCurrency: { - name: string; - symbol: string; - decimals: number; - }; - infoURL: string; - shortName: string; - chainId: number; - networkId: number; - slip44: number; - ens: { - registry: string; - }; - explorers: { - name: string; - url: string; - standard: string; - }[]; + name: string + chain: string + icon: { + url: string + width: number + height: number + format: string + }[] + rpc: string[] + features: { + name: string + }[] + faucets: string[] + nativeCurrency: { + name: string + symbol: string + decimals: number + } + infoURL: string + shortName: string + chainId: number + networkId: number + slip44: number + ens: { + registry: string + } + explorers: { + name: string + url: string + standard: string + }[] } export interface IPeanutTokenDetail { - chainId: string; - name: string; - tokens: { - address: string; - name: string; - symbol: string; - decimals: number; - logoURI: string; - }[]; + chainId: string + name: string + tokens: { + address: string + name: string + symbol: string + decimals: number + logoURI: string + }[] } export interface ILocalStorageItem { - address: string; - hash: string; - link: string; + address: string + hash: string + link: string } export interface ILinkDetails { - link: string; - chainId: number; - depositIndex: number; - contractVersion: string; - password: string; - tokenType: number; - tokenAddress: string; - tokenSymbol: string; - tokenName: string; - tokenAmount: string; + link: string + chainId: number + depositIndex: number + contractVersion: string + password: string + tokenType: number + tokenAddress: string + tokenSymbol: string + tokenName: string + tokenAmount: string } diff --git a/src/store/index.ts b/src/store/index.ts index f5990c259..16c863321 100644 --- a/src/store/index.ts +++ b/src/store/index.ts @@ -1 +1 @@ -export * from "./store"; +export * from './store' diff --git a/src/store/store.tsx b/src/store/store.tsx index c934b7e2f..660f35444 100644 --- a/src/store/store.tsx +++ b/src/store/store.tsx @@ -1,147 +1,134 @@ -"use client"; -import { atom, useAtom, useSetAtom } from "jotai"; -import { useAccount } from "wagmi"; -import { useEffect } from "react"; -const peanut = require("@squirrel-labs/peanut-sdk"); -import * as interfaces from "@/interfaces"; -import * as socketTech from "@socket.tech/socket-v2-sdk"; -import { ethers } from "ethers"; -import { formatEther } from "ethers/lib/utils"; - -export const userBalancesAtom = atom([]); - -export const defaultChainDetailsAtom = atom( - [] -); -export const defaultTokenDetailsAtom = atom( - [] -); - -export const supportedChainsSocketTechAtom = atom< - socketTech.ChainDetails[] | undefined ->(undefined); +'use client' +import { atom, useAtom, useSetAtom } from 'jotai' +import { useAccount } from 'wagmi' +import { useEffect } from 'react' +const peanut = require('@squirrel-labs/peanut-sdk') +import * as interfaces from '@/interfaces' +import * as socketTech from '@socket.tech/socket-v2-sdk' +import { ethers } from 'ethers' +import { formatEther } from 'ethers/lib/utils' + +export const userBalancesAtom = atom([]) + +export const defaultChainDetailsAtom = atom([]) +export const defaultTokenDetailsAtom = atom([]) + +export const supportedChainsSocketTechAtom = atom(undefined) export function Store({ children }: { children: React.ReactNode }) { - const [userBalances, setUserBalances] = useAtom(userBalancesAtom); - const setDefaultChainDetails = useSetAtom(defaultChainDetailsAtom); - const setDefaultTokenDetails = useSetAtom(defaultTokenDetailsAtom); - const setSupportedChainsSocketTech = useSetAtom( - supportedChainsSocketTechAtom - ); - - const { address: userAddr, isDisconnected } = useAccount(); - - useEffect(() => { - setUserBalances([]); - if (userAddr) { - //This will fetch all balances for the supported chains by socket.tech (https://docs.socket.tech/socket-liquidity-layer/socketll-overview/chains-dexs-bridges) - loadUserBalances(userAddr); - loadGoerliUserBalances(userAddr); + const [userBalances, setUserBalances] = useAtom(userBalancesAtom) + const setDefaultChainDetails = useSetAtom(defaultChainDetailsAtom) + const setDefaultTokenDetails = useSetAtom(defaultTokenDetailsAtom) + const setSupportedChainsSocketTech = useSetAtom(supportedChainsSocketTechAtom) + + const { address: userAddr, isDisconnected } = useAccount() + + useEffect(() => { + setUserBalances([]) + if (userAddr) { + //This will fetch all balances for the supported chains by socket.tech (https://docs.socket.tech/socket-liquidity-layer/socketll-overview/chains-dexs-bridges) + loadUserBalances(userAddr) + loadGoerliUserBalances(userAddr) + } + }, [userAddr]) + + useEffect(() => { + if (isDisconnected) { + setUserBalances([]) + } + }, [isDisconnected]) + + useEffect(() => { + getSupportedChainsSocketTech() + getPeanutChainAndTokenDetails() + }, []) + + const getSupportedChainsSocketTech = async () => { + try { + const supportedChainsResponse = await socketTech.Supported.getAllSupportedChains() + if (supportedChainsResponse.success) { + setSupportedChainsSocketTech(supportedChainsResponse.result) + } + } catch (error) { + console.error('error loading supportedChainsSocketTech, ', error) + } } - }, [userAddr]); - useEffect(() => { - if (isDisconnected) { - setUserBalances([]); - } - }, [isDisconnected]); - - useEffect(() => { - getSupportedChainsSocketTech(); - getPeanutChainAndTokenDetails(); - }, []); - - const getSupportedChainsSocketTech = async () => { - try { - const supportedChainsResponse = - await socketTech.Supported.getAllSupportedChains(); - if (supportedChainsResponse.success) { - setSupportedChainsSocketTech(supportedChainsResponse.result); - } - } catch (error) { - console.error("error loading supportedChainsSocketTech, ", error); + const getPeanutChainAndTokenDetails = async () => { + if (peanut) { + const chainDetailsArray = Object.keys(peanut.default.CHAIN_DETAILS).map( + (key) => peanut.default.CHAIN_DETAILS[key] + ) + const tokenDetailsArray = peanut.default.TOKEN_DETAILS + setDefaultChainDetails(chainDetailsArray) + setDefaultTokenDetails(tokenDetailsArray) + } } - }; - - const getPeanutChainAndTokenDetails = async () => { - if (peanut) { - const chainDetailsArray = Object.keys(peanut.default.CHAIN_DETAILS).map( - (key) => peanut.default.CHAIN_DETAILS[key] - ); - const tokenDetailsArray = peanut.default.TOKEN_DETAILS; - setDefaultChainDetails(chainDetailsArray); - setDefaultTokenDetails(tokenDetailsArray); - } - }; - - const loadUserBalances = async (address: string) => { - try { - const userBalancesResponse = await socketTech.Balances.getBalances({ - userAddress: address, - }); - - if (userBalancesResponse.success) { - setUserBalances((prev) => { - return [...prev, ...userBalancesResponse.result]; - }); - } else { - setUserBalances([]); - } - } catch (error) { - console.error("error loading userBalances, ", error); + + const loadUserBalances = async (address: string) => { + try { + const userBalancesResponse = await socketTech.Balances.getBalances({ + userAddress: address, + }) + + if (userBalancesResponse.success) { + setUserBalances((prev) => { + return [...prev, ...userBalancesResponse.result] + }) + } else { + setUserBalances([]) + } + } catch (error) { + console.error('error loading userBalances, ', error) + } } - }; - - const loadGoerliUserBalances = async (address: string) => { - const optiGoerli = new ethers.providers.JsonRpcProvider( - process.env.OPTI_GOERLI_RPC_URL - ); - const goerli = new ethers.providers.JsonRpcProvider( - process.env.GOERLI_RPC_URL - ); - - try { - const optiBalanceWei = await optiGoerli.getBalance(address); - const goerliBalanceWei = await goerli.getBalance(address); - - const optiBalanceEth = ethers.utils.formatEther(optiBalanceWei); - const goerliBalanceEth = ethers.utils.formatEther(goerliBalanceWei); - - const goerliBalanceObject: interfaces.IUserBalance = { - chainId: 5, - symbol: "GoerliETH", - name: "GoerliETH", - address: "0xdD69DB25F6D620A7baD3023c5d32761D353D3De9", - decimals: 18, - amount: Number(goerliBalanceEth), - price: 0, - currency: "GoerliETH", - }; - const optiBalanceObject: interfaces.IUserBalance = { - chainId: 420, - symbol: "GoerliETH", - name: "GoerliETH", - address: "", - decimals: 18, - amount: Number(optiBalanceEth), - price: 0, - currency: "GoerliETH", - }; - - if (Number(goerliBalanceEth) > 0) { - setUserBalances((prev) => { - return [...prev, goerliBalanceObject]; - }); - } - if (Number(optiBalanceEth) > 0) { - setUserBalances((prev) => { - return [...prev, optiBalanceObject]; - }); - } - } catch (error) { - console.error("Error:", error); + + const loadGoerliUserBalances = async (address: string) => { + const optiGoerli = new ethers.providers.JsonRpcProvider(process.env.OPTI_GOERLI_RPC_URL) + const goerli = new ethers.providers.JsonRpcProvider(process.env.GOERLI_RPC_URL) + + try { + const optiBalanceWei = await optiGoerli.getBalance(address) + const goerliBalanceWei = await goerli.getBalance(address) + + const optiBalanceEth = ethers.utils.formatEther(optiBalanceWei) + const goerliBalanceEth = ethers.utils.formatEther(goerliBalanceWei) + + const goerliBalanceObject: interfaces.IUserBalance = { + chainId: 5, + symbol: 'GoerliETH', + name: 'GoerliETH', + address: '0xdD69DB25F6D620A7baD3023c5d32761D353D3De9', + decimals: 18, + amount: Number(goerliBalanceEth), + price: 0, + currency: 'GoerliETH', + } + const optiBalanceObject: interfaces.IUserBalance = { + chainId: 420, + symbol: 'GoerliETH', + name: 'GoerliETH', + address: '', + decimals: 18, + amount: Number(optiBalanceEth), + price: 0, + currency: 'GoerliETH', + } + + if (Number(goerliBalanceEth) > 0) { + setUserBalances((prev) => { + return [...prev, goerliBalanceObject] + }) + } + if (Number(optiBalanceEth) > 0) { + setUserBalances((prev) => { + return [...prev, optiBalanceObject] + }) + } + } catch (error) { + console.error('Error:', error) + } } - }; - return <>{children}; + return <>{children} } diff --git a/src/styles/globals.css b/src/styles/globals.css index b69436e94..8be9e4ba7 100644 --- a/src/styles/globals.css +++ b/src/styles/globals.css @@ -3,137 +3,136 @@ @tailwind utilities; :root { - --foreground-rgb: 0, 0, 0; - --background-start-rgb: 214, 219, 220; - --background-end-rgb: 255, 255, 255; + --foreground-rgb: 0, 0, 0; + --background-start-rgb: 214, 219, 220; + --background-end-rgb: 255, 255, 255; } @media (prefers-color-scheme: dark) { - :root { - --foreground-rgb: 255, 255, 255; - --background-start-rgb: 0, 0, 0; - --background-end-rgb: 0, 0, 0; - } + :root { + --foreground-rgb: 255, 255, 255; + --background-start-rgb: 0, 0, 0; + --background-end-rgb: 0, 0, 0; + } } html, body { - width: 100%; - height: 100%; - margin: 0px; - padding: 0px; - overflow-x: hidden; + width: 100%; + height: 100%; + margin: 0px; + padding: 0px; + overflow-x: hidden; } body { - color: rgb(var(--foreground-rgb)); - background: linear-gradient( - to bottom, - transparent, - rgb(var(--background-end-rgb)) - ) - rgb(var(--background-start-rgb)); - margin: 0 !important; + color: rgb(var(--foreground-rgb)); + background: linear-gradient(to bottom, transparent, rgb(var(--background-end-rgb))) rgb(var(--background-start-rgb)); + margin: 0 !important; } /* SCROLLBAR */ /* For Webkit-based browsers (Chrome, Safari and Opera) */ .scrollbar-hide::-webkit-scrollbar { - display: none; + display: none; } /* For IE, Edge and Firefox */ .scrollbar-hide { - -ms-overflow-style: none; /* IE and Edge */ - scrollbar-width: none; /* Firefox */ + -ms-overflow-style: none; /* IE and Edge */ + scrollbar-width: none; /* Firefox */ } @font-face { - font-family: "Montserrat"; - font-style: normal; - font-weight: 100, 200, 300, 400, 500, 600, 700, 800, 900; - src: url(https://fonts.gstatic.com/s/montserrat/v25/JTUHjIg1_i6t8kCHKm4532VJOt5-QNFgpCtr6Hw5aXo.woff2) - format("woff2"); - unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, - U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, - U+FEFF, U+FFFD; + font-family: 'Montserrat'; + font-style: normal; + font-weight: 100, 200, 300, 400, 500, 600, 700, 800, 900; + src: url(https://fonts.gstatic.com/s/montserrat/v25/JTUHjIg1_i6t8kCHKm4532VJOt5-QNFgpCtr6Hw5aXo.woff2) + format('woff2'); + unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, + U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD; } .brutalborder { - border: 2px solid #000000; + border: 2px solid #000000; } .brutalborder-left { - border-left-style: solid; + border-left-style: solid; } .brutalborder-bottom { - border-bottom: 1px solid #ddd; + border-bottom: 1px solid #ddd; } /* replace cta-btn id with rainbow border in html if not CTA at some point @konrad */ #cta-btn { - border: 5px solid black; - padding: 1rem; - transition: box-shadow 1s ease-in-out, border-radius 1s ease-in-out; - box-shadow: 0.5rem 0.5rem 0 0px #000; - color: #000; - font-weight: 900; + border: 5px solid black; + padding: 1rem; + transition: + box-shadow 1s ease-in-out, + border-radius 1s ease-in-out; + box-shadow: 0.5rem 0.5rem 0 0px #000; + color: #000; + font-weight: 900; } #cta-btn:hover { - /* animation: disco 1s infinite; */ - /* background-color: #000; */ - transform: ease-in-out 2s; - border-radius: 2rem; - box-shadow: 0 0 0 0.5rem #ff90e8, 0 0 0 1rem #23a094, 0 0 0 1.5rem #f1f333, - 0 0 0 2rem #90a8ed; - /* normal shadow */ - /* 0.5rem 0.5rem 0 0 #ff90e8, + /* animation: disco 1s infinite; */ + /* background-color: #000; */ + transform: ease-in-out 2s; + border-radius: 2rem; + box-shadow: + 0 0 0 0.5rem #ff90e8, + 0 0 0 1rem #23a094, + 0 0 0 1.5rem #f1f333, + 0 0 0 2rem #90a8ed; + /* normal shadow */ + /* 0.5rem 0.5rem 0 0 #ff90e8, 1rem 1rem 0 0 #23a094, 1.5rem 1.5rem 0 0 #F1F333, 2rem 2rem 0 0 #90A8ED, */ } #cta-btn:active { - animation: disco 0.5s infinite; + animation: disco 0.5s infinite; } /* Chrome, Safari, Edge, Opera */ input::-webkit-outer-spin-button, input::-webkit-inner-spin-button { - -webkit-appearance: none; - margin: 0; + -webkit-appearance: none; + margin: 0; } -Firefox input[type="number"] { - appearance: textfield; - -moz-appearance: textfield; +Firefox input[type='number'] { + appearance: textfield; + -moz-appearance: textfield; } select { - -webkit-appearance: none; - -moz-appearance: none; - appearance: none; - background: url("data:image/svg+xml;utf8,") - no-repeat; - background-size: 12px; - background-position: calc(100% - 15px) center; - background-repeat: no-repeat; - background-color: white; - background-position-y: 60%; + -webkit-appearance: none; + -moz-appearance: none; + appearance: none; + background: url("data:image/svg+xml;utf8,") + no-repeat; + background-size: 12px; + background-position: calc(100% - 15px) center; + background-repeat: no-repeat; + background-color: white; + background-position-y: 60%; } input { - box-sizing: border-box; + box-sizing: border-box; } @layer base { - h1 { - font-weight: 900; - letter-spacing: 0.01em; - } - h2 { - font-weight: 900; - letter-spacing: 0.01em; - } + h1 { + font-weight: 900; + letter-spacing: 0.01em; + } + h2 { + font-weight: 900; + letter-spacing: 0.01em; + } } diff --git a/src/utils/general.utils.ts b/src/utils/general.utils.ts index 47e650168..5ac2dd2d7 100644 --- a/src/utils/general.utils.ts +++ b/src/utils/general.utils.ts @@ -1,94 +1,79 @@ -import * as interfaces from "@/interfaces"; +import * as interfaces from '@/interfaces' export const shortenAddress = (address: string) => { - const firstBit = address.substring(0, 6); - const endingBit = address.substring(address.length - 4, address.length); + const firstBit = address.substring(0, 6) + const endingBit = address.substring(address.length - 4, address.length) - return firstBit + ".."; -}; + return firstBit + '..' +} -export function waitForPromise( - promise: Promise, - timeoutTime: number = 30000 -): Promise { - return new Promise((resolve, reject) => { - let timeoutId = setTimeout(() => { - reject( - "Timeout: 30 seconds have passed without a response from the promise" - ); - }, timeoutTime); +export function waitForPromise(promise: Promise, timeoutTime: number = 30000): Promise { + return new Promise((resolve, reject) => { + let timeoutId = setTimeout(() => { + reject('Timeout: 30 seconds have passed without a response from the promise') + }, timeoutTime) - promise - .then((result) => { - clearTimeout(timeoutId); - resolve(result); - }) - .catch((error) => { - clearTimeout(timeoutId); - reject(error); - }); - }); + promise + .then((result) => { + clearTimeout(timeoutId) + resolve(result) + }) + .catch((error) => { + clearTimeout(timeoutId) + reject(error) + }) + }) } export const saveToLocalStorage = (key: string, data: any) => { - try { - // Convert the data to a string before storing it in localStorage - const serializedData = JSON.stringify(data); - localStorage.setItem(key, serializedData); - } catch (error) { - console.error("Error saving to localStorage:", error); - } -}; + try { + // Convert the data to a string before storing it in localStorage + const serializedData = JSON.stringify(data) + localStorage.setItem(key, serializedData) + } catch (error) { + console.error('Error saving to localStorage:', error) + } +} -export const getAllLinksFromLocalStorage = ({ - address, -}: { - address: string; -}) => { - try { - const localStorageData: interfaces.ILocalStorageItem[] = []; +export const getAllLinksFromLocalStorage = ({ address }: { address: string }) => { + try { + const localStorageData: interfaces.ILocalStorageItem[] = [] - for (let i = 0; i < localStorage.length; i++) { - const key = localStorage.key(i); + for (let i = 0; i < localStorage.length; i++) { + const key = localStorage.key(i) - if (key !== null && key?.includes(address)) { - const value = localStorage.getItem(key); - if (value !== null) { - const x = { - address: key.split("-")[0].trim(), - hash: key.split("-")[1].trim(), - link: value.replaceAll('"', ""), - }; - localStorageData.push(x); + if (key !== null && key?.includes(address)) { + const value = localStorage.getItem(key) + if (value !== null) { + const x = { + address: key.split('-')[0].trim(), + hash: key.split('-')[1].trim(), + link: value.replaceAll('"', ''), + } + localStorageData.push(x) + } + } } - } + return localStorageData + } catch (error) { + console.error('Error getting data from localStorage:', error) } - return localStorageData; - } catch (error) { - console.error("Error getting data from localStorage:", error); - } -}; +} -export function formatAmountWithDecimals({ - amount, - decimals, -}: { - amount: number; - decimals: number; -}) { - const divider = 10 ** decimals; - const formattedAmount = amount / divider; - return formattedAmount; +export function formatAmountWithDecimals({ amount, decimals }: { amount: number; decimals: number }) { + const divider = 10 ** decimals + const formattedAmount = amount / divider + return formattedAmount } export function formatAmount(amount: number) { - return amount.toFixed(2); + return amount.toFixed(2) } export function formatTokenAmount(amount: number) { - const formattedAmount = amount.toLocaleString("en-US", { - minimumFractionDigits: 0, - maximumFractionDigits: 4, - }); - return formattedAmount; + const formattedAmount = amount.toLocaleString('en-US', { + minimumFractionDigits: 0, + maximumFractionDigits: 4, + }) + return formattedAmount } diff --git a/src/utils/index.ts b/src/utils/index.ts index 1a0690ff0..4843de62d 100644 --- a/src/utils/index.ts +++ b/src/utils/index.ts @@ -1 +1 @@ -export * from "./general.utils"; +export * from './general.utils' diff --git a/tailwind.config.js b/tailwind.config.js index 5ec68abe0..e73c959f1 100644 --- a/tailwind.config.js +++ b/tailwind.config.js @@ -1,78 +1,78 @@ -const colors = require("tailwindcss/colors"); +const colors = require('tailwindcss/colors') /** @type {import('tailwindcss').Config} */ module.exports = { - corePlugins: { - preflight: false, - }, - - content: [ - "./src/pages/**/*.{js,ts,jsx,tsx,mdx}", - "./src/components/**/*.{js,ts,jsx,tsx,mdx}", - "./src/app/**/*.{js,ts,jsx,tsx,mdx}", - ], - theme: { - extend: { - animation: { - wiggle: "wiggle 1s ease-in-out infinite", - "spin-slow": "spin 3s linear infinite", - }, - minWidth: { - 25: "25px", - 50: "50px", - 75: "75px", - }, + corePlugins: { + preflight: false, }, - colors: { - transparent: "transparent", - current: "currentColor", - black: colors.black, - white: colors.white, - fuchsia: "#FF90E8", - yellow: "#F1F333", - teal: "#23A094", - lightblue: "#90A8ED", - red: "#E2442F", - orange: "#FFC900", - gray: { - 50: "#f9fafb", - 100: "#f3f4f6", - 200: "#e5e7eb", - 300: "#d1d5db", - 400: "#9ca3af", - 500: "#6b7280", - 600: "#4b5563", - 700: "#374151", - 800: "#1f2937", - 900: "#111827", - }, - orange: { - 50: "#fff8f1", - 100: "#feecdc", - 200: "#fcd9bd", - 300: "#fdba8c", - 400: "#ff8a4c", - 500: "#ff5a1f", - 600: "#d03801", - 700: "#b43403", - 800: "#8a2c0d", - 900: "#771d1d", - }, - green: { - 50: "#f3faf7", - 100: "#def7ec", - 200: "#bcf0da", - 300: "#84e1bc", - 400: "#31c48d", - 500: "#0e9f6e", - 600: "#057a55", - 700: "#046c4e", - 800: "#03543f", - 900: "#014737", - }, + content: [ + './src/pages/**/*.{js,ts,jsx,tsx,mdx}', + './src/components/**/*.{js,ts,jsx,tsx,mdx}', + './src/app/**/*.{js,ts,jsx,tsx,mdx}', + ], + theme: { + extend: { + animation: { + wiggle: 'wiggle 1s ease-in-out infinite', + 'spin-slow': 'spin 3s linear infinite', + }, + minWidth: { + 25: '25px', + 50: '50px', + 75: '75px', + }, + }, + colors: { + transparent: 'transparent', + current: 'currentColor', + black: colors.black, + white: colors.white, + fuchsia: '#FF90E8', + yellow: '#F1F333', + teal: '#23A094', + lightblue: '#90A8ED', + red: '#E2442F', + orange: '#FFC900', + gray: { + 50: '#f9fafb', + 100: '#f3f4f6', + 200: '#e5e7eb', + 300: '#d1d5db', + 400: '#9ca3af', + 500: '#6b7280', + 600: '#4b5563', + 700: '#374151', + 800: '#1f2937', + 900: '#111827', + }, + + orange: { + 50: '#fff8f1', + 100: '#feecdc', + 200: '#fcd9bd', + 300: '#fdba8c', + 400: '#ff8a4c', + 500: '#ff5a1f', + 600: '#d03801', + 700: '#b43403', + 800: '#8a2c0d', + 900: '#771d1d', + }, + green: { + 50: '#f3faf7', + 100: '#def7ec', + 200: '#bcf0da', + 300: '#84e1bc', + 400: '#31c48d', + 500: '#0e9f6e', + 600: '#057a55', + 700: '#046c4e', + 800: '#03543f', + 900: '#014737', + }, + }, }, - }, - plugins: [], -}; + plugins: [], +} diff --git a/tsconfig.json b/tsconfig.json index 0c7555fa7..9557b813f 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,28 +1,28 @@ { - "compilerOptions": { - "target": "es5", - "lib": ["dom", "dom.iterable", "esnext"], - "allowJs": true, - "skipLibCheck": true, - "strict": true, - "forceConsistentCasingInFileNames": true, - "noEmit": true, - "esModuleInterop": true, - "module": "esnext", - "moduleResolution": "node", - "resolveJsonModule": true, - "isolatedModules": true, - "jsx": "preserve", - "incremental": true, - "plugins": [ - { - "name": "next" - } - ], - "paths": { - "@/*": ["./src/*"] - } - }, - "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], - "exclude": ["node_modules"] + "compilerOptions": { + "target": "es5", + "lib": ["dom", "dom.iterable", "esnext"], + "allowJs": true, + "skipLibCheck": true, + "strict": true, + "forceConsistentCasingInFileNames": true, + "noEmit": true, + "esModuleInterop": true, + "module": "esnext", + "moduleResolution": "node", + "resolveJsonModule": true, + "isolatedModules": true, + "jsx": "preserve", + "incremental": true, + "plugins": [ + { + "name": "next" + } + ], + "paths": { + "@/*": ["./src/*"] + } + }, + "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], + "exclude": ["node_modules"] }