diff --git a/package-lock.json b/package-lock.json index 4f14235..2da836e 100644 --- a/package-lock.json +++ b/package-lock.json @@ -10,9 +10,12 @@ "dependencies": { "@react-spring/parallax": "^9.7.1", "@react-spring/web": "^9.7.1", + "chart.js": "^3.9.1", "localforage": "^1.10.0", "match-sorter": "^6.3.1", + "randomcolor": "^0.6.2", "react": "^18.2.0", + "react-chartjs-2": "^4.3.1", "react-dom": "^18.2.0", "react-icons": "^4.7.1", "react-router-dom": "^6.8.2", @@ -393,6 +396,84 @@ "node": ">=12" } }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.3.tgz", + "integrity": "sha512-HLhSWOLRi875zjjMG/r+Nv0oCW8umGb0BgEhyX3dDX3egwZtB8PqLnjz3yedt8R5StBrzcg4aBpnh8UA9D1BoQ==", + "dev": true, + "optional": true, + "peer": true, + "dependencies": { + "@jridgewell/set-array": "^1.0.1", + "@jridgewell/sourcemap-codec": "^1.4.10", + "@jridgewell/trace-mapping": "^0.3.9" + }, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.0.tgz", + "integrity": "sha512-F2msla3tad+Mfht5cJq7LSXcdudKTWCVYUgw6pLFOOHSTtZlj6SWNYAp+AhuqLmWdBO2X5hPrLcu8cVP8fy28w==", + "dev": true, + "optional": true, + "peer": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/set-array": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/set-array/-/set-array-1.1.2.tgz", + "integrity": "sha512-xnkseuNADM0gt2bs+BvhO0p78Mk762YnZdsuzFV018NoG1Sj1SCQvpSqa7XUaTam5vAGasABV9qXASMKnFMwMw==", + "dev": true, + "optional": true, + "peer": true, + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/source-map": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.3.tgz", + "integrity": "sha512-b+fsZXeLYi9fEULmfBrhxn4IrPlINf8fiNarzTof004v3lFdntdwa9PF7vFJqm3mg7s+ScJMxXaE3Acp1irZcg==", + "dev": true, + "optional": true, + "peer": true, + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.0", + "@jridgewell/trace-mapping": "^0.3.9" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.4.15", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.15.tgz", + "integrity": "sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg==", + "dev": true, + "optional": true, + "peer": true + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.18", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.18.tgz", + "integrity": "sha512-w+niJYzMHdd7USdiH2U6869nqhD2nbfZXND5Yp93qIbEmnDNk7PD48o+YchRVpzMU7M6jVCbenTR7PA1FLQ9pA==", + "dev": true, + "optional": true, + "peer": true, + "dependencies": { + "@jridgewell/resolve-uri": "3.1.0", + "@jridgewell/sourcemap-codec": "1.4.14" + } + }, + "node_modules/@jridgewell/trace-mapping/node_modules/@jridgewell/sourcemap-codec": { + "version": "1.4.14", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.4.14.tgz", + "integrity": "sha512-XPSJHWmi394fuUuzDnGz1wiKqWfo1yXecHQMRf2l6hztTO+nPru658AyDngaBe7isIxEkRsPR3FZh+s7iVa4Uw==", + "dev": true, + "optional": true, + "peer": true + }, "node_modules/@nodelib/fs.scandir": { "version": "2.1.5", "resolved": "https://registry.npmjs.org/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", @@ -708,6 +789,14 @@ "node": "^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7" } }, + "node_modules/buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true, + "optional": true, + "peer": true + }, "node_modules/camelcase-css": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/camelcase-css/-/camelcase-css-2.0.1.tgz", @@ -733,6 +822,11 @@ } ] }, + "node_modules/chart.js": { + "version": "3.9.1", + "resolved": "https://registry.npmjs.org/chart.js/-/chart.js-3.9.1.tgz", + "integrity": "sha512-Ro2JbLmvg83gXF5F4sniaQ+lTbSv18E+TIf2cOeiH1Iqd2PGFOtem+DUufMZsCJwFE7ywPOpfXFBwRTGq7dh6w==" + }, "node_modules/chokidar": { "version": "3.5.3", "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-3.5.3.tgz", @@ -778,6 +872,14 @@ "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", "dev": true }, + "node_modules/commander": { + "version": "2.20.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", + "dev": true, + "optional": true, + "peer": true + }, "node_modules/cssesc": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/cssesc/-/cssesc-3.0.0.tgz", @@ -1369,6 +1471,11 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/randomcolor": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/randomcolor/-/randomcolor-0.6.2.tgz", + "integrity": "sha512-Mn6TbyYpFgwFuQ8KJKqf3bqqY9O1y37/0jgSK/61PUxV4QfIMv0+K2ioq8DfOjkBslcjwSzRfIDEXfzA9aCx7A==" + }, "node_modules/react": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react/-/react-18.2.0.tgz", @@ -1380,6 +1487,15 @@ "node": ">=0.10.0" } }, + "node_modules/react-chartjs-2": { + "version": "4.3.1", + "resolved": "https://registry.npmjs.org/react-chartjs-2/-/react-chartjs-2-4.3.1.tgz", + "integrity": "sha512-5i3mjP6tU7QSn0jvb8I4hudTzHJqS8l00ORJnVwI2sYu0ihpj83Lv2YzfxunfxTZkscKvZu2F2w9LkwNBhj6xA==", + "peerDependencies": { + "chart.js": "^3.5.0", + "react": "^16.8.0 || ^17.0.0 || ^18.0.0" + } + }, "node_modules/react-dom": { "version": "18.2.0", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.2.0.tgz", @@ -1540,6 +1656,17 @@ "resolved": "https://registry.npmjs.org/sort-by/-/sort-by-0.0.2.tgz", "integrity": "sha512-iOX5oHA4a0eqTMFiWrHYqv924UeRKFBLhym7iwSVG37Egg2wApgZKAjyzM9WZjMwKv6+8Zi+nIaJ7FYsO9EkoA==" }, + "node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "optional": true, + "peer": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/source-map-js": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.0.2.tgz", @@ -1549,6 +1676,18 @@ "node": ">=0.10.0" } }, + "node_modules/source-map-support": { + "version": "0.5.21", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", + "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", + "dev": true, + "optional": true, + "peer": true, + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, "node_modules/supports-preserve-symlinks-flag": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/supports-preserve-symlinks-flag/-/supports-preserve-symlinks-flag-1.0.0.tgz", @@ -1619,6 +1758,40 @@ "postcss": "^8.0.0" } }, + "node_modules/terser": { + "version": "5.16.8", + "resolved": "https://registry.npmjs.org/terser/-/terser-5.16.8.tgz", + "integrity": "sha512-QI5g1E/ef7d+PsDifb+a6nnVgC4F22Bg6T0xrBrz6iloVB4PUkkunp6V8nzoOOZJIzjWVdAGqCdlKlhLq/TbIA==", + "dev": true, + "optional": true, + "peer": true, + "dependencies": { + "@jridgewell/source-map": "^0.3.2", + "acorn": "^8.5.0", + "commander": "^2.20.0", + "source-map-support": "~0.5.20" + }, + "bin": { + "terser": "bin/terser" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/terser/node_modules/acorn": { + "version": "8.8.2", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.8.2.tgz", + "integrity": "sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw==", + "dev": true, + "optional": true, + "peer": true, + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/to-regex-range": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", diff --git a/package.json b/package.json index e759d44..20c43a5 100644 --- a/package.json +++ b/package.json @@ -11,9 +11,12 @@ "dependencies": { "@react-spring/parallax": "^9.7.1", "@react-spring/web": "^9.7.1", + "chart.js": "^3.9.1", "localforage": "^1.10.0", "match-sorter": "^6.3.1", + "randomcolor": "^0.6.2", "react": "^18.2.0", + "react-chartjs-2": "^4.3.1", "react-dom": "^18.2.0", "react-icons": "^4.7.1", "react-router-dom": "^6.8.2", diff --git a/src/index.css b/src/index.css index 2fce690..3af7e8e 100644 --- a/src/index.css +++ b/src/index.css @@ -3,20 +3,26 @@ @tailwind utilities; @keyframes slide-loop { - 0% { transform: translateX(0); } - 50% { transform: translateX(50px); } - 100% { transform: translateX(0); } + 0% { + transform: translateX(0); } - - .animate-slide-loop { - animation-name: slide-loop; - animation-duration: 3s; - animation-timing-function: linear; - animation-iteration-count: infinite; - animation-direction: alternate; + 50% { + transform: translateX(50px); + } + 100% { + transform: translateX(0); } +} + +.animate-slide-loop { + animation-name: slide-loop; + animation-duration: 3s; + animation-timing-function: linear; + animation-iteration-count: infinite; + animation-direction: alternate; +} - /* .text-container { +/* .text-container { white-space: nowrap; overflow: hidden; } @@ -27,32 +33,37 @@ transform: translateX(-10px); transition: opacity 0.3s ease-out, transform 0.3s ease-out; } */ - .back-to-top { - position: fixed; - bottom: 20px; - right: 20px; - color: #fff; - width: 60px; - height: 60px; - border-radius: 50%; - display: flex; - justify-content: center; - align-items: center; - cursor: pointer; +.back-to-top { + position: fixed; + bottom: 20px; + right: 20px; + color: #fff; + width: 60px; + height: 60px; + border-radius: 50%; + display: flex; + justify-content: center; + align-items: center; + cursor: pointer; + opacity: 0; + transition: opacity 0.4s ease-in-out; +} +.back-to-top.visible { + opacity: 1; +} + +@keyframes TopToBottom { + 0% { + transform: translate(50%, -20px); opacity: 0; - transition: opacity 0.4s ease-in-out; } - .back-to-top.visible { + 100% { + transform: translate(50%, 0); opacity: 1; } - - @keyframes TopToBottom { - 0% { - transform: translate(50%, -20px); - opacity: 0; - } - 100% { - transform: translate(50%, 0); - opacity: 1; - } - } \ No newline at end of file +} +@keyframes cursor { + 50% { + border-color: transparent; + } +} diff --git a/src/shared/components/Header.tsx b/src/shared/components/Header.tsx index 453e822..2ecff36 100644 --- a/src/shared/components/Header.tsx +++ b/src/shared/components/Header.tsx @@ -1,233 +1,223 @@ -import React, { useEffect } from 'react' -import Button from './Button' -import robotLogo from '../../assets/images/robot-logo.png' -import { BsNewspaper, BsGithub } from 'react-icons/bs' -import Whitepaper from '../../assets/Whitepaper.pdf' -type Props = {} +import React, { useEffect } from "react"; +import Button from "./Button"; +import robotLogo from "../../assets/images/robot-logo.png"; +import { BsNewspaper, BsGithub } from "react-icons/bs"; +import Whitepaper from "../../assets/Whitepaper.pdf"; +type Props = {}; const menuItems = [ - { - name: 'Home', - path: '/', - id: 'home', - }, - { - name: 'About', - path: '', - id: 'about', - }, - { - name: 'Roadmap', - path: '', - id: 'roadmap', - }, - { - name: 'Tokenomics', - path: '', - id: 'tokenomics', - }, -] + { + name: "Home", + path: "/", + id: "home", + }, + { + name: "About", + path: "", + id: "about", + }, + { + name: "Roadmap", + path: "", + id: "roadmap", + }, + { + name: "Tokenomics", + path: "", + id: "tokenomics", + }, +]; const Header = (props: Props) => { - const [isScrolled, setIsScrolled] = React.useState(false) - const [isOpenMenu, setIsOpenMenu] = React.useState(false) - const [isMobile, setIsMobile] = React.useState(false) + const [isScrolled, setIsScrolled] = React.useState(false); + const [isOpenMenu, setIsOpenMenu] = React.useState(false); + const [isMobile, setIsMobile] = React.useState(false); - React.useEffect(() => { - // check is mobile - if (window.innerWidth <= 768) { - setIsMobile(true) - } else { - setIsMobile(false) - } + React.useEffect(() => { + // check is mobile + if (window.innerWidth <= 768) { + setIsMobile(true); + } else { + setIsMobile(false); + } - if (window.innerWidth <= 1024) { - setIsScrolled(true) + if (window.innerWidth <= 1024) { + setIsScrolled(true); + } else { + window.addEventListener("scroll", () => { + if (window.scrollY > 0) { + setIsScrolled(true); } else { - window.addEventListener('scroll', () => { - if (window.scrollY > 0) { - setIsScrolled(true) - } else { - setIsScrolled(false) - } - }) - } - }, []) - - const jumpToSection = (section: string) => { - console.log('section', section) - const element = document.getElementById(section) - if (element) { - element.scrollIntoView({ behavior: 'smooth' }) + setIsScrolled(false); } + }); } + }, []); - const openLocalPdf = () => { - const pdf = Whitepaper - window.open(pdf) + const jumpToSection = (section: string) => { + console.log("section", section); + const element = document.getElementById(section); + if (element) { + element.scrollIntoView({ behavior: "smooth" }); } + }; - return ( - <> - {isScrolled ? ( -
-
-
-
- -
-

- SGPT -

-
+ const openLocalPdf = () => { + const pdf = Whitepaper; + window.open(pdf); + }; - { - // Mobile menu - isMobile ? ( -
setIsOpenMenu(!isOpenMenu)} - > -
-
-
-
- ) : ( -
-
    - {menuItems.map((item) => ( -
  • - jumpToSection(item.id) - } - > -

    - {item.name} -

    -
  • - ))} -
