diff --git a/package.json b/package.json index c328055..12f1c3e 100644 --- a/package.json +++ b/package.json @@ -70,7 +70,7 @@ "typescript": "^4.6.3" }, "engines": { - "node": "14.x", + "node": ">=14.x", "yarn": "1.x" }, "browserslist": [ diff --git a/public/images/community/events/card01.png b/public/images/community/events/card01.png new file mode 100644 index 0000000..7e483f6 Binary files /dev/null and b/public/images/community/events/card01.png differ diff --git a/public/images/community/events/card02.png b/public/images/community/events/card02.png new file mode 100644 index 0000000..cbecb58 Binary files /dev/null and b/public/images/community/events/card02.png differ diff --git a/public/images/community/events/card03.png b/public/images/community/events/card03.png new file mode 100644 index 0000000..c89b9bb Binary files /dev/null and b/public/images/community/events/card03.png differ diff --git a/public/images/community/events/card04.png b/public/images/community/events/card04.png new file mode 100644 index 0000000..e94c603 Binary files /dev/null and b/public/images/community/events/card04.png differ diff --git a/public/images/community/hero/arrow.svg b/public/images/community/hero/arrow.svg new file mode 100644 index 0000000..ff75bfa --- /dev/null +++ b/public/images/community/hero/arrow.svg @@ -0,0 +1,3 @@ + + + diff --git a/public/images/community/hero/hero.png b/public/images/community/hero/hero.png new file mode 100644 index 0000000..af427d8 Binary files /dev/null and b/public/images/community/hero/hero.png differ diff --git a/public/images/community/hero/hero2.png b/public/images/community/hero/hero2.png new file mode 100644 index 0000000..b1e28ea Binary files /dev/null and b/public/images/community/hero/hero2.png differ diff --git a/public/images/community/socials/planet.png b/public/images/community/socials/planet.png new file mode 100644 index 0000000..38ac11a Binary files /dev/null and b/public/images/community/socials/planet.png differ diff --git a/src/components/common/card/card.module.scss b/src/components/common/card/card.module.scss new file mode 100644 index 0000000..b3e6b32 --- /dev/null +++ b/src/components/common/card/card.module.scss @@ -0,0 +1,72 @@ +@import '~/css/helpers'; + +.cardContainer { + width: 100%; + display: flex; + flex-direction: column; + + .eventHeader { + display: flex; + flex-direction: column; + gap: tovw(14px, 'default', 8px); + font-size: tovw(18px, 'default', 12px); + font-family: var(--font-dm-mono), sans-serif; + font-weight: 400; + line-height: 1.2; + letter-spacing: -0.02rem; + + .date, + .hour { + display: flex; + align-items: center; + gap: tovw(10px, 'default', 6px); + + svg { + height: tovw(18px, 'default', 12px); + margin-bottom: tovw(1px, 'default', 1px); + } + } + + div { + display: flex; + gap: tovw(30px, 'default', 25px); + color: var(--color-grey-light); + } + } + + .imageContainer { + margin: tovw(25px, 'default', 16px) 0; + width: 100%; + height: tovw(232px, 'default', 200px); + border-top: tovw(1px, 'default', 1px) solid var(--color-white); + border-bottom: tovw(1px, 'default', 1px) solid var(--color-white); + + img { + width: 100%; + height: 100%; + object-fit: cover; + } + } + + .body { + display: flex; + flex-direction: column; + gap: tovw(24px, 'default', 18px); + + a { + padding-top: tovw(20px, 'default', 12px); + width: fit-content; + } + + p { + margin: 0; + font-weight: 400; + line-height: 1.4; + font-size: tovw(18px, 'default', 15px); + + @media screen and (max-width: 800px) { + line-height: 1.6; + } + } + } +} diff --git a/src/components/common/card/index.tsx b/src/components/common/card/index.tsx new file mode 100644 index 0000000..cf4a837 --- /dev/null +++ b/src/components/common/card/index.tsx @@ -0,0 +1,42 @@ +import { Calendar, Clock } from '~/components/icons/events' +import Heading from '~/components/primitives/heading' +import Link from '~/components/primitives/link' + +import s from './card.module.scss' + +interface Props { + className?: string + data?: any +} + +function Card({ className, data }: Props) { + return ( +
+
+ {data?.location?.toUpperCase()} +
+ + + {data?.date} + + + + {data?.time} HS + +
+
+
+ preview +
+
+ + {data?.title} + +

{data?.preview}

+ LEARN MORE +
+
+ ) +} + +export default Card diff --git a/src/components/icons/arrow.tsx b/src/components/icons/arrow.tsx index 6c184b8..15b5917 100644 --- a/src/components/icons/arrow.tsx +++ b/src/components/icons/arrow.tsx @@ -65,4 +65,37 @@ const ArrowLink = ({ ) } -export { Arrow, ArrowDotted, ArrowLink } +const ArrowSlider = ({ + className, + fill, + onClick, + disabled +}: { + className?: string + fill?: string + onClick?: any + disabled?: any +}) => { + return ( + + + + + ) +} + +export { Arrow, ArrowDotted, ArrowLink, ArrowSlider } diff --git a/src/components/icons/events.tsx b/src/components/icons/events.tsx new file mode 100644 index 0000000..34b4d71 --- /dev/null +++ b/src/components/icons/events.tsx @@ -0,0 +1,28 @@ +const Calendar = ({ className }: { className?: string }) => { + return ( + + + + ) +} + +const Clock = ({ className }: { className?: string }) => { + return ( + + + + + ) +} + +export { Calendar, Clock } diff --git a/src/components/icons/socials.tsx b/src/components/icons/socials.tsx index d748489..447bbc3 100644 --- a/src/components/icons/socials.tsx +++ b/src/components/icons/socials.tsx @@ -225,4 +225,28 @@ const Instagram = ({ ) } -export { Facebook, Instagram, Linkedin, Reddit, Telegram, Twitter } +const Discourse = ({ + className, + fill +}: { + className?: string + fill?: string +}) => { + return ( + + + + ) +} + +export { Discourse, Facebook, Instagram, Linkedin, Reddit, Telegram, Twitter } diff --git a/src/components/sections/community/events/events.module.scss b/src/components/sections/community/events/events.module.scss new file mode 100644 index 0000000..425bc8a --- /dev/null +++ b/src/components/sections/community/events/events.module.scss @@ -0,0 +1,123 @@ +@import '~/css/helpers'; + +.section { + display: flex; + place-content: center; + align-items: center; + margin-top: tovw(55px, 'default', 20px); + padding: tovw(220px, 'default', 72px) 0; + + .heading { + display: flex; + align-items: center; + justify-content: space-between; + border-bottom: tovw(1px, 'default', 1px) solid #fbfbfb; + padding-bottom: tovw(60px, 'default', 30px); + margin-bottom: tovw(80px, 'default', 64px); + + @media screen and (max-width: 800px) { + flex-direction: column; + align-items: flex-start; + border-bottom: unset; + padding-bottom: unset; + gap: tovw(16px, 'mobile'); + } + + h2 { + text-shadow: 0px 0px tovw(20px, 'default', 20px) rgb(255 255 255 / 0.4); + } + + span { + line-height: 1.32; + font-size: tovw(24px, 'default', 18px); + font-family: var(--font-tt-hoves), sans-serif; + width: tovw(350px, 'default', 265px); + } + + .gradient { + position: absolute; + z-index: -1; + left: 0; + right: 0; + width: 100vw; + margin-left: 0; + height: tovw(500px, 'default', 250px); + content: ''; + user-select: none; + pointer-events: none; + opacity: 0.4; + background: linear-gradient( + 180deg, + rgb(229 229 229 / 0) 0%, + rgb(241 241 241 / 0.4) 48.91%, + rgb(241 241 241 / 0) 89.23% + ); + + @media screen and (max-width: 800px) { + display: none; + } + } + } + + .eventsContainer { + display: grid; + grid-auto-flow: column; + + &::after, + &::before { + position: absolute; + content: ''; + height: 100%; + width: tovw(280px, 'default', 150px); + right: 0; + background: linear-gradient( + 90deg, + rgb(3 3 3 / 0) 0%, + rgb(3 3 3 / 0.95) 35%, + rgb(3 3 3 / 1) 65% + ); + + @media screen and (max-width: 800px) { + background: linear-gradient( + 90deg, + rgb(3 3 3 / 0) 0%, + rgb(3 3 3 / 0.55) 35%, + rgb(3 3 3 / 1) 95% + ); + width: tovw(20px, 'default', 20px); + } + } + + &::before { + left: 0; + z-index: 1; + background: linear-gradient( + 270deg, + rgb(3 3 3 / 0) 0%, + rgb(3 3 3 / 0.95) 35%, + rgb(3 3 3 / 1) 65% + ); + } + } + + .navigation { + display: flex; + place-content: center; + width: 100%; + gap: tovw(25px, 'default', 15px); + padding-top: tovw(75px, 'default', 45px); + + @media screen and (max-width: 800px) { + display: none; + } + + .arrow { + cursor: pointer; + width: tovw(50px, 'default', 30px); + + &:first-child { + transform: rotate(180deg); + } + } + } +} diff --git a/src/components/sections/community/events/events.ts b/src/components/sections/community/events/events.ts new file mode 100644 index 0000000..cca0644 --- /dev/null +++ b/src/components/sections/community/events/events.ts @@ -0,0 +1,42 @@ +export const events = [ + { + location: 'California, US', + date: '01.31.22', + time: '20:30', + imgSrc: '/images/community/events/card01.png', + title: 'ETH Denver', + preview: + 'Sit sed dolor felis quis. Porttitor semper enim placerat luctus purus aliquam. Diam eu varius donec sit urna feugiat libero diam augue.', + link: 'https://google.com' + }, + { + location: 'San Francisco, US', + date: '04.25.22', + time: '19:30', + imgSrc: '/images/community/events/card02.png', + title: 'Devconnect', + preview: + 'Sit sed dolor felis quis. Porttitor semper enim placerat luctus purus aliquam. Diam eu varius donec sit urna feugiat libero diam augue.', + link: 'https://google.com' + }, + { + location: 'Paris, FR', + date: '06.25.22', + time: '19:30', + imgSrc: '/images/community/events/card03.png', + title: 'Paris Blockchain Week', + preview: + 'Sit sed dolor felis quis. Porttitor semper enim placerat luctus purus aliquam. Diam eu varius donec sit urna feugiat libero diam augue.', + link: 'https://google.com' + }, + { + location: 'Amsterdam, NL', + date: '08.25.22', + time: '19:30', + imgSrc: '/images/community/events/card04.png', + title: 'ETHCC', + preview: + 'Sit sed dolor felis quis. Porttitor semper enim placerat luctus purus aliquam. Diam eu varius donec sit urna feugiat libero diam augue.', + link: 'https://google.com' + } +] diff --git a/src/components/sections/community/events/index.tsx b/src/components/sections/community/events/index.tsx new file mode 100644 index 0000000..e1bdb24 --- /dev/null +++ b/src/components/sections/community/events/index.tsx @@ -0,0 +1,83 @@ +import { useKeenSlider } from 'keen-slider/react' +import { useState } from 'react' + +import Card from '~/components/common/card' +import { ArrowSlider } from '~/components/icons/arrow' +import { Container } from '~/components/layout/container' +import Section from '~/components/layout/section' +import Heading from '~/components/primitives/heading' + +import { events } from './events' +import s from './events.module.scss' + +const Events = () => { + const [currentSlide, setCurrentSlide] = useState(0) + const [loaded, setLoaded] = useState(false) + const [slideHasEnded, setSlideHasEnded] = useState(false) + + const [sliderRef, slider] = useKeenSlider({ + initial: 0, + loop: false, + slideChanged(slider) { + setCurrentSlide(slider.track.details.rel) + }, + detailsChanged: (slider) => { + setSlideHasEnded(slider.track.details.progress >= 1 ? true : false) + }, + created() { + setLoaded(true) + }, + breakpoints: { + '(max-width: 1050px)': { + slides: { perView: 1, spacing: 12 } + }, + '(min-width: 1050px)': { + slides: { perView: 2, spacing: 22 } + }, + '(min-width: 1600px)': { + slides: { perView: 3, spacing: 26 } + } + } + }) + + return ( +
+ +
+ + Events + + + We’d love to meet you in person. Find us at a conference near you: + +
+
+
+ {events.map((event, i) => ( + + ))} +
+ {loaded && slider.current && ( +
+ + e.stopPropagation() || slider.current?.prev() + } + disabled={currentSlide === 0} + className={s['arrow']} + /> + + e.stopPropagation() || slider.current?.next() + } + disabled={slideHasEnded} + className={s['arrow']} + /> +
+ )} + +
+ ) +} + +export default Events diff --git a/src/components/sections/community/hero/hero.module.scss b/src/components/sections/community/hero/hero.module.scss new file mode 100644 index 0000000..2978d6d --- /dev/null +++ b/src/components/sections/community/hero/hero.module.scss @@ -0,0 +1,135 @@ +@import '~/css/helpers'; + +.section { + display: grid; + align-items: center; + gap: tovw(140px, 'default', 80px) tovw(130px, 'default', 30px); + justify-content: center; + grid-template-columns: repeat(2, 1fr); + grid-template-rows: repeat(2, 1fr); + min-height: calc(var(--vh) * 100); + max-width: 100%; + + @media screen and (max-width: 800px) { + display: flex; + flex-direction: column; + width: 100vw; + padding: 0 tovw(27px, 'tablet', 27px); + padding-bottom: tovw(18px, 'mobile'); + min-height: 100vh; + } + + img { + position: absolute; + z-index: -2; + width: tovw(1050px, 'default', 400px); + padding-top: tovw(150px, 'default', 90px); + + @media screen and (max-width: 800px) { + position: unset; + width: 110vw; + padding-top: tovw(55px, 'mobile'); + margin-bottom: tovw(-85px, 'mobile'); + } + } + + .headingContainer { + justify-self: end; + align-self: end; + width: tovw(580px, 'default', 80px); + + @media screen and (max-width: 800px) { + display: flex; + align-self: flex-start; + align-items: flex-end; + justify-content: space-between; + width: 100%; + } + + h1 { + margin: 0; + text-shadow: 0px 0px tovw(20px, 'default', 20px) rgb(255 255 255 / 0.4); + + @media screen and (max-width: 800px) { + font-size: tovw(50px, 'mobile'); + } + } + } + + .textContainer { + display: flex; + flex-direction: column; + gap: tovw(60px, 'default', 20px); + align-self: start; + grid-area: 2 / 2 / 3 / 3; + + @media screen and (max-width: 800px) { + width: 100%; + gap: tovw(120px, 'default', 30px); + } + + p { + margin: 0; + width: tovw(500px, 'default', 370px); + line-height: 1.3; + + @media screen and (max-width: 800px) { + width: tovw(150px, 'mobile', 320px); + } + } + + a { + width: fit-content; + } + } + + .buttonsContainer { + display: flex; + gap: tovw(24px, 'default', 20px); + + @media screen and (max-width: 800px) { + width: 100%; + flex-direction: column; + gap: tovw(20px, 'mobile'); + } + } + + .gradient { + position: absolute; + top: 0; + width: 100%; + height: 55%; + background: linear-gradient( + 180deg, + rgb(0 0 244 / 0.9) 1.63%, + rgb(0 0 244 / 0) 99.89% + ); + z-index: -1; + + @media screen and (max-width: 800px) { + height: 75%; + mix-blend-mode: screen; + } + } + + .arrow { + position: absolute; + margin-left: tovw(-58px, 'default', -58px); + width: tovw(22px, 'default', 15px); + height: tovw(22px, 'default', 15px); + + @media screen and (max-width: 800px) { + display: none; + } + } + + .arrowMobile { + width: tovw(25px, 'default', 25px); + height: tovw(25px, 'default', 25px); + margin-bottom: tovw(8px, 'default', 7px); + + @media screen and (min-width: 801px) { + display: none; + } + } +} diff --git a/src/components/sections/community/hero/index.tsx b/src/components/sections/community/hero/index.tsx new file mode 100644 index 0000000..2bdcd82 --- /dev/null +++ b/src/components/sections/community/hero/index.tsx @@ -0,0 +1,38 @@ +import { Arrow } from '~/components/icons/arrow' +import Section from '~/components/layout/section' +import { Button } from '~/components/primitives/button' +import Heading from '~/components/primitives/heading' +import Link from '~/components/primitives/link' + +import s from './hero.module.scss' + +const Hero = () => { + return ( +
+
+ hero +
+ + Laconic Community + + +
+
+ +

+ Join us as we accelerate blockchain development and interoperability + by expanding access to verifiable data. +

+ LEARN MORE +
+ + +
+
+
+ ) +} + +export default Hero diff --git a/src/components/sections/community/socials/index.tsx b/src/components/sections/community/socials/index.tsx new file mode 100644 index 0000000..0e0af78 --- /dev/null +++ b/src/components/sections/community/socials/index.tsx @@ -0,0 +1,68 @@ +import Line from '~/components/icons/line' +import { + Discourse, + Facebook, + Instagram, + Linkedin, + Reddit, + Telegram, + Twitter +} from '~/components/icons/socials' +import { Container } from '~/components/layout/container' +import Section from '~/components/layout/section' +import Heading from '~/components/primitives/heading' + +import s from './socials.module.scss' + +const Socials = () => { + return ( +
+ + planet figure +
+
+ + Socials + + + Connect With Us + +
+ +
+
+ GET IN TOUCH +
+ + + + + + + +
+
+
+
+ ) +} + +export default Socials diff --git a/src/components/sections/community/socials/socials.module.scss b/src/components/sections/community/socials/socials.module.scss new file mode 100644 index 0000000..25234b3 --- /dev/null +++ b/src/components/sections/community/socials/socials.module.scss @@ -0,0 +1,157 @@ +@import '~/css/helpers'; + +.section { + position: relative; + padding: tovw(124px, 'default', 100px) 0; + + @media screen and (max-width: 800px) { + margin-top: 0; + } + + .container { + display: grid; + grid-template-columns: 1.7fr 1fr; + grid-template-rows: repeat(2, 1fr); + gap: tovw(70px, 'default', 20px) 0; + + @media screen and (max-width: 800px) { + display: flex; + flex-direction: column; + gap: tovw(5px, 'mobile', 15px); + } + } + + .headingContainer { + display: flex; + flex-direction: column; + width: 100%; + + @media screen and (max-width: 800px) { + margin-top: tovw(-135px, 'mobile', -150px); + } + + h2 { + margin: 0; + text-shadow: 0px 0px tovw(20px, 'default', 20px) rgb(255 255 255 / 0.4); + + @media screen and (max-width: 800px) { + font-size: tovw(42px, 'default', 36px); + text-align: center; + } + + &:nth-child(1) { + padding-left: tovw(125px, 'default', 60px); + + @media screen and (max-width: 800px) { + padding-left: unset; + } + } + + &:nth-child(2) { + align-self: end; + width: tovw(465px, 'default', 80px); + + @media screen and (max-width: 800px) { + width: 100%; + } + } + } + } + + .line { + position: absolute; + left: tovw(770px, 'default', 300px); + top: tovw(170px, 'default', 120px); + transform: rotate(270deg) scale(1.6); + width: tovw(173px, 'default', 120px); + height: tovw(72px, 'default', 40px); + + @media screen and (max-width: 800px) { + transform: rotate(0deg) translateY(35%) scaleX(1.6); + height: tovw(80px, 'default', 38px); + left: 0; + right: 0; + margin: auto; + top: unset; + } + } + + .socialIconsContainer { + grid-area: 2 / 2 / 3 / 3; + + @media screen and (max-width: 800px) { + display: flex; + flex-direction: column; + } + + span { + font-family: var(--font-dm-mono), sans-serif; + font-size: tovw(18px, 'default', 12px); + letter-spacing: -0.02rem; + + &::before { + position: absolute; + transform: translate(-220%, -50%); + display: block; + content: ''; + width: tovw(24px, 'default', 15px); + height: tovw(18px, 'default', 15px); + border-bottom: tovw(2px, 'default', 2px) solid blue; + + @media screen and (max-width: 800px) { + display: none; + } + } + + @media screen and (max-width: 800px) { + text-align: center; + } + } + + .iconsGrid { + width: tovw(400px, 'default', 255px); + padding-top: tovw(30px, 'default', 15px); + display: flex; + flex-wrap: wrap; + gap: tovw(20px, 'default', 12px); + + @media screen and (max-width: 800px) { + place-self: center; + place-content: center; + } + + button { + cursor: pointer; + display: flex; + place-content: center; + padding: tovw(13px, 'default', 8px); + height: tovw(55px, 'default', 38px); + width: tovw(72px, 'default', 54px); + border: tovw(1px, 'default', 1px) solid #fff; + border-radius: tovw(30px, 'default', 20px); + background-color: var(--color-black); + transition: filter 200ms; + + &:hover { + filter: invert(1); + } + } + + svg { + width: tovw(27px, 'default', 20px); + } + } + } + + .planetImage { + position: absolute; + padding-top: tovw(160px, 'default', 80px); + width: tovw(725px, 'default', 320px); + + @media screen and (max-width: 800px) { + padding-top: unset; + width: 100%; + position: relative; + } + } +} diff --git a/src/pages/community.tsx b/src/pages/community.tsx new file mode 100644 index 0000000..89c8b30 --- /dev/null +++ b/src/pages/community.tsx @@ -0,0 +1,20 @@ +import { Meta } from '~/components/common/meta' +import { PageLayout } from '~/components/layout/page' +import Events from '~/components/sections/community/events' +import Hero from '~/components/sections/community/hero' +import Socials from '~/components/sections/community/socials' + +import { Page } from './_app' + +const Community: Page = () => { + return ( + + + + + + + ) +} + +export default Community