diff --git a/components/Popup.tsx b/components/Popup.tsx new file mode 100644 index 00000000..5f0da3b9 --- /dev/null +++ b/components/Popup.tsx @@ -0,0 +1,83 @@ +import styles from "./popup.module.css" +import { + Modal, + ModalOverlay, + ModalContent, + useDisclosure, +} from '@chakra-ui/react' +import React, { + forwardRef, + useImperativeHandle, + useState, +} from 'react' + +const infoType = { + sushi: '/images/popup/sushi.webp', + stamina: '/images/popup/stamina.webp', + fish: '/images/popup/fish.webp', + ore: '/images/popup/ore.webp', + other: '/images/popup/other.webp', + success: '/images/popup/success.webp', + failed: '/images/popup/failed.webp', + cancel: '/images/popup/cancel.webp', + waiting: '/images/popup/waiting.webp', +} + +export type PopupRef = { + isOpen: boolean + open: () => void + close: () => void + popup: (type, content, subcontent?, actionContent?, action?) => void +} + +function Popup(_, ref) { + const { isOpen, onOpen, onClose } = useDisclosure() + const [info, setInfo] = useState({ + type: '', + content: '', + subcontent: '', + actionContent: 'Close', + action: onClose + }) + + useImperativeHandle(ref, () => ({ + isOpen: isOpen, + open: onOpen, + close: onClose, + popup(type, content, subcontent = '', actionContent = 'Close', action = onClose){ + setInfo({ + type, + content, + subcontent, + actionContent, + action + }) + } + }), [onClose]) + + return ( + + + +
+
+
+
+
NOTI
+ +
+ {info.type && } +
{info.content}
+ {info.subcontent &&
({info.subcontent})
} + +
+
+
+
+
+ ) +} + +export default forwardRef(Popup) \ No newline at end of file diff --git a/components/Shop/ConfirmationModal.tsx b/components/Shop/ConfirmationModal.tsx index d7269533..c8827d01 100644 --- a/components/Shop/ConfirmationModal.tsx +++ b/components/Shop/ConfirmationModal.tsx @@ -16,6 +16,7 @@ import { ModalOverlay, } from '@chakra-ui/react' import LoadingModal from '@components/LoadingModal' +import Popup, { PopupRef } from '@components/Popup' import Button from '@components/theme/components/Button' import { utils } from 'ethers' import useTransactionState, { @@ -28,6 +29,7 @@ import { useState, useCallback, useEffect, + useRef, } from 'react' import { buyFirstHammer, getHammerPrice } from 'utils/Item' import Price from './Price' @@ -43,6 +45,7 @@ function ConfirmationModal(_, ref) { const [buyAmount, setBuyAmount] = useState(1) const [loading, setLoading] = useState(false) const handleTxStateChange = useTransactionState() + const popupRef = useRef() useEffect(() => { ;(async () => { @@ -67,7 +70,11 @@ function ConfirmationModal(_, ref) { const handleConfirm = useCallback(async () => { setLoading(true) await buyFirstHammer((hash) => { - handleTxStateChange('Buy first hammer', hash, TRANSACTION_STATE.WAITING) + handleTxStateChange('Buy first hammer', hash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) setLoading(false) onToggle() @@ -148,6 +155,7 @@ function ConfirmationModal(_, ref) { + ) } diff --git a/components/marketplace/DashBoard.tsx b/components/marketplace/DashBoard.tsx index 6e6ad1c1..37d3480f 100644 --- a/components/marketplace/DashBoard.tsx +++ b/components/marketplace/DashBoard.tsx @@ -1,11 +1,12 @@ import Link from 'next/link' -import { useEffect, useMemo, useState } from 'react' +import { useEffect, useMemo, useRef, useState } from 'react' import { listMultiItems } from 'utils/NFTMarket' import styles from './dashboard.module.css' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' import { getHeroes, listingHero } from 'utils/HeroMarketUtils' +import Popup, { PopupRef } from '@components/Popup' const numOfPage = 8 @@ -17,6 +18,7 @@ export default function DashBoard() { const [priceInput, setPriceInput] = useState(null) const [status, setStatus] = useState('Loading ...') const handleTxStateChange = useTransactionState() + const popupRef = useRef() const getHeroesData = async () => { const result = await getHeroes() @@ -37,17 +39,29 @@ export default function DashBoard() { selected.id, Number(priceInput), (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } ) if (result) { setDataInit([]) await getHeroesData() - handleTxStateChange(title, result.transactionHash, result.status) + handleTxStateChange(title, result.transactionHash, result.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { setData(dataInit) setStatus('Loading ...') - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } const renderData = useMemo(() => { @@ -164,6 +178,7 @@ export default function DashBoard() { /> + ) } diff --git a/components/marketplace/History.tsx b/components/marketplace/History.tsx index 87a5daea..5904c83b 100644 --- a/components/marketplace/History.tsx +++ b/components/marketplace/History.tsx @@ -1,10 +1,11 @@ import Link from 'next/link' -import { useEffect, useState } from 'react' +import { useEffect, useRef, useState } from 'react' import { cancelListingItem, getListingIDsBySeller, getNumberOfItemListings } from 'utils/NFTMarket' import styles from './history.module.css' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import Popup, { PopupRef } from '@components/Popup' const numOfPage = 4 @@ -16,6 +17,7 @@ export default function History() { const [status, setStatus] = useState('Loading ...') const [isOpenNotify, setIsOpenNotify] = useState(null) const handleTxStateChange = useTransactionState() + const popupRef = useRef() useEffect(() => { getItems() @@ -36,7 +38,11 @@ export default function History() { const result = await cancelListingItem( id, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }, ) if (result) { @@ -151,6 +157,7 @@ export default function History() { img + } diff --git a/components/marketplace/Market.tsx b/components/marketplace/Market.tsx index dc077a45..709105ad 100644 --- a/components/marketplace/Market.tsx +++ b/components/marketplace/Market.tsx @@ -1,5 +1,5 @@ import Link from 'next/link' -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import styles from './market.module.css' import useTransactionState, { TRANSACTION_STATE, @@ -12,6 +12,7 @@ import { getListingIDs, purchaseHero, } from 'utils/HeroMarketUtils' +import Popup, { PopupRef } from '@components/Popup' const numOfPage = 12 @@ -24,6 +25,7 @@ function Market() { const [data, setData] = useState([]) const [loading, setLoading] = useState(false) const handleTxStateChange = useTransactionState() + const popupRef = useRef() useEffect(() => { getItems() @@ -43,11 +45,14 @@ function Market() { const handlePurchase = async (value) => { const title = 'Purchase item' - const result = await purchaseHero( parseInt(value?.id), (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }, async (_) => { setData(dataInit) @@ -55,22 +60,42 @@ function Market() { ) if (result) { await getItems() - handleTxStateChange(title, result.transactionHash, result.status) + handleTxStateChange(title, result.transactionHash, result.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } const handleCancel = async (value) => { const title = 'Cancel listing item' const result = await cancelListingItem(value?.id, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (result) { await getItems() - handleTxStateChange(title, result.transactionHash, result.status) + handleTxStateChange(title, result.transactionHash, result.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } @@ -235,6 +260,7 @@ function Market() { img + ) } diff --git a/components/popup.module.css b/components/popup.module.css new file mode 100644 index 00000000..5044ca0c --- /dev/null +++ b/components/popup.module.css @@ -0,0 +1,104 @@ + +.modal { + position: fixed; /* Stay in place */ + z-index: 1000000; /* Sit on top */ + left: 0; + top: 0; + width: 100vw; /* Full width */ + height: 100vh; /* Full height */ + background-color: rgb(0,0,0); /* Fallback color */ + background-color: rgba(0,0,0,0.8); /* Black w/ opacity */ + display: flex; + align-items: center; + justify-content: center; +} + +/* Modal Content/Box */ +.background3 { + padding: 2px; + flex: 1; + max-width: 600px; + height: fit-content; + background-image: url('/images/popup/background-3.webp'); + background-size: 100% 100%; + background-repeat: no-repeat; + background-color: transparent; +} + +.background2{ + background-image: url('/images/popup/background-2.webp'); + background-size: 100% 100%; + background-repeat: no-repeat; + height: 100%; + width: 100%; + padding: 10px; +} + +.background1{ + background-image: url('/images/popup/background.webp'); + background-size: 100% 100%; + background-repeat: no-repeat; + height: 100%; + width: 100%; + text-align: center; + padding: 15px 20px; +} + +.background1 > div:first-child{ + display: flex; + justify-content: space-between; +} + +.background1 > div:first-child > img{ + width: 22px; + height: 22px; +} + +.background1 > div:first-child > div{ + color: #472805; + font-size: 24px; + font-weight: 800; +} + +.background1 > img{ + display: block; + margin: auto; + margin-top: 20px; +} + +.background1 > div:nth-child(3){ + font-family: cursive; + color: #592203; + font-size: 22px; + padding: 16px; +} + +.background1 > div:nth-child(4){ + font-family: "Gill Sans", sans-serif; + color: #c74f0c; + font-size: 16px; +} + +.background1 > div:nth-child(4) a svg{ + margin-top: -5px; +} + +.background1 > button.invalid{ + font-family: system-ui; + background-color: #bcbcbc; + color: #838383; + padding: 6px 25px; + border-radius: 10px; + font-weight: 500; + margin: 20px 0; +} + +.background1 > button{ + font-family: system-ui; + background-color: #472805; + color: #f0e0d0; + padding: 5px 20px; + border-radius: 10px; + font-weight: 500; + margin: 20px 0; +} \ No newline at end of file diff --git a/components/professions/Inventory/index.tsx b/components/professions/Inventory/index.tsx index 348623db..9d50003d 100644 --- a/components/professions/Inventory/index.tsx +++ b/components/professions/Inventory/index.tsx @@ -3,6 +3,7 @@ import React, { useCallback, useEffect, useImperativeHandle, + useRef, useState, } from 'react' import styled from '@emotion/styled' @@ -22,6 +23,7 @@ import { useDisclosure, } from '@chakra-ui/react' import ItemGrid from './ItemGrid' +import Popup, { PopupRef } from '@components/Popup' type Item = { type: 'sushi' | 'ore' | 'hammer' | 'fish' @@ -41,6 +43,8 @@ function Inventory(_, ref) { const [isOpenNotify, setIsOpenNotify] = useState(null) const [data, setData] = useState(null) const handleTxStateChange = useTransactionState() + const popupRef = useRef() + useImperativeHandle( ref, @@ -68,14 +72,26 @@ function Inventory(_, ref) { selectedItem?.ids?.slice(0, Number(amountItems)), price, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } ) if (result) { - handleTxStateChange(title, result.transactionHash, result.status) + handleTxStateChange(title, result.transactionHash, result.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } getItemsIndex() @@ -250,6 +266,7 @@ function Inventory(_, ref) { + ) } diff --git a/components/professions/ProfessionsModal.tsx b/components/professions/ProfessionsModal.tsx index 5a44c49b..f5299321 100644 --- a/components/professions/ProfessionsModal.tsx +++ b/components/professions/ProfessionsModal.tsx @@ -2,7 +2,7 @@ import { Button, Grid, GridItem } from '@chakra-ui/react' import mainStyle from './professions.module.css' import inheritStyle from './professionsSelection.module.css' import style from './professionsModal.module.css' -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import { fetchRequireBalanceProfession, fetchUserProfessionNFT, @@ -14,6 +14,7 @@ import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' import { ethers } from 'ethers' +import Popup, { PopupRef } from '@components/Popup' const NPCList = ['openian', 'supplier', 'blacksmith'] @@ -58,6 +59,7 @@ function ProfessionsModal(props: Props) { const [requireBalance, setRequireBalance] = useState([]) const [isLoading, setIsLoading] = useState(false) const handleTxStateChange = useTransactionState() + const popupRef = useRef() const onActivateProfession = useCallback(async () => { const title = 'Activate career' @@ -74,15 +76,27 @@ function ProfessionsModal(props: Props) { professionNft, hero.heroId, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } ) if (data) { getResult(data.status) - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } setIsLoading(false) @@ -209,6 +223,7 @@ function ProfessionsModal(props: Props) { onClick={closeModal} /> + ) } diff --git a/components/professions/blacksmith/forgehammer/ForgeHammer.tsx b/components/professions/blacksmith/forgehammer/ForgeHammer.tsx index 0d595a7e..21e0ffac 100644 --- a/components/professions/blacksmith/forgehammer/ForgeHammer.tsx +++ b/components/professions/blacksmith/forgehammer/ForgeHammer.tsx @@ -1,12 +1,13 @@ import { Button } from '@chakra-ui/button' import style from './forgeHammer.module.css' -import { useCallback, useEffect, useMemo, useState } from 'react' +import { useCallback, useEffect, useMemo, useRef, useState } from 'react' import NotificationForge from './NotificationForge' import ResultForgeHammer from './ResultForgeHammer' import { fetchAmountItemByTrait, makeHammer } from 'utils/blackSmithContract' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import Popup, { PopupRef } from '@components/Popup' type Props = { toggleModal: (boolean) => void @@ -23,6 +24,7 @@ export default function ForgeHammer(props: Props) { const [isStartQuestFail, setIsStartQuestFail] = useState(false) const [checkIsSuccess, setCheckIsSuccess] = useState(false) const handleTxStateChange = useTransactionState() + const popupRef = useRef() const numberOreNeed = useMemo(() => numberHammer / 2, [numberHammer]) @@ -51,19 +53,28 @@ export default function ForgeHammer(props: Props) { if (numberOreNeed <= numberYourOre.length && numberHammer !== 0) { const listSellHammer = numberYourOre.slice(0, numberOreNeed) const forgeHammer = await makeHammer(listSellHammer, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (forgeHammer) { setCheckIsSuccess(forgeHammer) setIsStartQuest(true) - handleTxStateChange( - title, - forgeHammer.transactionHash, - forgeHammer.status - ) + handleTxStateChange(title, forgeHammer.transactionHash, forgeHammer.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) + getListYourOre() } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } toggleLoadingModal(false) @@ -174,6 +185,7 @@ export default function ForgeHammer(props: Props) { {isStartQuestFail && ( )} + ) } diff --git a/components/professions/openian/fishingModal/FishingModal.tsx b/components/professions/openian/fishingModal/FishingModal.tsx index 6a75c4b1..d8f9453a 100644 --- a/components/professions/openian/fishingModal/FishingModal.tsx +++ b/components/professions/openian/fishingModal/FishingModal.tsx @@ -1,6 +1,6 @@ -import { Button, useToast } from '@chakra-ui/react' +import { Button } from '@chakra-ui/react' import { FontAwesomeIcon } from '@fortawesome/react-fontawesome' -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import { getFishingQuest, fetchFishingQuestData, @@ -17,6 +17,8 @@ import { addHours, millisecondsToHours, fromUnixTime, intervalToDuration, isBefo import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import Popup, { PopupRef } from '@components/Popup' +import { useRouter } from 'next/router' type Props = { isOpen: boolean @@ -36,12 +38,13 @@ function FishingModal(props: Props) { const [typeofModal, setTypeOfModal] = useState(TYPE_OF_MODAL.START) const [requireStamina, setRequireStamina] = useState(0) const [duration, setDuration] = useState(10) + const router = useRouter() const [canFinish, setCanFinish] = useState(false) const [timeLeft, setTimeLeft] = useState(null) const [loading, setLoading] = useState(true) - const toast = useToast() const handleTxStateChange = useTransactionState() + const popupRef = useRef() const initialize = useCallback(async () => { setLoading(true) @@ -81,19 +84,18 @@ function FishingModal(props: Props) { const checkRequirementBeforeStartQuest = useCallback(async () => { const stamina = await getStamina() const data = await fetchFishingQuestData() - if (Number(stamina) < data.requireStamina) { - toast({ - title: 'Fishing Quest', - description: `Fishing quest requires at least ${data.requireStamina} stamina to start. You don't have enough stamina to start fishing quest.`, - status: 'error', - duration: 15000, - isClosable: true, - }) + popupRef.current.open() + popupRef.current.popup( + 'stamina', + 'Fishing Quest', + `Fishing quest requires at least ${data.requireStamina} stamina to start. You don't have enough stamina to start fishing quest.`, + 'Bye Sushi', + () => { router.push('foodcourt') } + ) } - return Number(stamina) >= data.requireStamina - }, [toast]) + }, [popupRef]) const handleStartQuest = useCallback(async () => { const title = 'Start fishing quest' @@ -111,7 +113,11 @@ function FishingModal(props: Props) { toggleLoadingModal(true) const fishing = await startFishing((txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) setTimeout(() => { toggleLoadingModal(false) @@ -119,10 +125,18 @@ function FishingModal(props: Props) { if (fishing !== null) { setTypeOfModal(TYPE_OF_MODAL.WAITING) setCanFinish(false) - handleTxStateChange(title, fishing.transactionHash, fishing.status) + handleTxStateChange(title, fishing.transactionHash, fishing.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { toggleLoadingModal(false) - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } }, [checkRequirementBeforeStartQuest, toggleLoadingModal]) @@ -131,14 +145,26 @@ function FishingModal(props: Props) { if (canFinish) { toggleLoadingModal(true) const finish = await finishFishing((txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (finish) { - handleTxStateChange(title, finish.transactionHash, finish.status) + handleTxStateChange(title, finish.transactionHash, finish.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) updateInventory() setTypeOfModal(TYPE_OF_MODAL.FINISH) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } toggleLoadingModal(false) } @@ -228,6 +254,7 @@ function FishingModal(props: Props) {
+ ) } diff --git a/components/professions/openian/miningModal/MiningModal.tsx b/components/professions/openian/miningModal/MiningModal.tsx index 670adc6e..23eca474 100644 --- a/components/professions/openian/miningModal/MiningModal.tsx +++ b/components/professions/openian/miningModal/MiningModal.tsx @@ -1,6 +1,6 @@ -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import style from './Mining.module.css' -import { Button, useToast } from '@chakra-ui/react' +import { Button } from '@chakra-ui/react' import ResultMining from './ResultMining' import MiningWait from './MiningWait' @@ -18,6 +18,8 @@ import { getStamina } from 'utils/profileContract' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import { useRouter } from 'next/router' +import Popup, { PopupRef } from '@components/Popup' type Props = { isOpen: boolean @@ -38,7 +40,8 @@ export default function MiningModal(props: Props) { intervalToDuration({ start: 0, end: 0 }) ) const handleTxStateChange = useTransactionState() - const toast = useToast() + const router = useRouter() + const popupRef = useRef() const initialize = useCallback(async () => { toggleLoadingModal(true) @@ -77,30 +80,31 @@ export default function MiningModal(props: Props) { const stamina = await getStamina() if (Number(stamina) < data.requireStamina) { - toast({ - title: 'Mining Quest', - description: `Mining quest requires at least ${data.requireStamina} stamina to start. You don't have enough stamina to start mining quest.`, - status: 'error', - duration: 15000, - isClosable: true, - }) + popupRef.current.open() + popupRef.current.popup( + 'stamina', + 'Mining Quest', + `Mining quest requires at least ${data.requireStamina} stamina to start. You don't have enough stamina to start mining quest.`, + 'Bye Sushi', + () => { router.push('professions') } + ) return false } const hammerList = await fetchAmountItemByTrait(3) if (hammerList?.length < 1) { - toast({ - title: 'Mining Quest', - description: "You don't have enough hammer to start mining quest", - status: 'error', - duration: 15000, - isClosable: true, - }) + popupRef.current.open() + popupRef.current.popup( + 'stamina', + 'Mining Quest', + 'You don\'t have enough hammer to start mining quest', + 'Bye hammer', + () => { router.push('professions') } + ) return false } - return true - }, [toast]) + }, [popupRef]) const startQuest = useCallback(async () => { try { @@ -113,17 +117,29 @@ export default function MiningModal(props: Props) { toggleLoadingModal(true) const mining = await startMining((txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (mining) { - handleTxStateChange(title, mining.transactionHash, mining.status) + handleTxStateChange(title, mining.transactionHash, mining.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) const data = await getMiningQuest() setIsFinished(data.finish) setIsStartQuest(false) setCanFinish(false) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } catch (e) { } finally { @@ -139,17 +155,29 @@ export default function MiningModal(props: Props) { const title = 'Finish mining quest' toggleLoadingModal(true) const finish = await finishMining((txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (finish) { - handleTxStateChange(title, finish.transactionHash, finish.status) + handleTxStateChange(title, finish.transactionHash, finish.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) updateInventory() setIsStartQuest(false) setIsFinished(true) // setTimeLeft(duration) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } toggleLoadingModal(false) }, []) @@ -191,6 +219,7 @@ export default function MiningModal(props: Props) { ) : ( )} + ) } diff --git a/components/professions/openian/sellModal/SellBoard.tsx b/components/professions/openian/sellModal/SellBoard.tsx index 434bbe31..80450991 100644 --- a/components/professions/openian/sellModal/SellBoard.tsx +++ b/components/professions/openian/sellModal/SellBoard.tsx @@ -12,6 +12,7 @@ import { listMultiItems } from 'utils/NFTMarket' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import Popup, { PopupRef } from '@components/Popup' type Props = { selectedItem: number @@ -31,6 +32,7 @@ function SellBoard(props: Props) { const [isLoading, setIsLoading] = useState(false) const [listingResult, setListingResult] = useState(undefined) const handleTxStateChange = useTransactionState() + const popupRef = useRef() const fetchSelectedItemAmount = async () => { const itemAmount = await fetchUserInventoryItemAmount() @@ -129,15 +131,27 @@ function SellBoard(props: Props) { const itemSellIds = selectedItemIds.slice(0, sellingAmount) const result = await listMultiItems(itemSellIds, price, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (result !== null) { handleFinishListing() setListingResult(true) - handleTxStateChange(title, result.transactionHash, result.status) + handleTxStateChange(title, result.transactionHash, result.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { setListingResult(false) - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } priceRef.current.value = '0' setPrice(0) @@ -255,6 +269,7 @@ function SellBoard(props: Props) { + ) } diff --git a/components/workshop/LayoutShop.tsx b/components/workshop/LayoutShop.tsx index 66d5fb28..635dc67d 100644 --- a/components/workshop/LayoutShop.tsx +++ b/components/workshop/LayoutShop.tsx @@ -52,6 +52,7 @@ import { PopoverHeader, PopoverBody, } from '@chakra-ui/react' +import Popup, { PopupRef } from '@components/Popup' type Props = { isPage: string @@ -75,6 +76,7 @@ export default function LayoutShop(props: Props) { const inventoryRef = useRef() const initRef = useRef() const handleTxStateChange = useTransactionState() + const popupRef = useRef() const handleGetOreOrSushiList = async () => { const data = await getListingIDs(false) @@ -153,15 +155,27 @@ export default function LayoutShop(props: Props) { setIsLoading(true) const title = isPage === 'workshop' ? `Cancel listing item in Workshop` : `Cancel listing item in Food Court` const data = await cancelListingItem(item?.id, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) setIsLoading(false) }) if (data) { - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) handleGetMyList() setIsLoading(false) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) setIsLoading(false) } }, @@ -201,15 +215,27 @@ export default function LayoutShop(props: Props) { id, listIds, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }, (error) => { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) setIsLoading(false) } ) if (data) { - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) setIsLoading(false) if (isItemBoard === 'ore' || isItemBoard === 'sushi') { handleGetOreOrSushiList() @@ -219,7 +245,11 @@ export default function LayoutShop(props: Props) { return data } else { setIsLoading(false) - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } }, [isItemBoard] @@ -550,6 +580,7 @@ export default function LayoutShop(props: Props) { /> + ) } diff --git a/components/worldmap/CreateProfile.tsx b/components/worldmap/CreateProfile.tsx index cdd4784d..d87b9e44 100644 --- a/components/worldmap/CreateProfile.tsx +++ b/components/worldmap/CreateProfile.tsx @@ -1,4 +1,4 @@ -import { useCallback, useMemo, useState } from 'react' +import { useCallback, useMemo, useRef, useState } from 'react' import styled from '@emotion/styled' import { useRouter } from 'next/router' import { @@ -10,6 +10,7 @@ import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' import LoadingModal from '@components/LoadingModal' +import Popup, { PopupRef } from '@components/Popup' const imagesIndex = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13] @@ -29,6 +30,7 @@ function CreateProfile({ const [isLoading, setIsLoading] = useState(false) const router = useRouter() const handleTxStateChange = useTransactionState() + const popupRef = useRef() // const dispatch = useDispatch() @@ -63,7 +65,11 @@ function CreateProfile({ : 'Create profile' const status = data.status ? 1 : 0 - handleTxStateChange(title, data.transactionHash, status) + handleTxStateChange(title, data.transactionHash, status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }, [handleTxStateChange, heroSelector, isEdit, profile?._picId] ) @@ -75,7 +81,11 @@ function CreateProfile({ ? 'Update profile' : 'Create profile' - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }, [handleTxStateChange, heroSelector, isEdit, profile?._picId] ) @@ -94,10 +104,11 @@ function CreateProfile({ router.push('/') getDataProfile() } else { - handleTxStateChange( - 'Update profile', - '', - TRANSACTION_STATE.NOT_EXECUTED + handleTxStateChange('Update profile', '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + } ) } setIsOpenCreateProfile(false) @@ -123,10 +134,11 @@ function CreateProfile({ getDataProfile() handleOpenTutorial(true) } else { - handleTxStateChange( - 'Create profile', - '', - TRANSACTION_STATE.NOT_EXECUTED + handleTxStateChange('Create profile', '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + } ) } @@ -221,6 +233,7 @@ function CreateProfile({ + ) } diff --git a/components/worldmap/RefillStaminaModal.tsx b/components/worldmap/RefillStaminaModal.tsx index bc3ab830..08e17fea 100644 --- a/components/worldmap/RefillStaminaModal.tsx +++ b/components/worldmap/RefillStaminaModal.tsx @@ -1,4 +1,4 @@ -import React, { useCallback, useState } from 'react' +import React, { useCallback, useRef, useState } from 'react' import { Button, Center, @@ -17,7 +17,6 @@ import { Wrap, WrapItem, Text, - useToast, Link, useDisclosure, } from '@chakra-ui/react' @@ -25,6 +24,8 @@ import { fetchAmountItemByTrait } from 'utils/blackSmithContract' import { refillStamina } from 'utils/professionContract' import { ExternalLinkIcon } from '@chakra-ui/icons' import LoadingModal from '@components/LoadingModal' +import { useRouter } from 'next/router' +import Popup, { PopupRef } from '@components/Popup' type Props = { isOpen: boolean @@ -41,7 +42,8 @@ function RefillStaminaModal(props: Props) { } = useDisclosure() const [amountSushi, setAmountSushi] = useState(0) const [success, setSuccess] = useState(false) - const toast = useToast() + const router = useRouter() + const popupRef = useRef() const handleUseSushi = useCallback(async () => { if (success) { @@ -53,13 +55,14 @@ function RefillStaminaModal(props: Props) { onToggleLoading() const availableSushi = await fetchAmountItemByTrait(4) if (availableSushi?.length < amountSushi) { - toast({ - title: 'Recover stamina', - description: 'Not enough sushi to recover stamina', - duration: 10000, - isClosable: true, - status: 'warning', - }) + popupRef.current.open() + popupRef.current.popup( + 'sushi', + 'Not enough Sushi to recover stamina', + 'Make Sushi or buy on maket', + 'Bye Sushi', + () => { router.push('foodcourt') } + ) onClose() return } @@ -67,20 +70,17 @@ function RefillStaminaModal(props: Props) { await refillStamina( availableSushi?.slice(0, amountSushi).map((v) => `${v}`), (txHash) => { - toast({ - title: 'Recover stamina transaction is executing', - description: ( - - Transaction detail - - ), - duration: 10000, - isClosable: true, - status: 'info', - }) + popupRef.current.open() + popupRef.current.popup( + 'stamina', + 'Recover stamina transaction is executing', + + Transaction detail + + ) } ) onSuccess() @@ -89,7 +89,7 @@ function RefillStaminaModal(props: Props) { } finally { onClose() } - }, [amountSushi, onClose, onSuccess, onToggleLoading, success, toast]) + }, [amountSushi, onClose, onSuccess, onToggleLoading, success, popupRef]) const handleChangeAmountSushi = useCallback((_: string, value: number) => { setAmountSushi(value) @@ -210,6 +210,7 @@ function RefillStaminaModal(props: Props) { + ) } diff --git a/hooks/useTransactionState.tsx b/hooks/useTransactionState.tsx index bb2f5e40..9a6ffc89 100644 --- a/hooks/useTransactionState.tsx +++ b/hooks/useTransactionState.tsx @@ -1,6 +1,6 @@ import { useCallback, useMemo } from 'react' -import { useToast } from '@chakra-ui/react' import { ExternalLinkIcon } from '@chakra-ui/icons' +import Popup from '@components/Popup' export enum TRANSACTION_STATE { FAILED = 0, @@ -10,8 +10,6 @@ export enum TRANSACTION_STATE { } function useTransactionState() { - const toast = useToast() - const blockExplorer = useMemo(() => { const chainId = window?.ethereum?.chainId switch (chainId) { @@ -36,72 +34,55 @@ function useTransactionState() { }, []) const handleTxStateChange = useCallback( - (title, txHash, txResult: TRANSACTION_STATE) => { - toast.closeAll() + (title, txHash, txResult: TRANSACTION_STATE, handlePopup) => { switch (txResult) { case TRANSACTION_STATE.FAILED: - return toast({ - title: title + ' transaction is failed', - description: ( - - Transaction detail - - ), - duration: 3000, - isClosable: true, - status: 'error', - }) + handlePopup( + "failed", + title + ' transaction is failed', + + ) + return null case TRANSACTION_STATE.SUCCESSFUL: - return toast({ - title: title + ' transaction is successful', - description: ( - - Transaction detail - - ), - duration: 3000, - isClosable: true, - status: 'success', - }) - + handlePopup( + 'success', + title + ' transaction is successful', + + Transaction detail + + ) + return null case TRANSACTION_STATE.WAITING: - return toast({ - title: title + ' transaction is excuting', - duration: 3000, - description: ( - - Transaction detail - - ), - status: 'info', - containerStyle: { - zIndex: 999999, - }, - isClosable: true, - }) - + handlePopup( + 'waiting', + title + ' transaction is excuting', + + Transaction detail + + ) + return null case TRANSACTION_STATE.NOT_EXECUTED: - return toast({ - title: title + ' transaction is failed to execute', - duration: 3000, - isClosable: true, - status: 'error', - }) + handlePopup( + 'cancel', + title + ' transaction is failed to execute', + null + ) + return null } }, - [blockExplorer, toast] + [blockExplorer] ) return handleTxStateChange diff --git a/pages/castle/index.tsx b/pages/castle/index.tsx index e4173df6..fd42702f 100644 --- a/pages/castle/index.tsx +++ b/pages/castle/index.tsx @@ -29,6 +29,7 @@ import { import LoadingModal from '@components/LoadingModal' import { useDispatch } from 'react-redux' import { setOpenBalance } from 'reduxActions/profileAction' +import Popup, { PopupRef } from '@components/Popup' export default function Castle() { // Ref @@ -48,6 +49,7 @@ export default function Castle() { const handleTxStateChange = useTransactionState() const { onClose } = useDisclosure() const toast = useToast() + const popupRef = useRef() const [nftsAmount, setNftsAmount] = useState({ openianAmount: 0, @@ -156,22 +158,33 @@ export default function Castle() { if (balance >= NTFCardPrice) { const title = 'Purchase NFT card' const data = await mintProfessionNFT(trait, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (data) { - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) // await fetchNFTAmount() } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } else { - toast({ - title: 'Purchase NFT card transaction is failed to excute', - description: "You don't have enough OPEN to purchase", - duration: 10000, - isClosable: true, - status: 'error', - }) + popupRef.current.open() + popupRef.current.popup( + 'failed', + 'Purchase NFT card transaction is failed to excute', + 'You don\'t have enough OPEN to purchase' + ) onClose() } fetchNFTAmount() @@ -305,6 +318,7 @@ export default function Castle() { toggleLandAuction={() => setIsLandAuctionOpen(false)} key={action} /> + ) } diff --git a/pages/castle/shop/index.tsx b/pages/castle/shop/index.tsx index 3ffa4d5c..e4db0bcc 100644 --- a/pages/castle/shop/index.tsx +++ b/pages/castle/shop/index.tsx @@ -8,7 +8,7 @@ import { import style from '@components/castle/shop/shop.module.css' import Head from 'next/head' import Link from 'next/link' -import { useCallback, useEffect, useState } from 'react' +import { useCallback, useEffect, useRef, useState } from 'react' import { mintProfessionNFT, fetchProfessionsNFTAmount, @@ -18,6 +18,7 @@ import LoadingModal from '@components/LoadingModal' import useTransactionState, { TRANSACTION_STATE, } from 'hooks/useTransactionState' +import Popup, { PopupRef } from '@components/Popup' import { getOpenBalance } from 'utils/checkBalanceOpen' function Shop() { @@ -36,7 +37,7 @@ function Shop() { const [isLoading, setIsLoading] = useState(false) const handleTxStateChange = useTransactionState() const { onClose } = useDisclosure() - const toast = useToast() + const popupRef = useRef() const mintProfessionsNFT = async (trait) => { setIsLoading(true) @@ -45,22 +46,33 @@ function Shop() { if (balance >= NTFCardPrice) { const title = 'Purchase NFT card' const data = await mintProfessionNFT(trait, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (data) { - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) await fetchNFTAmount() } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } } else { - toast({ - title: 'Purchase NFT card transaction is failed to excute', - description: "You don't have enough OPEN to purchase", - duration: 10000, - isClosable: true, - status: 'error', - }) + popupRef.current.popup( + 'failed', + 'Purchase NFT card transaction is failed to excute', + "You don\'t have enough OPEN to purchase" + ) + popupRef.current.open() onClose() } setIsLoading(false) @@ -193,6 +205,7 @@ function Shop() { + ) } diff --git a/pages/foodcourt/index.tsx b/pages/foodcourt/index.tsx index 00e884de..21ca8c5e 100644 --- a/pages/foodcourt/index.tsx +++ b/pages/foodcourt/index.tsx @@ -1,7 +1,5 @@ import LayoutShop from '@components/workshop/LayoutShop' export default function FoodCourt() { - - return - -} \ No newline at end of file + return +} diff --git a/pages/professions/supplier/index.tsx b/pages/professions/supplier/index.tsx index 111011d6..1d2482ce 100644 --- a/pages/professions/supplier/index.tsx +++ b/pages/professions/supplier/index.tsx @@ -13,6 +13,7 @@ import useTransactionState, { import { useDisclosure } from '@chakra-ui/react' import Inventory, { InventoryRef } from '@components/professions/Inventory' import { TransformComponent, TransformWrapper } from 'react-zoom-pan-pinch' +import Popup, { PopupRef } from '@components/Popup' function Supplier() { const { isOpen: isOpenMakeSushi, onToggle: onToggleMakeSushi } = @@ -24,6 +25,7 @@ function Supplier() { const handleTxStateChange = useTransactionState() const inventoryRef = useRef() const [windowWidth, setWindowWidth] = useState(window.innerWidth) + const popupRef = useRef() useEffect(() => { const checkWindowWidth = () => { @@ -58,13 +60,25 @@ function Supplier() { setIsLoading(true) const data = await makeMultiSushi(listFishBurn, (txHash) => { - handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING) + handleTxStateChange(title, txHash, TRANSACTION_STATE.WAITING, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) }) if (data) { - handleTxStateChange(title, data.transactionHash, data.status) + handleTxStateChange(title, data.transactionHash, data.status, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } else { - handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED) + handleTxStateChange(title, '', TRANSACTION_STATE.NOT_EXECUTED, + (type, content, subcontent) => { + popupRef.current.open() + popupRef.current.popup(type, content, subcontent) + }) } setIsLoading(false) @@ -135,6 +149,7 @@ function Supplier() { {isLoading && } + ) } diff --git a/pages/workshop/index.tsx b/pages/workshop/index.tsx index a1ac5c56..f63f50df 100644 --- a/pages/workshop/index.tsx +++ b/pages/workshop/index.tsx @@ -1,6 +1,5 @@ import LayoutShop from "@components/workshop/LayoutShop"; export default function WorkShop() { - return } diff --git a/public/images/popup/background-2.webp b/public/images/popup/background-2.webp new file mode 100644 index 00000000..276a53b5 Binary files /dev/null and b/public/images/popup/background-2.webp differ diff --git a/public/images/popup/background-3.webp b/public/images/popup/background-3.webp new file mode 100644 index 00000000..da87c12b Binary files /dev/null and b/public/images/popup/background-3.webp differ diff --git a/public/images/popup/background.webp b/public/images/popup/background.webp new file mode 100644 index 00000000..b1d29c70 Binary files /dev/null and b/public/images/popup/background.webp differ diff --git a/public/images/popup/cancel.webp b/public/images/popup/cancel.webp new file mode 100644 index 00000000..cf5ead99 Binary files /dev/null and b/public/images/popup/cancel.webp differ diff --git a/public/images/popup/close.webp b/public/images/popup/close.webp new file mode 100644 index 00000000..b1e90144 Binary files /dev/null and b/public/images/popup/close.webp differ diff --git a/public/images/popup/failed.webp b/public/images/popup/failed.webp new file mode 100644 index 00000000..71d2d641 Binary files /dev/null and b/public/images/popup/failed.webp differ diff --git a/public/images/popup/fish.webp b/public/images/popup/fish.webp new file mode 100644 index 00000000..c421e12c Binary files /dev/null and b/public/images/popup/fish.webp differ diff --git a/public/images/popup/ore.webp b/public/images/popup/ore.webp new file mode 100644 index 00000000..dfe09873 Binary files /dev/null and b/public/images/popup/ore.webp differ diff --git a/public/images/popup/other.webp b/public/images/popup/other.webp new file mode 100644 index 00000000..35682737 Binary files /dev/null and b/public/images/popup/other.webp differ diff --git a/public/images/popup/stamina.webp b/public/images/popup/stamina.webp new file mode 100644 index 00000000..a12095d4 Binary files /dev/null and b/public/images/popup/stamina.webp differ diff --git a/public/images/popup/success.webp b/public/images/popup/success.webp new file mode 100644 index 00000000..d381b9f5 Binary files /dev/null and b/public/images/popup/success.webp differ diff --git a/public/images/popup/sushi.webp b/public/images/popup/sushi.webp new file mode 100644 index 00000000..6f9cbf01 Binary files /dev/null and b/public/images/popup/sushi.webp differ diff --git a/public/images/popup/waiting.webp b/public/images/popup/waiting.webp new file mode 100644 index 00000000..61c6f385 Binary files /dev/null and b/public/images/popup/waiting.webp differ