diff --git a/app/(home)/components/SponsorsDesktop.tsx b/app/(home)/components/SponsorsDesktop.tsx index 11061cf..db81c73 100644 --- a/app/(home)/components/SponsorsDesktop.tsx +++ b/app/(home)/components/SponsorsDesktop.tsx @@ -158,7 +158,7 @@ const SponsorsDesktop = ({ sponsors }: { sponsors: SponsorshipProps[] }) => {

{featuredSponsor.description}

-

— {featuredSponsor.name} +

- {featuredSponsor.name}

diff --git a/app/(home)/components/Testimonials.tsx b/app/(home)/components/Testimonials.tsx new file mode 100644 index 0000000..47fd153 --- /dev/null +++ b/app/(home)/components/Testimonials.tsx @@ -0,0 +1,291 @@ +'use client'; + +import { Button } from '@/components/ui/button'; +import Image from 'next/image'; +import { Container } from '@/components/ui/container'; +import Link from 'next/link'; +import { CarouselDots, type CarouselApi } from '@/components/ui/carousel'; +import { useState, useRef, useEffect } from 'react'; +import YellowStar from '@/public/assets/testimonials/yellow-star.svg'; +import WhiteStar from '@/public/assets/testimonials/white-star.svg'; +import ChatBubble from '@/public/assets/testimonials/chat-bubble.svg'; +import { Avatar, AvatarFallback, AvatarImage } from '@/components/ui/avatar'; +import { + Carousel, + CarouselContent, + CarouselItem, + CarouselNext, + CarouselPrevious, +} from '@/components/ui/carousel'; + +type TestimonialProps = { + text: string; + rate: number; + active: boolean; +}; + +export function Testimonials() { + const dummyData = [ + { + name: 'AlexByte_97', + date: '2 days ago', + comment: + "I've been following similar content for a while, but this one really stands out. The attention to detail and the way everything is explained so clearly make it incredibly easy to understand. Honestly, I wish more people put this level of effort into their posts. Keep it up! Looking forward to more amazing content like this! ????", + rate: 5, + profilePic: 'https://github.com/shadcn.png', + }, + { + name: 'GamerXtreme', + date: '3 weeks ago', + comment: 'Not bad, but I expected a bit more tbh. ??', + rate: 3, + profilePic: 'https://github.com/shadcn.png', + }, + { + name: 'TechieTasha', + date: '5 days ago', + comment: 'Super useful, definitely sharing this! ??', + rate: 4, + profilePic: 'https://github.com/shadcn.png', + }, + { + name: 'MemeLord420', + date: '1 month ago', + comment: "Bro, this ain't it... ??", + rate: 2, + profilePic: 'https://github.com/shadcn.png', + }, + { + name: 'NeonC0der', + date: '10 hours ago', + comment: + 'I appreciate the effort that went into this, but I feel like some parts could have been elaborated on a bit more. Certain sections were great, but others felt a little rushed. That being said, I still learned a lot and really enjoyed the overall message. Keep refining your style because you definitely have potential! Excited to see how your content evolves over time. ??', + rate: 4, + profilePic: 'https://github.com/shadcn.png', + }, + ]; + + const [api, setApi] = useState(); + const [current, setCurrent] = useState(0); + const [isInteracting, setIsInteracting] = useState(false); + + useEffect(() => { + if (!api) { + return; + } + setCurrent(api.selectedScrollSnap()); + + api.on('select', () => { + setCurrent(api.selectedScrollSnap()); + }); + }, [api]); + + return ( +
+ + {/* Combined container: Ratings + Button */} +
+ {/* Logo & Ratings */} +
+
+
+ Durianpy Logo +

+ Ratings +

+
+ + {/* Star Ratings */} +
+ 4.8 +
+ {[...Array(4)].map((_, i) => ( + yellow star + ))} + yellow star +
+ 5 reviews +
+
+
+ + {/* Button */} +
+ + + +
+
+ + {/* CAROUSEL */} +
+ setIsInteracting(true)} + onMouseLeave={() => setIsInteracting(false)} + className="max-w-96 sm:w-96 lg:max-w-full lg:w-full lg:px-5 mx-auto" + > + + {dummyData.map((data, index) => ( + + +
+ + + + {data.name + .split(' ') + .map((word) => word[0]) + .join('') + .toUpperCase()} + + +
+
{data.name}
+
{data.date}
+
+
+
+ ))} +
+ api?.scrollTo(current - 1)} + /> + api?.scrollTo(current + 1)} + /> + +
+
+
+
+ ); +} + +export function TestimonialCard({ text, rate, active }: TestimonialProps) { + const starRate = []; + const textRef = useRef(null); + const [isTextOverflowing, setIsTextOverflowing] = useState(false); + + // Check if text is overflowing + useEffect(() => { + const checkOverflow = () => { + if (textRef.current) { + const element = textRef.current; + const isOverflowing = + element.scrollHeight > element.clientHeight || + element.scrollWidth > element.clientWidth; + setIsTextOverflowing(isOverflowing); + } + }; + + checkOverflow(); + // Re-check on window resize + window.addEventListener('resize', checkOverflow); + return () => window.removeEventListener('resize', checkOverflow); + }, [text]); + + // Append stars + for (let i = 0; i < 5; i++) { + // If index is greater than the rating, append white star, else yellow star. + if (i >= rate) { + starRate.push( + yellow star + ); + } else { + starRate.push( + yellow star + ); + } + } + + return ( + <> + {/* Mobile View Display */} +
+
{text}
+ {isTextOverflowing && ( +
+ + Read more + +
+ )} +
+ + {/* Tablet & Laptop View Display */} +
+ chat-bubble +
+ {starRate} +
+
+ {text} +
+ {isTextOverflowing && ( +
+ + Read more + +
+ )} +
+ + ); +} diff --git a/app/(home)/page.tsx b/app/(home)/page.tsx index 5992684..ba6fbe0 100644 --- a/app/(home)/page.tsx +++ b/app/(home)/page.tsx @@ -7,6 +7,8 @@ import { Partners } from './components//Partners'; // import UpcomingEvents from './components//UpcomingEvents'; import { Sponsors } from './components/Sponsors'; +import { Testimonials } from './components/Testimonials'; + export default function HomePage() { return (
@@ -14,6 +16,7 @@ export default function HomePage() { + {/* */} diff --git a/components/ui/avatar.tsx b/components/ui/avatar.tsx new file mode 100644 index 0000000..afb7c8a --- /dev/null +++ b/components/ui/avatar.tsx @@ -0,0 +1,50 @@ +'use client'; + +import * as React from 'react'; +import * as AvatarPrimitive from '@radix-ui/react-avatar'; + +import { cn } from '@/lib/utils'; + +const Avatar = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +Avatar.displayName = AvatarPrimitive.Root.displayName; + +const AvatarImage = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +AvatarImage.displayName = AvatarPrimitive.Image.displayName; + +const AvatarFallback = React.forwardRef< + React.ElementRef, + React.ComponentPropsWithoutRef +>(({ className, ...props }, ref) => ( + +)); +AvatarFallback.displayName = AvatarPrimitive.Fallback.displayName; + +export { Avatar, AvatarImage, AvatarFallback }; diff --git a/package-lock.json b/package-lock.json index 8feab5d..ba16fd3 100644 --- a/package-lock.json +++ b/package-lock.json @@ -12,6 +12,7 @@ "@fortawesome/react-fontawesome": "^0.2.2", "@gsap/react": "^2.1.2", "@radix-ui/react-accordion": "^1.2.3", + "@radix-ui/react-avatar": "^1.1.3", "@radix-ui/react-checkbox": "^1.1.4", "@radix-ui/react-dialog": "^1.1.6", "@radix-ui/react-dropdown-menu": "^2.1.6", @@ -25,11 +26,11 @@ "gsap": "^3.12.7", "lenis": "^1.1.22", "lucide-react": "^0.475.0", - "next": "14.2.21", + "next": "^14.2.28", "odometer": "^0.4.8", - "react": "^18", + "react": "^18.2.0", "react-countup": "^6.5.3", - "react-dom": "^18", + "react-dom": "^18.2.0", "tailwind-merge": "^3.0.1", "tailwindcss-animate": "^1.0.7", "tailwindcss-gradients": "^3.0.0" @@ -348,9 +349,9 @@ } }, "node_modules/@next/env": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/env/-/env-14.2.21.tgz", - "integrity": "sha512-lXcwcJd5oR01tggjWJ6SrNNYFGuOOMB9c251wUNkjCpkoXOPkDeF/15c3mnVlBqrW4JJXb2kVxDFhC4GduJt2A==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/env/-/env-14.2.28.tgz", + "integrity": "sha512-PAmWhJfJQlP+kxZwCjrVd9QnR5x0R3u0mTXTiZDgSd4h5LdXmjxCCWbN9kq6hkZBOax8Rm3xDW5HagWyJuT37g==", "license": "MIT" }, "node_modules/@next/eslint-plugin-next": { @@ -364,9 +365,9 @@ } }, "node_modules/@next/swc-darwin-arm64": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.21.tgz", - "integrity": "sha512-HwEjcKsXtvszXz5q5Z7wCtrHeTTDSTgAbocz45PHMUjU3fBYInfvhR+ZhavDRUYLonm53aHZbB09QtJVJj8T7g==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-14.2.28.tgz", + "integrity": "sha512-kzGChl9setxYWpk3H6fTZXXPFFjg7urptLq5o5ZgYezCrqlemKttwMT5iFyx/p1e/JeglTwDFRtb923gTJ3R1w==", "cpu": [ "arm64" ], @@ -380,9 +381,9 @@ } }, "node_modules/@next/swc-darwin-x64": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.21.tgz", - "integrity": "sha512-TSAA2ROgNzm4FhKbTbyJOBrsREOMVdDIltZ6aZiKvCi/v0UwFmwigBGeqXDA97TFMpR3LNNpw52CbVelkoQBxA==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-14.2.28.tgz", + "integrity": "sha512-z6FXYHDJlFOzVEOiiJ/4NG8aLCeayZdcRSMjPDysW297Up6r22xw6Ea9AOwQqbNsth8JNgIK8EkWz2IDwaLQcw==", "cpu": [ "x64" ], @@ -396,9 +397,9 @@ } }, "node_modules/@next/swc-linux-arm64-gnu": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.21.tgz", - "integrity": "sha512-0Dqjn0pEUz3JG+AImpnMMW/m8hRtl1GQCNbO66V1yp6RswSTiKmnHf3pTX6xMdJYSemf3O4Q9ykiL0jymu0TuA==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-14.2.28.tgz", + "integrity": "sha512-9ARHLEQXhAilNJ7rgQX8xs9aH3yJSj888ssSjJLeldiZKR4D7N08MfMqljk77fAwZsWwsrp8ohHsMvurvv9liQ==", "cpu": [ "arm64" ], @@ -412,9 +413,9 @@ } }, "node_modules/@next/swc-linux-arm64-musl": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.21.tgz", - "integrity": "sha512-Ggfw5qnMXldscVntwnjfaQs5GbBbjioV4B4loP+bjqNEb42fzZlAaK+ldL0jm2CTJga9LynBMhekNfV8W4+HBw==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-14.2.28.tgz", + "integrity": "sha512-p6gvatI1nX41KCizEe6JkF0FS/cEEF0u23vKDpl+WhPe/fCTBeGkEBh7iW2cUM0rvquPVwPWdiUR6Ebr/kQWxQ==", "cpu": [ "arm64" ], @@ -428,9 +429,9 @@ } }, "node_modules/@next/swc-linux-x64-gnu": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.21.tgz", - "integrity": "sha512-uokj0lubN1WoSa5KKdThVPRffGyiWlm/vCc/cMkWOQHw69Qt0X1o3b2PyLLx8ANqlefILZh1EdfLRz9gVpG6tg==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-14.2.28.tgz", + "integrity": "sha512-nsiSnz2wO6GwMAX2o0iucONlVL7dNgKUqt/mDTATGO2NY59EO/ZKnKEr80BJFhuA5UC1KZOMblJHWZoqIJddpA==", "cpu": [ "x64" ], @@ -444,9 +445,9 @@ } }, "node_modules/@next/swc-linux-x64-musl": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.21.tgz", - "integrity": "sha512-iAEBPzWNbciah4+0yI4s7Pce6BIoxTQ0AGCkxn/UBuzJFkYyJt71MadYQkjPqCQCJAFQ26sYh7MOKdU+VQFgPg==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-14.2.28.tgz", + "integrity": "sha512-+IuGQKoI3abrXFqx7GtlvNOpeExUH1mTIqCrh1LGFf8DnlUcTmOOCApEnPJUSLrSbzOdsF2ho2KhnQoO0I1RDw==", "cpu": [ "x64" ], @@ -460,9 +461,9 @@ } }, "node_modules/@next/swc-win32-arm64-msvc": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.21.tgz", - "integrity": "sha512-plykgB3vL2hB4Z32W3ktsfqyuyGAPxqwiyrAi2Mr8LlEUhNn9VgkiAl5hODSBpzIfWweX3er1f5uNpGDygfQVQ==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-14.2.28.tgz", + "integrity": "sha512-l61WZ3nevt4BAnGksUVFKy2uJP5DPz2E0Ma/Oklvo3sGj9sw3q7vBWONFRgz+ICiHpW5mV+mBrkB3XEubMrKaA==", "cpu": [ "arm64" ], @@ -476,9 +477,9 @@ } }, "node_modules/@next/swc-win32-ia32-msvc": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.21.tgz", - "integrity": "sha512-w5bacz4Vxqrh06BjWgua3Yf7EMDb8iMcVhNrNx8KnJXt8t+Uu0Zg4JHLDL/T7DkTCEEfKXO/Er1fcfWxn2xfPA==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.28.tgz", + "integrity": "sha512-+Kcp1T3jHZnJ9v9VTJ/yf1t/xmtFAc/Sge4v7mVc1z+NYfYzisi8kJ9AsY8itbgq+WgEwMtOpiLLJsUy2qnXZw==", "cpu": [ "ia32" ], @@ -492,9 +493,9 @@ } }, "node_modules/@next/swc-win32-x64-msvc": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.21.tgz", - "integrity": "sha512-sT6+llIkzpsexGYZq8cjjthRyRGe5cJVhqh12FmlbxHqna6zsDDK8UNaV7g41T6atFHCJUPeLb3uyAwrBwy0NA==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-14.2.28.tgz", + "integrity": "sha512-1gCmpvyhz7DkB1srRItJTnmR2UwQPAUXXIg9r0/56g3O8etGmwlX68skKXJOp9EejW3hhv7nSQUJ2raFiz4MoA==", "cpu": [ "x64" ], @@ -622,6 +623,134 @@ } } }, + "node_modules/@radix-ui/react-avatar": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/@radix-ui/react-avatar/-/react-avatar-1.1.7.tgz", + "integrity": "sha512-V7ODUt4mUoJTe3VUxZw6nfURxaPALVqmDQh501YmaQsk3D8AZQrOPRnfKn4H7JGDLBc0KqLhT94H79nV88ppNg==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-context": "1.1.2", + "@radix-ui/react-primitive": "2.1.0", + "@radix-ui/react-use-callback-ref": "1.1.1", + "@radix-ui/react-use-is-hydrated": "0.1.0", + "@radix-ui/react-use-layout-effect": "1.1.1" + }, + "peerDependencies": { + "@types/react": "*", + "@types/react-dom": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc", + "react-dom": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + }, + "@types/react-dom": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-compose-refs": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@radix-ui/react-compose-refs/-/react-compose-refs-1.1.2.tgz", + "integrity": "sha512-z4eqJvfiNnFMHIIvXP3CY57y2WJs5g2v3X0zm9mEJkrkNv4rDxu+sg9Jh8EkXyeqBkB7SOcboo9dMVqhyrACIg==", + "license": "MIT", + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-context": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@radix-ui/react-context/-/react-context-1.1.2.tgz", + "integrity": "sha512-jCi/QKUM2r1Ju5a3J64TH2A5SpKAgh0LpknyqdQ4m6DCV0xJ2HG1xARRwNGPQfi1SLdLWZ1OJz6F4OMBBNiGJA==", + "license": "MIT", + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-primitive": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@radix-ui/react-primitive/-/react-primitive-2.1.0.tgz", + "integrity": "sha512-/J/FhLdK0zVcILOwt5g+dH4KnkonCtkVJsa2G6JmvbbtZfBEI1gMsO3QMjseL4F/SwfAMt1Vc/0XKYKq+xJ1sw==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-slot": "1.2.0" + }, + "peerDependencies": { + "@types/react": "*", + "@types/react-dom": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc", + "react-dom": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + }, + "@types/react-dom": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-slot": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/@radix-ui/react-slot/-/react-slot-1.2.0.tgz", + "integrity": "sha512-ujc+V6r0HNDviYqIK3rW4ffgYiZ8g5DEHrGJVk4x7kTlLXRDILnKX9vAUYeIsLOoDpDJ0ujpqMkjH4w2ofuo6w==", + "license": "MIT", + "dependencies": { + "@radix-ui/react-compose-refs": "1.1.2" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-use-callback-ref": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@radix-ui/react-use-callback-ref/-/react-use-callback-ref-1.1.1.tgz", + "integrity": "sha512-FkBMwD+qbGQeMu1cOHnuGB6x4yzPjho8ap5WtbEJ26umhgqVXbhekKUQO+hZEL1vU92a3wHwdp0HAcqAUF5iDg==", + "license": "MIT", + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, + "node_modules/@radix-ui/react-avatar/node_modules/@radix-ui/react-use-layout-effect": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/@radix-ui/react-use-layout-effect/-/react-use-layout-effect-1.1.1.tgz", + "integrity": "sha512-RbJRS4UWQFkzHTTwVymMTUv8EqYhOp8dOOviLj2ugtTiXRaRQS7GLGxZTLL1jWhMeoSCf5zmcZkqTl9IiYfXcQ==", + "license": "MIT", + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-checkbox": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/@radix-ui/react-checkbox/-/react-checkbox-1.1.4.tgz", @@ -1203,6 +1332,24 @@ } } }, + "node_modules/@radix-ui/react-use-is-hydrated": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/@radix-ui/react-use-is-hydrated/-/react-use-is-hydrated-0.1.0.tgz", + "integrity": "sha512-U+UORVEq+cTnRIaostJv9AGdV3G6Y+zbVd+12e18jQ5A3c0xL03IhnHuiU4UV69wolOQp5GfR58NW/EgdQhwOA==", + "license": "MIT", + "dependencies": { + "use-sync-external-store": "^1.5.0" + }, + "peerDependencies": { + "@types/react": "*", + "react": "^16.8 || ^17.0 || ^18.0 || ^19.0 || ^19.0.0-rc" + }, + "peerDependenciesMeta": { + "@types/react": { + "optional": true + } + } + }, "node_modules/@radix-ui/react-use-layout-effect": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/@radix-ui/react-use-layout-effect/-/react-use-layout-effect-1.1.0.tgz", @@ -4515,12 +4662,12 @@ "license": "MIT" }, "node_modules/next": { - "version": "14.2.21", - "resolved": "https://registry.npmjs.org/next/-/next-14.2.21.tgz", - "integrity": "sha512-rZmLwucLHr3/zfDMYbJXbw0ZeoBpirxkXuvsJbk7UPorvPYZhP7vq7aHbKnU7dQNCYIimRrbB2pp3xmf+wsYUg==", + "version": "14.2.28", + "resolved": "https://registry.npmjs.org/next/-/next-14.2.28.tgz", + "integrity": "sha512-QLEIP/kYXynIxtcKB6vNjtWLVs3Y4Sb+EClTC/CSVzdLD1gIuItccpu/n1lhmduffI32iPGEK2cLLxxt28qgYA==", "license": "MIT", "dependencies": { - "@next/env": "14.2.21", + "@next/env": "14.2.28", "@swc/helpers": "0.5.5", "busboy": "1.6.0", "caniuse-lite": "^1.0.30001579", @@ -4535,15 +4682,15 @@ "node": ">=18.17.0" }, "optionalDependencies": { - "@next/swc-darwin-arm64": "14.2.21", - "@next/swc-darwin-x64": "14.2.21", - "@next/swc-linux-arm64-gnu": "14.2.21", - "@next/swc-linux-arm64-musl": "14.2.21", - "@next/swc-linux-x64-gnu": "14.2.21", - "@next/swc-linux-x64-musl": "14.2.21", - "@next/swc-win32-arm64-msvc": "14.2.21", - "@next/swc-win32-ia32-msvc": "14.2.21", - "@next/swc-win32-x64-msvc": "14.2.21" + "@next/swc-darwin-arm64": "14.2.28", + "@next/swc-darwin-x64": "14.2.28", + "@next/swc-linux-arm64-gnu": "14.2.28", + "@next/swc-linux-arm64-musl": "14.2.28", + "@next/swc-linux-x64-gnu": "14.2.28", + "@next/swc-linux-x64-musl": "14.2.28", + "@next/swc-win32-arm64-msvc": "14.2.28", + "@next/swc-win32-ia32-msvc": "14.2.28", + "@next/swc-win32-x64-msvc": "14.2.28" }, "peerDependencies": { "@opentelemetry/api": "^1.1.0", @@ -6338,6 +6485,15 @@ } } }, + "node_modules/use-sync-external-store": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/use-sync-external-store/-/use-sync-external-store-1.5.0.tgz", + "integrity": "sha512-Rb46I4cGGVBmjamjphe8L/UnvJD+uPPtTkNvX5mZgqdbavhI4EbgIWJiIHXJ8bc/i9EQGPRh4DwEURJ552Do0A==", + "license": "MIT", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, "node_modules/util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", diff --git a/package.json b/package.json index 5988df9..7f36515 100644 --- a/package.json +++ b/package.json @@ -15,6 +15,7 @@ "@fortawesome/react-fontawesome": "^0.2.2", "@gsap/react": "^2.1.2", "@radix-ui/react-accordion": "^1.2.3", + "@radix-ui/react-avatar": "^1.1.3", "@radix-ui/react-checkbox": "^1.1.4", "@radix-ui/react-dialog": "^1.1.6", "@radix-ui/react-dropdown-menu": "^2.1.6", @@ -28,11 +29,11 @@ "gsap": "^3.12.7", "lenis": "^1.1.22", "lucide-react": "^0.475.0", - "next": "14.2.21", + "next": "^14.2.28", "odometer": "^0.4.8", - "react": "^18", + "react": "^18.2.0", "react-countup": "^6.5.3", - "react-dom": "^18", + "react-dom": "^18.2.0", "tailwind-merge": "^3.0.1", "tailwindcss-animate": "^1.0.7", "tailwindcss-gradients": "^3.0.0" diff --git a/public/assets/testimonials/chat-bubble.svg b/public/assets/testimonials/chat-bubble.svg new file mode 100644 index 0000000..2dcf7d6 --- /dev/null +++ b/public/assets/testimonials/chat-bubble.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/public/assets/testimonials/white-star.svg b/public/assets/testimonials/white-star.svg new file mode 100644 index 0000000..29f5581 --- /dev/null +++ b/public/assets/testimonials/white-star.svg @@ -0,0 +1,3 @@ + + + diff --git a/public/assets/testimonials/yellow-star.svg b/public/assets/testimonials/yellow-star.svg new file mode 100644 index 0000000..50debfa --- /dev/null +++ b/public/assets/testimonials/yellow-star.svg @@ -0,0 +1,3 @@ + + + diff --git a/tsconfig.json b/tsconfig.json index 40f87ee..37ebeb5 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -24,7 +24,8 @@ "@/components/*": ["./components/*"], "@/lib/*": ["./lib/*"], "@/styles/*": ["./styles/*"] - } + }, + "target": "ES2017" }, "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], "exclude": ["node_modules"]