+ return ( + <> + {isScrolled ? ( +
+
+
+
+ +
+

+ SGPT +

+
-
- - -
-
- ) - } - - { - // Mobile menu - isMobile && isOpenMenu ? ( -
-
-
    - {menuItems.map((item) => ( -
  • - jumpToSection(item.id) - } - > -

    - {item.name} -

    -
  • - ))} -
  • openLocalPdf()} - > -

    - Whitepaper -

    -
  • -
  • -

    - Audit -

    -
  • -
-
-
- ) : null - } -
+ { + // Mobile menu + isMobile ? ( +
setIsOpenMenu(!isOpenMenu)} + > +
+
+
- ) : ( -
-
-
-
- -
-

- SGPT -

-
+ ) : ( +
+
    + {menuItems.map((item) => ( +
  • jumpToSection(item.id)} + > +

    + {item.name} +

    +
  • + ))} +
-
-
    - {menuItems.map((item) => ( -
  • jumpToSection(item.id)} - > -

    - {item.name} -

    -
  • - ))} -
+
+ + +
+
+ ) + } -
- - -
-
-
+ { + // Mobile menu + isMobile && isOpenMenu ? ( +
+
+
    + {menuItems.map((item) => ( +
  • jumpToSection(item.id)} + > +

    + {item.name} +

    +
  • + ))} +
  • openLocalPdf()} + > +

    + Whitepaper +

    +
  • +
  • +

    + Audit +

    +
  • +
