Skip to content

Commit

Permalink
Merge pull request #115 from ShinichiShi/fix/achievements-110
Browse files Browse the repository at this point in the history
fixes #110 achievement-section
  • Loading branch information
SkySingh04 authored Nov 22, 2024
2 parents 4807170 + 181fe29 commit 2c24ff0
Show file tree
Hide file tree
Showing 14 changed files with 371 additions and 14 deletions.
3 changes: 0 additions & 3 deletions app/(default)/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ import "../css/additional-styles/landing.css";
import Activities from "@/components/activities";
import Image from "next/image";
import SparklesText from "@/components/magicui/sparkles-text";
import EventComponent from "@/components/eventcards";
import Achievements from '@/components/achievements';
import Founder from "@/components/founder";
import Share from "@/components/share";
Expand Down Expand Up @@ -51,8 +50,6 @@ export default function Home() {
</div>
<Founder />
<Achievements />
<EventComponent />

<Share />
<div className="text-center mb-12">
<h1 className="text-3xl sm:text-4xl font-extrabold text-gray-100 mt-2 p-2">
Expand Down
157 changes: 157 additions & 0 deletions components/achievementList.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,157 @@

export const achievementJson = [
{
id: 1,
name: "Pratyush Singh",
username: "@GSOC",
body: "The Mifos Initiative",
img: "gsoclogo.png",
},
{
id: 2,
name: "Ashutosh Pandey",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 3,
name: "Mohit Agarwal",
username: "@ICPC",
body: "ACM-ICPC Regionalist",
img: "icpclogo.png",
},
{
id: 4,
name: "Debayan G",
username: "@SIH",
body: "Winner OF SIH’23",
img: "sihlogo.png",
},
{
id: 5,
name: "Rahul Jagwani",
username: "@GSOC",
body: "Global Alliance for Genomics and Health",
img: "gsoclogo.png",
},
{
id: 6,
name: "Saalim Quadri",
username: "@LFX",
body: "Linux Kernel Mentorship Program",
img: "lfxlogo.png",
},
{
id: 7,
name: "Soumya Pattanayak",
username: "@ICPC",
body: "First team to qualify to ICPC regionals from DSCE",
img: "icpclogo.png",
},
{
id: 8,
name: "Akash Singh",
username: "@HackGlobal",
body: "Winner of HackBangalore | Top 9 in HackGlobal",
img: "hackglobal.png",
},
{
id: 9,
name: "Uttkarsh",
username: "@GSOC",
body: "OWASP Foundation",
img: "gsoclogo.png",
},
{
name: "Aayush Kumar",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 10,
name: "Priyanshu Gupta",
username: "@ICPC",
body: "ACM-ICPC Regionalist",
img: "icpclogo.png",
},
{
id: 11,
name: "Madhur Mehta",
username: "@SIH",
body: "Winner OF SIH’23",
img: "sihlogo.png",
},
{
id: 12,
name: "Akash Singh",
username: "@GSOC",
body: "Keploy: E2E test generation",
img: "gsoclogo.png",
},
{
id: 13,
name: "Tanmay R K",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 14,
name: "Aditya",
username: "@GSOC",
body: "The Mifos Initiative",
img: "gsoclogo.png",
},
{
id: 15,
name: "Abhyuday Hari",
username: "@HackGlobal",
body: "Winner of HackBangalore | Top 9 in HackGlobal",
img: "hackglobal.png",
},

{
id: 16,
name: "Pratik Singh",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 17,
name: "Palak Khandelwal",
username: "@SIH",
body: "Winner OF SIH’23",
img: "sihlogo.png",
},
{
id: 18,
name: "Bhuvan M",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 19,
name: "Ankit Kumar Singh",
username: "@Centuriton",
body: "Winner OF CentuRITon'22",
img: "centuriton.png",
},
{
id: 20,
name: "Abhyuday Hari",
username: "@LFX",
body: "LiFT Scholarship Holder",
img: "lfxlogo.png",
},
{
id: 21,
name: "Sreeniketh Madugula",
username: "@Centuriton",
body: "Winner OF CentuRITon'22",
img: "centuriton.png",
},
];
63 changes: 52 additions & 11 deletions components/achievements.tsx
Original file line number Diff line number Diff line change
@@ -1,25 +1,66 @@
"use client";

import Carousel from "./carousel.component";
import imageOne from "../public/images/pbach1.jpg";
import imageTwo from "../public/images/pbach2.jpg";
import imageThree from "../public/images/pbach3.jpg";
import React from "react";
import { cn } from "@/lib/server/utils";
import Marquee from "@/components/magicui/marquee";
import { achievementJson } from "./achievementList";
import Image from 'next/image'

function Achievements() {
let slides = [imageOne, imageTwo, imageThree];
const ReviewCard = ({
img,
name,
username,
body,
}: {
img: string;
name: string;
username: string;
body: string;
}) => {
return (
<figure
className={cn(
"relative w-64 cursor-pointer overflow-hidden rounded-xl border p-4",
"border-gray-950/[.1] bg-gray-950/[.01] hover:bg-gray-950/[.05]",
"dark:border-gray-50/[.1] dark:bg-gray-50/[.10] dark:hover:bg-gray-50/[.15]",
)}
>
<div className="flex flex-row items-center gap-2">
<Image className="rounded-full" width={38} height={38} alt="" src={`/images/${img}`} />
<div className="flex flex-col">
<figcaption className="text-sm font-medium dark:text-white">
{name}
</figcaption>
<p className="text-xs font-medium dark:text-white/40">{username}</p>
</div>
</div>
<blockquote className="mt-2 text-sm">{body}</blockquote>
</figure>
);
};

function Achievements() {
const firstRow = achievementJson.slice(0, achievementJson.length / 2);
const secondRow = achievementJson.slice(achievementJson.length / 2);
return (
<>
<div className="container place-items-center font-bold pt-20 pb-5">
<div className="container place-items-center font-bold pb-5">
<h2 className="text-3xl sm:text-4xl text-white-800 text-center font-black">
Achievements
</h2>
</div>
<div className="sm:w-[50%] md:w-[40%] m-auto pt-11">
<Carousel slides={slides} />
</div>
<Marquee pauseOnHover className="[--duration:60s]">
{firstRow.map((review) => (
<ReviewCard key={review.id} {...review} />
))}
</Marquee>
<Marquee reverse pauseOnHover className="[--duration:60s]">
{secondRow.map((review) => (
<ReviewCard key={review.id} {...review} />
))}
</Marquee>
</>
);
}
export default Achievements;

export default Achievements;
59 changes: 59 additions & 0 deletions components/magicui/animated-list.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
"use client";

import React, { ReactElement, useEffect, useMemo, useState } from "react";
import { AnimatePresence, motion } from "framer-motion";

export interface AnimatedListProps {
className?: string;
children: React.ReactNode;
delay?: number;
}

export const AnimatedList = React.memo(
({ className, children, delay = 1000 }: AnimatedListProps) => {
const [index, setIndex] = useState(0);
const childrenArray = React.Children.toArray(children);

useEffect(() => {
const interval = setInterval(() => {
setIndex((prevIndex) => (prevIndex + 1) % childrenArray.length);
}, delay);

return () => clearInterval(interval);
}, [childrenArray.length, delay]);

const itemsToShow = useMemo(
() => childrenArray.slice(0, index + 1).reverse(),
[index, childrenArray],
);

return (
<div className={`flex flex-col items-center gap-4 ${className}`}>
<AnimatePresence>
{itemsToShow.map((item) => (
<AnimatedListItem key={(item as ReactElement).key}>
{item}
</AnimatedListItem>
))}
</AnimatePresence>
</div>
);
},
);

AnimatedList.displayName = "AnimatedList";

export function AnimatedListItem({ children }: { children: React.ReactNode }) {
const animations = {
initial: { scale: 0, opacity: 0 },
animate: { scale: 1, opacity: 1, originY: 0 },
exit: { scale: 0, opacity: 0 },
transition: { type: "spring", stiffness: 350, damping: 40 },
};

return (
<motion.div {...animations} layout className="mx-auto w-full">
{children}
</motion.div>
);
}
82 changes: 82 additions & 0 deletions components/ui/AnimatedList.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
"use client";

import { cn } from "@/lib/server/utils";
import { AnimatedList } from "@/components/magicui/animated-list";
import { notificationData } from "../achievementList";
import Image from 'next/image'
interface Item {
name: string;
description: string;
icon: string;
time: string;
}
const Notification = ({ name, description, icon, time }: Item) => {
return (
<figure
className={cn(
"relative mx-auto min-h-fit w-full max-w-[400px] cursor-pointer overflow-hidden rounded-2xl p-4",
"transition-all duration-200 ease-in-out hover:scale-[103%]",
"bg-white [box-shadow:0_0_0_1px_rgba(0,0,0,.03),0_2px_4px_rgba(0,0,0,.05),0_12px_24px_rgba(0,0,0,.05)]",
"transform-gpu dark:bg-transparent dark:backdrop-blur-md dark:[border:1px_solid_rgba(255,255,255,.1)] dark:[box-shadow:0_-20px_80px_-20px_#ffffff1f_inset]",
)}
>
<div className="flex flex-row items-center gap-3">
<div
className="flex size-10 items-center justify-center rounded-2xl"

>
<Image
src={`/images/${icon}`}
alt="icpc"
height={400}
width={300}
/>
</div>
<div className="flex flex-col overflow-hidden">
<figcaption className="flex flex-row items-center whitespace-pre text-lg font-medium dark:text-white">
<span className="text-sm sm:text-lg">{name}</span>
<span className="mx-1">·</span>
<span className="text-xs text-gray-500">{time}</span>
</figcaption>
<p className="text-sm font-normal dark:text-white/60">
{description}
</p>
</div>
</div>
</figure>
);
};

interface AnimatedListDemoProps {
className?: string;
type?: 'gsoc' | 'lfx' | 'icpc' | 'sih';
repeatCount?: number;
}

export function AnimatedListDemo({
className,
type = 'gsoc',
repeatCount = 10,
}: AnimatedListDemoProps) {
const selected = notificationData[type];

const repeatedNotifications = Array.from(
{ length: repeatCount },
() => selected
).flat();

return (
<div
className={cn(
"relative flex h-[500px] w-full flex-col overflow-hidden rounded-lg bg-background md:shadow-xl",
className,
)}
>
<AnimatedList>
{repeatedNotifications.map((item, idx) => (
<Notification {...item} key={idx} />
))}
</AnimatedList>
</div>
);
}
Loading

0 comments on commit 2c24ff0

Please sign in to comment.