+
- )} - - ) -} + ) : null + } +
+
+ ) : ( +
+
+
+
+ +
+

+ SGPT +

+
+ +
+
    + {menuItems.map((item) => ( +
  • jumpToSection(item.id)} + > +

    + {item.name} +

    +
  • + ))} +
+ +
+ + +
+
+
+
+ )} + + ); +}; -export default Header +export default Header; diff --git a/src/shared/components/animated/QnASection.css b/src/shared/components/animated/QnASection.css new file mode 100644 index 0000000..7ab212f --- /dev/null +++ b/src/shared/components/animated/QnASection.css @@ -0,0 +1,15 @@ +/* .list-answer { + animation: modalFadeIn ease 0.5s; + background-color: red; +} +@keyframes modalFadeIn { + 0% { + opacity: 0; + transform: translateY(-150px); + } + + 100% { + opacity: 1; + transform: translateY(0px); + } +} */ diff --git a/src/shared/components/animated/TypingText.tsx b/src/shared/components/animated/TypingText.tsx new file mode 100644 index 0000000..d2a5275 --- /dev/null +++ b/src/shared/components/animated/TypingText.tsx @@ -0,0 +1,28 @@ +import React, { useEffect, useState } from "react"; + +type Props = { + children: string; +}; +const TypingText = ({ children, ...props }: Props) => { + const [text, setText] = useState(``); + + useEffect(() => { + setText(children); + }); + const [typedText, setTypedText] = useState(""); + + useEffect(() => { + if (text.length === typedText.length) { + return; + } + + const timeoutId = setTimeout(() => { + setTypedText(text.slice(0, typedText.length + 1)); + }, 70); + + return () => clearTimeout(timeoutId); + }, [text, typedText]); + + return

{typedText}

; +}; +export default TypingText; diff --git a/src/shared/components/backtotop/index.tsx b/src/shared/components/backtotop/index.tsx index 699bcc4..5accff6 100644 --- a/src/shared/components/backtotop/index.tsx +++ b/src/shared/components/backtotop/index.tsx @@ -1,39 +1,44 @@ -import { useState } from 'react' -import robotLogo from '../../../assets/images/robot-coin1.png' -import { MdOutlineKeyboardDoubleArrowUp } from 'react-icons/md' +import { useState } from "react"; +import robotLogo from "../../../assets/images/robot-coin1.png"; +import { MdOutlineKeyboardDoubleArrowUp } from "react-icons/md"; +import { VscFoldUp } from "react-icons/vsc"; const BackToTopButton = () => { - const [isVisible, setIsVisible] = useState(false) + const [isVisible, setIsVisible] = useState(false); - const toggleVisibility = () => { - if (window.pageYOffset > 100) { - setIsVisible(true) - } else { - setIsVisible(false) - } + const toggleVisibility = () => { + if (window.pageYOffset > 100) { + setIsVisible(true); + } else { + setIsVisible(false); } + }; - const scrollToTop = () => { - window.scrollTo({ - top: 0, - behavior: 'smooth', - }) - } + const scrollToTop = () => { + window.scrollTo({ + top: 0, + behavior: "smooth", + }); + }; - window.addEventListener('scroll', toggleVisibility) + window.addEventListener("scroll", toggleVisibility); - return ( -
- back - - 👆 - -
- ) -} + return ( +
+ + back + + 👆 + +
+ ); +}; -export default BackToTopButton +export default BackToTopButton; diff --git a/src/shared/providers/RouterProviderComponent.tsx b/src/shared/providers/RouterProviderComponent.tsx index 21c3514..4dd55f2 100644 --- a/src/shared/providers/RouterProviderComponent.tsx +++ b/src/shared/providers/RouterProviderComponent.tsx @@ -1,4 +1,5 @@ import { createBrowserRouter, RouterProvider } from "react-router-dom"; + import Animated from "../../pages/Animated"; import Home from "../../pages/Home"; import HomeLayout from "../components/layouts/HomeLayout"; @@ -19,6 +20,7 @@ const router = createBrowserRouter([ ], }, ]); +// const RouterProviderComponent = () => { return ; }; diff --git a/tailwind.config.cjs b/tailwind.config.cjs index f57a2db..b9b890c 100644 --- a/tailwind.config.cjs +++ b/tailwind.config.cjs @@ -2,7 +2,19 @@ module.exports = { content: ["./index.html", "./src/**/*.{js,ts,jsx,tsx}"], theme: { - extend: {}, + extend: { + keyframes: { + listShowdown: { + "0%": { opacity: 0, transform: "translateY(-150px)" }, + "50%": { opacity: 0, transform: "translateY(-75px)" }, + "100%": { opacity: 1, transform: "translateY(0px)" }, + }, + listHidden: { + "100%": { opacity: 0, transform: "translateY(-150px)" }, + "0%": { opacity: 1, transform: "translateY(0px)" }, + }, + }, + }, fontFamily: { sans: ["Sen", "sans-serif"], body: ["Comfortaa", "sans-serif"],