From b65fbdf191d3b5a5ec729ad1bd37b31da26f73e1 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 7 Aug 2025 20:45:59 +0530 Subject: [PATCH 01/44] updated omegaimgs --- src/data/liveEvents/omega/Sponsor.json | 4 ++-- src/sections/LiveEvents/Omega/Attend/Attend.jsx | 8 ++++---- src/sections/LiveEvents/Omega/Hero/Hero.jsx | 2 +- src/sections/LiveEvents/Omega/TeamImage/TeamImage.jsx | 2 +- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/data/liveEvents/omega/Sponsor.json b/src/data/liveEvents/omega/Sponsor.json index b2f70bc5..702d14d3 100644 --- a/src/data/liveEvents/omega/Sponsor.json +++ b/src/data/liveEvents/omega/Sponsor.json @@ -1,10 +1,10 @@ [ { - "image": "https://ucarecdn.com/89def985-c8ff-440e-90ea-0159a410c9c0/" + "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c270e31a5b614a55a4e8_unstop.png" }, { - "image": "https://ucarecdn.com/1f48ea80-f710-4ce1-ac09-5d72b42c9b8d/" + "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c26fb6206100bba45491_unlox.png" } ] diff --git a/src/sections/LiveEvents/Omega/Attend/Attend.jsx b/src/sections/LiveEvents/Omega/Attend/Attend.jsx index fd0c4ce5..656fedad 100644 --- a/src/sections/LiveEvents/Omega/Attend/Attend.jsx +++ b/src/sections/LiveEvents/Omega/Attend/Attend.jsx @@ -34,10 +34,10 @@ function Attend() {
- - - - + + + +
diff --git a/src/sections/LiveEvents/Omega/Hero/Hero.jsx b/src/sections/LiveEvents/Omega/Hero/Hero.jsx index 5d6c600a..44e9a286 100644 --- a/src/sections/LiveEvents/Omega/Hero/Hero.jsx +++ b/src/sections/LiveEvents/Omega/Hero/Hero.jsx @@ -204,7 +204,7 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) { style={{ perspective: 1000 }} > Hero diff --git a/src/sections/LiveEvents/Omega/TeamImage/TeamImage.jsx b/src/sections/LiveEvents/Omega/TeamImage/TeamImage.jsx index f9923680..36523008 100644 --- a/src/sections/LiveEvents/Omega/TeamImage/TeamImage.jsx +++ b/src/sections/LiveEvents/Omega/TeamImage/TeamImage.jsx @@ -5,7 +5,7 @@ import styles from "./styles/TeamImage.module.scss" const TeamImage = () => { return (
- +
) } From c532f0ec71106b6ab6f2a3ab1bb1e7d9c6f20411 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 7 Aug 2025 20:51:00 +0530 Subject: [PATCH 02/44] updated --- src/pages/LiveEvents/Omega/styles/Omega.module.scss | 4 ++-- .../LiveEvents/Omega/Attend/styles/Attend.module.scss | 2 +- src/sections/LiveEvents/Omega/Event/styles/Event.module.scss | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/pages/LiveEvents/Omega/styles/Omega.module.scss b/src/pages/LiveEvents/Omega/styles/Omega.module.scss index b0aad108..df8625d1 100644 --- a/src/pages/LiveEvents/Omega/styles/Omega.module.scss +++ b/src/pages/LiveEvents/Omega/styles/Omega.module.scss @@ -4,7 +4,7 @@ .imageContainer { height: 100%; - background-image: url('https://ucarecdn.com/376d0a3a-5958-465b-9f2c-69610d307916/'); + background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); background-size: cover; background-position: center; background-repeat: no-repeat; @@ -16,7 +16,7 @@ .imageContainer { height: 100%; - background-image: url('https://ucarecdn.com/376d0a3a-5958-465b-9f2c-69610d307916/'); + background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); background-position: 13% 20%; diff --git a/src/sections/LiveEvents/Omega/Attend/styles/Attend.module.scss b/src/sections/LiveEvents/Omega/Attend/styles/Attend.module.scss index 75108445..c7300353 100644 --- a/src/sections/LiveEvents/Omega/Attend/styles/Attend.module.scss +++ b/src/sections/LiveEvents/Omega/Attend/styles/Attend.module.scss @@ -7,7 +7,7 @@ display: flex; flex-direction: column; background-image: - url('https://ucarecdn.com/acba11db-2395-4837-a842-bfa45b1af8ed/'); + url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c399bdd958e9c06c9875_events.png'); background-size: cover; background-position: center; diff --git a/src/sections/LiveEvents/Omega/Event/styles/Event.module.scss b/src/sections/LiveEvents/Omega/Event/styles/Event.module.scss index 08049945..f9d3f8e1 100644 --- a/src/sections/LiveEvents/Omega/Event/styles/Event.module.scss +++ b/src/sections/LiveEvents/Omega/Event/styles/Event.module.scss @@ -8,7 +8,7 @@ background-color: black; background-image: - url('https://ucarecdn.com/8e7a7a91-e675-466b-9fa6-2351e2525d4f/'); + url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c399bdd958e9c06c9875_events.png'); background-size: cover; background-position: center; background-repeat: no-repeat; From f34d702c14acead4ebf965a48c1efe4981f939d3 Mon Sep 17 00:00:00 2001 From: Rudrika Date: Fri, 8 Aug 2025 10:27:13 +0530 Subject: [PATCH 03/44] Social page update --- src/data/SocialLink.json | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/data/SocialLink.json b/src/data/SocialLink.json index edeed898..b32c611c 100644 --- a/src/data/SocialLink.json +++ b/src/data/SocialLink.json @@ -1,10 +1,10 @@ { "instagramTopPost": "https://www.instagram.com/p/C_NcMspy94V/?utm_source=ig_web_copy_link&igsh=MzRlODBiNWFlZA==", - "instagramBottomPost": "https://www.instagram.com/p/C_D1KOoSt7c/?utm_source=ig_web_copy_link&igsh=MzRlODBiNWFlZA==", - "instagramReel": "https://www.instagram.com/reel/C_NWmC_SBH5/?utm_source=ig_web_copy_link&igsh=MzRlODBiNWFlZA==", + "instagramBottomPost": "https://www.instagram.com/p/DNBKQZXzDvn/?igsh=MTM4c2N6c2ZpMXcxeA==", + "instagramReel": "https://www.instagram.com/p/DM5azT6TVt4/?igsh=MXI1eHBodjU3cHB5OA%3D%3D", "linkedInPost": { - "url": "https://www.linkedin.com/embed/feed/update/urn:li:share:7232779054104387585", - "postUrl": "https://www.linkedin.com/posts/fedkiit_fedpreneurshow-omega4-fedkiit-activity-7232779055119351810-JXC2?utm_source=share&utm_medium=member_desktop" + "url": "https://www.linkedin.com/embed/feed/update/urn:li:share:7358731261688827904", + "postUrl": "https://www.linkedin.com/posts/fedkiit_were-excited-to-welcome-unstop-as-the-platform-activity-7358731264897478657-BKWI?utm_source=share&utm_medium=member_desktop&rcm=ACoAAEGVnCgBVHbcyHMpjs36i2Lkz8H7ZXtJp4Y" } } \ No newline at end of file From f5879c6293963a4cc799661b70ce9aab5b27da76 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Fri, 8 Aug 2025 16:16:07 +0530 Subject: [PATCH 04/44] upi id change --- src/features/Modals/Profile/Admin/PreviewForm.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 62cb381e..31e10e5d 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -525,7 +525,7 @@ const handleDownloadQR = async () => { const handleShareQR = () => { // 🔁 Replace these with your actual values - const upiID = "8709217658@superyes"; // e.g., rudrika123@oksbi + const upiID = "8709217658@ybl"; // e.g., rudrika123@oksbi const name = "Mr ANURAG PRASOON"; // e.g., Rudrika const amount = "89"; // e.g., ₹89 From 00d09b897a613248daf25def446c8c4aa7c52a24 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Fri, 8 Aug 2025 16:52:06 +0530 Subject: [PATCH 05/44] omega static updates --- src/data/liveEvents/omega/Accordion.json | 85 ++++++++++++++----- src/data/liveEvents/omega/Sponsor.json | 21 ++++- src/sections/LiveEvents/Omega/Hero/Hero.jsx | 49 ++++++++++- .../Sponsors/styles/Sponsors.module.scss | 4 +- 4 files changed, 133 insertions(+), 26 deletions(-) diff --git a/src/data/liveEvents/omega/Accordion.json b/src/data/liveEvents/omega/Accordion.json index e4b8b448..1e742fb8 100644 --- a/src/data/liveEvents/omega/Accordion.json +++ b/src/data/liveEvents/omega/Accordion.json @@ -1,46 +1,89 @@ [ { - "title": "How to register?", - "content": "Be updated with our Instagram posts and FED site. A registration link will be provided once the registrations are on, or you can scan the QR code provided on our official Instagram account: https://www.instagram.com/fedkiit/." + "title": "What is Omega 5.0?", + "content": "Omega is FED’s flagship event, consisting of four unique segments focusing on developing entrepreneurship, strategic thinking, innovation, and leadership skills. It's open to students from KIIT and beyond." }, { - "title": "What is Omega?", - "content": "Omega is FED’s flagship event consisting of four different segments, focusing on the development of entrepreneurship and other skills." + "title": "Who can participate in Omega 5.0?", + "content": "Anyone can participate! You can register as an individual or as part of a team. You don’t have to be a KIIT student; students from other institutions are welcome too." }, { - "title": "What are the rewards?", - "content": "We have exciting prizes for the winners. Be updated with all our announcements and discover for yourself what exciting things we have in store for you all." + "title": "How can I register for Omega 5.0?", + "content": "The registration link is already available on our official Instagram page (@fedkiit). You can also register directly by visiting our website (fedkiit.com). Simply use the 'Sign in with Google' option to complete your registration quickly and securely!" + }, + { + "title": "Can the registration payment be done via the website?", + "content": "Yes, participants can easily register and pay directly on the official website." + }, + { + "title": "What is the early bird offer?", + "content": "Register before 10th August 2025 to avail the early bird price of ₹89 (instead of ₹129)." + }, + { + "title": "Is there a deadline for registration?", + "content": "Yes, check the official social media or website for the exact registration deadlines. Early bird offers end on 10th August 2025." + }, + { + "title": "Where do I find the schedule for the event?", + "content": "The main event will be held on 16th and 17th August.\nTIMINGS:\n10:00 AM – 2:00 PM\n3:00 PM – 6:00 PM" + }, + { + "title": "What are the main events in Omega 5.0?", + "content": "Fedpreneur Show (The FED Show): 16th Aug\nFed Premier League (FPL): 16th Aug\nStrategic Pivot Challenge: 17th Aug\nInnovate X Hackathon: 17th Aug" + }, + { + "title": "Can a single participant take part in all the events?", + "content": "Yes, contestants may compete in one or all events, alone or with a team." + }, + { + "title": "What is the Fedpreneur (FED) Show?", + "content": "This is a special segment where entrepreneurial journeys, stories, and strategies are shared and discussed, offering insights into starting up and innovating." + }, + { + "title": "What is the Fed Premier League (FPL)?", + "content": "An imitation of the Indian Premier League (IPL) cricket auction process, designed for a fun, team-based strategic experience." + }, + { + "title": "What is the Strategic Pivot Challenge?", + "content": "A competition requiring participants to solve unique and realistic business challenges using critical thinking and quick decision-making." + }, + { + "title": "What is Innovate X Hackathon?", + "content": "A hackathon challenging teams and individuals to come up with innovative solutions for real-world problems in a creative environment." + }, + { + "title": "How is this year’s Pitchers event different from previous editions?", + "content": "This year, Pitchers will involve analyzing failed business ideas and pitching innovative solutions to improve or revive them." }, { "title": "Is it necessary that all the team members belong to KIIT only?", - "content": "No, there is no such specific condition. You are free to select your teammates." + "content": "No. Teams can be made up of students from KIIT or any other institution." }, - - { - "title": "What is FPL?", - "content": "It is an imitation of Indian Premier League cricket auctions." + "title": "What is the maximum or minimum team size?", + "content": "Except for Fedpreneur Show, the rest are group events. But if you register alone and can’t find a friend to attend the event, don’t worry—we will combine you with someone prior to the event." }, { - "title": "How is the Pitchers event this year different from that of the previous editions?", - "content": "This time, the Pitchers can pitch as well as invest in other ideas." + "title": "What are the rewards/prizes?", + "content": "Exciting prizes await the winners! Stay connected with our official announcements for detailed updates about prizes." }, { - "title": "How to connect with the Organising Committee from the FED website?", - "content": "Our website has all the info related to our members, and you can directly head to any of our members' social media accounts to connect with them. If you have any doubts, you can ask us on https://www.instagram.com/fedkiit/ or visit https://www.fedkiit.com/ (our official website)." + "title": "How can I connect with the Organising Committee?", + "content": "All the organizing members’ details are available on the website. You can also reach out via our official Instagram or website for any queries." }, { - "title": "Is it possible for a single participant to participate in all the events of Omega?", - "content": "Yes, contestants can participate alone or as a team." + "title": "Where can I get the latest updates about Omega and its rounds?", + "content": "Follow @fedkiit on Instagram and keep checking fedkiit.com for real-time updates." }, { - "title": "How long will the events last on the given dates?", - "content": "DATES: 16th and 17th of August. TIMINGS: 9:00 AM – 2:00 PM, 3:00 PM – 6:00 PM." + "title": "Where will the events be conducted?", + "content": "The event locations will be shared soon." }, { - "title": "Can the registration payment be done via the website?", - "content": "Participants can register from the website itself." + "title": "What do I need to bring on event day?", + "content": "Bring a valid ID and any materials specified in your event’s instructions." } ] + \ No newline at end of file diff --git a/src/data/liveEvents/omega/Sponsor.json b/src/data/liveEvents/omega/Sponsor.json index 702d14d3..1326e4e9 100644 --- a/src/data/liveEvents/omega/Sponsor.json +++ b/src/data/liveEvents/omega/Sponsor.json @@ -4,9 +4,26 @@ "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c270e31a5b614a55a4e8_unstop.png" }, { - "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c26fb6206100bba45491_unlox.png" + "image": "https://ucarecdn.com/954dedb5-e0ae-490c-a91e-8811e65aaf0c/" + }, + + + { + "image": "https://ucarecdn.com/f6d3ea35-b99c-436b-bc8d-59b23cf6cc62/" + }, + { + "image": "https://ucarecdn.com/cd6865b6-ad3a-45c0-b0dc-08c47774b5f7/" + }, + + { + "image": "https://ucarecdn.com/8516d64f-1ecb-4747-a971-98265f992fa6/" + }, + + { + "image": "https://ucarecdn.com/5a1423e5-656b-4f8b-9c29-470e3c95f640/" } - + + ] diff --git a/src/sections/LiveEvents/Omega/Hero/Hero.jsx b/src/sections/LiveEvents/Omega/Hero/Hero.jsx index 44e9a286..11603d36 100644 --- a/src/sections/LiveEvents/Omega/Hero/Hero.jsx +++ b/src/sections/LiveEvents/Omega/Hero/Hero.jsx @@ -184,7 +184,9 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) { ]); return ( +
+ -

FED PRESENTS

+ +

FEDKIIT PRESENTS

@@ -207,7 +210,51 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) { src="https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6891e0b089a56fcddcf969e2_omega5.png" alt="Hero" /> + +
+ + + + POWERED BY + + + +
+ Remax Logo + +
+ REMAX + TEMPLE CITY +
+
+ +
+ + + + + +

Empowering Entrepreneurs, Energizing the Future

diff --git a/src/sections/LiveEvents/Omega/Sponsors/styles/Sponsors.module.scss b/src/sections/LiveEvents/Omega/Sponsors/styles/Sponsors.module.scss index e5d02119..9831d5af 100644 --- a/src/sections/LiveEvents/Omega/Sponsors/styles/Sponsors.module.scss +++ b/src/sections/LiveEvents/Omega/Sponsors/styles/Sponsors.module.scss @@ -34,11 +34,11 @@ } .sponsor { - margin: 20px; + margin: 40px; } .sponsor img { - max-width: 80px; + max-width: 90px; height: auto; } From fd3b24f94dbbd93a8a043e27f2e168d8e1c6ffa3 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Fri, 8 Aug 2025 17:21:50 +0530 Subject: [PATCH 06/44] upi id sourav --- src/features/Modals/Profile/Admin/PreviewForm.jsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 31e10e5d..5d696cbf 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -525,8 +525,8 @@ const handleDownloadQR = async () => { const handleShareQR = () => { // 🔁 Replace these with your actual values - const upiID = "8709217658@ybl"; // e.g., rudrika123@oksbi - const name = "Mr ANURAG PRASOON"; // e.g., Rudrika + const upiID = "6205888014@superyes"; // e.g., rudrika123@oksbi + const name = "SOURAV KIRAN ROUTRAY"; // e.g., Rudrika const amount = "89"; // e.g., ₹89 // ✅ UPI deep link format From 37cfbf57279f0a8c1ee6483ca9a2de1a811e1859 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 00:49:39 +0530 Subject: [PATCH 07/44] ritam pay link --- src/features/Modals/Profile/Admin/PreviewForm.jsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 5d696cbf..9702ff4c 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -525,8 +525,8 @@ const handleDownloadQR = async () => { const handleShareQR = () => { // 🔁 Replace these with your actual values - const upiID = "6205888014@superyes"; // e.g., rudrika123@oksbi - const name = "SOURAV KIRAN ROUTRAY"; // e.g., Rudrika + const upiID = "9609887167@ibl"; // e.g., rudrika123@oksbi + const name = "RITAM VASKAR"; // e.g., Rudrika const amount = "89"; // e.g., ₹89 // ✅ UPI deep link format From 5f4072db002fc58c7ed416b0399925410b6526c5 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 10:13:26 +0530 Subject: [PATCH 08/44] upi dynamic --- .../Modals/Profile/Admin/PreviewForm.jsx | 215 +++++++++--------- 1 file changed, 103 insertions(+), 112 deletions(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 9702ff4c..1ab2521f 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -163,7 +163,6 @@ const PreviewForm = ({ useEffect(() => { if (isSuccess) { - const participationType = eventData?.participationType; const successMessage = eventData?.successMessage; console.log(participationType); @@ -173,7 +172,7 @@ const PreviewForm = ({ setTeamCode(code); setTeamName(team); } - if (successMessage){ + if (successMessage) { setSuccessMessage(successMessage); } navigate("/Events"); @@ -343,10 +342,9 @@ const PreviewForm = ({ }; const handleSubmit = async () => { - if (!currentSection || !areRequiredFieldsFilled()) { - return; - } + return; + } const formData = new FormData(); const mediaFields = filterMediaFields() || []; @@ -421,7 +419,7 @@ const PreviewForm = ({ setcode(teamCode); // console.log("saved context teamCode:",recoveryCtx.teamCode) } - if (successMessage){ + if (successMessage) { setMessage(successMessage); } // console.log("consoling teamdata:", teamName, teamCode); @@ -487,122 +485,115 @@ const PreviewForm = ({ }; const renderPaymentScreen = () => { - const { eventType, receiverDetails, eventAmount } = formData; - -const handleDownloadQR = async () => { - try { - let imageUrl = - typeof receiverDetails.media === "string" - ? receiverDetails.media - : URL.createObjectURL(receiverDetails.media); - - let blobUrl = imageUrl; - - if (typeof receiverDetails.media === "string") { - // Fetch image and convert to blob for remote URLs - const response = await fetch(imageUrl); - const blob = await response.blob(); - blobUrl = URL.createObjectURL(blob); - } - - const link = document.createElement("a"); - link.href = blobUrl; - link.download = "qr-code.png"; - document.body.appendChild(link); - link.click(); - document.body.removeChild(link); - - // Revoke object URL to free memory - if (typeof receiverDetails.media !== "string") { - URL.revokeObjectURL(blobUrl); - } - } catch (error) { - console.error("Error downloading QR code:", error); - alert("Failed to download QR code."); - } -}; - + const { eventType, receiverDetails, eventAmount } = formData; + + const handleDownloadQR = async () => { + try { + let imageUrl = + typeof receiverDetails.media === "string" + ? receiverDetails.media + : URL.createObjectURL(receiverDetails.media); + + let blobUrl = imageUrl; + + if (typeof receiverDetails.media === "string") { + // Fetch image and convert to blob for remote URLs + const response = await fetch(imageUrl); + const blob = await response.blob(); + blobUrl = URL.createObjectURL(blob); + } -const handleShareQR = () => { - // 🔁 Replace these with your actual values - const upiID = "9609887167@ibl"; // e.g., rudrika123@oksbi - const name = "RITAM VASKAR"; // e.g., Rudrika - const amount = "89"; // e.g., ₹89 + const link = document.createElement("a"); + link.href = blobUrl; + link.download = "qr-code.png"; + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); - // ✅ UPI deep link format - const upiLink = `upi://pay?pa=${encodeURIComponent( - upiID - )}&pn=${encodeURIComponent(name)}&am=${encodeURIComponent( - amount - )}&cu=INR`; + // Revoke object URL to free memory + if (typeof receiverDetails.media !== "string") { + URL.revokeObjectURL(blobUrl); + } + } catch (error) { + console.error("Error downloading QR code:", error); + alert("Failed to download QR code."); + } + }; - // 🔁 Optional: Mobile-only guard - if (!/Android|iPhone/i.test(navigator.userAgent)) { - alert("UPI payment redirection works only on mobile devices."); - return; - } + const handleShareQR = () => { + // 🔁 Replace these with your actual values + const upiID = receiverDetails.upi; // e.g., rudrika123@oksbi + const name = "FED KIIT"; // e.g., Rudrika + const amount = "89"; // e.g., ₹89 + + // ✅ UPI deep link format + const upiLink = `upi://pay?pa=${encodeURIComponent( + upiID + )}&pn=${encodeURIComponent(name)}&am=${encodeURIComponent( + amount + )}&cu=INR`; + + // 🔁 Optional: Mobile-only guard + if (!/Android|iPhone/i.test(navigator.userAgent)) { + alert("UPI payment redirection works only on mobile devices."); + return; + } - // 🔗 Redirect to the UPI payment app - window.location.href = upiLink; -}; + // 🔗 Redirect to the UPI payment app + window.location.href = upiLink; + }; + if (eventType === "Paid" && currentSection.name === "Payment Details") { + return ( +
+ {receiverDetails.media && ( + {"QR-Code"} + )} + {/* ✅ Download & Share Buttons */} +
+ + +
- if (eventType === "Paid" && currentSection.name === "Payment Details") { - return ( -
- {receiverDetails.media && ( - {"QR-Code"} - )} - - {/* ✅ Download & Share Buttons */} -
- - + > + Make the payment of{" "} + ₹{eventAmount}{" "} + using QR-Code +

+ ); + } -

- Make the payment of{" "} - - ₹{eventAmount} - {" "} - using QR-Code or UPI Id{" "} - {receiverDetails.upi} -

-
- ); - } - - return null; -}; - + return null; + }; return ( <> @@ -757,4 +748,4 @@ const handleShareQR = () => { ); }; -export default PreviewForm; \ No newline at end of file +export default PreviewForm; From 2f81dd840db9cb345d1850edd4c12dd1bbc099f9 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 10:22:58 +0530 Subject: [PATCH 09/44] copy upi id --- .../Modals/Profile/Admin/PreviewForm.jsx | 183 ++++++++---------- 1 file changed, 86 insertions(+), 97 deletions(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 1ab2521f..298b2f8c 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -485,115 +485,104 @@ const PreviewForm = ({ }; const renderPaymentScreen = () => { - const { eventType, receiverDetails, eventAmount } = formData; - - const handleDownloadQR = async () => { - try { - let imageUrl = - typeof receiverDetails.media === "string" - ? receiverDetails.media - : URL.createObjectURL(receiverDetails.media); - - let blobUrl = imageUrl; - - if (typeof receiverDetails.media === "string") { - // Fetch image and convert to blob for remote URLs - const response = await fetch(imageUrl); - const blob = await response.blob(); - blobUrl = URL.createObjectURL(blob); - } + const { eventType, receiverDetails, eventAmount } = formData; - const link = document.createElement("a"); - link.href = blobUrl; - link.download = "qr-code.png"; - document.body.appendChild(link); - link.click(); - document.body.removeChild(link); + const handleDownloadQR = async () => { + try { + let imageUrl = + typeof receiverDetails.media === "string" + ? receiverDetails.media + : URL.createObjectURL(receiverDetails.media); - // Revoke object URL to free memory - if (typeof receiverDetails.media !== "string") { - URL.revokeObjectURL(blobUrl); - } - } catch (error) { - console.error("Error downloading QR code:", error); - alert("Failed to download QR code."); - } - }; + let blobUrl = imageUrl; - const handleShareQR = () => { - // 🔁 Replace these with your actual values - const upiID = receiverDetails.upi; // e.g., rudrika123@oksbi - const name = "FED KIIT"; // e.g., Rudrika - const amount = "89"; // e.g., ₹89 - - // ✅ UPI deep link format - const upiLink = `upi://pay?pa=${encodeURIComponent( - upiID - )}&pn=${encodeURIComponent(name)}&am=${encodeURIComponent( - amount - )}&cu=INR`; - - // 🔁 Optional: Mobile-only guard - if (!/Android|iPhone/i.test(navigator.userAgent)) { - alert("UPI payment redirection works only on mobile devices."); - return; + if (typeof receiverDetails.media === "string") { + const response = await fetch(imageUrl); + const blob = await response.blob(); + blobUrl = URL.createObjectURL(blob); } - // 🔗 Redirect to the UPI payment app - window.location.href = upiLink; - }; + const link = document.createElement("a"); + link.href = blobUrl; + link.download = "qr-code.png"; + document.body.appendChild(link); + link.click(); + document.body.removeChild(link); - if (eventType === "Paid" && currentSection.name === "Payment Details") { - return ( -
- {receiverDetails.media && ( - {"QR-Code"} - )} + if (typeof receiverDetails.media !== "string") { + URL.revokeObjectURL(blobUrl); + } + } catch (error) { + console.error("Error downloading QR code:", error); + alert("Failed to download QR code."); + } + }; - {/* ✅ Download & Share Buttons */} -
- - -
+ const handleCopyUPIID = () => { + if (receiverDetails.upi) { + navigator.clipboard.writeText(receiverDetails.upi) + .then(() => { + alert("UPI ID copied to clipboard!"); + }) + .catch(() => { + alert("Failed to copy UPI ID."); + }); + } + }; -

+ {receiverDetails.media && ( + {"QR-Code"} - Make the payment of{" "} - ₹{eventAmount}{" "} - using QR-Code -

+ /> + )} + + {/* ✅ Download & Copy Buttons */} +
+ +
- ); - } - return null; - }; +

+ Make the payment of{" "} + ₹{eventAmount}{" "} + using QR-Code or Pay using UPI ID:{" "} + {receiverDetails.upi} +

+
+ ); + } + + return null; +}; + return ( <> From 68077ecf622acff0eea7484d7a0e67ce3f9bddc1 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 11:07:40 +0530 Subject: [PATCH 10/44] hardcoded path for Omega 5.0 in omega page --- src/sections/LiveEvents/Omega/Hero/Hero.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sections/LiveEvents/Omega/Hero/Hero.jsx b/src/sections/LiveEvents/Omega/Hero/Hero.jsx index 44e9a286..416e60a3 100644 --- a/src/sections/LiveEvents/Omega/Hero/Hero.jsx +++ b/src/sections/LiveEvents/Omega/Hero/Hero.jsx @@ -64,7 +64,7 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) { (e) => e.info.relatedEvent === "null" )?.id; if (relatedEventId) { - setNavigatePath(`/Events/${relatedEventId}/Form`); + setNavigatePath(`/Events/6890fd2b2ee5496826b3a5a9/Form`); //hardcoded path for Omega 5.0 setShouldNavigate(true); } setTimeout(() => { From 1bd27bf011e18af16123f638a022e3695d14b079 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 12:50:32 +0530 Subject: [PATCH 11/44] tnc payment --- .../Profile/Admin/Form/NewForm/NewForm.jsx | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/src/sections/Profile/Admin/Form/NewForm/NewForm.jsx b/src/sections/Profile/Admin/Form/NewForm/NewForm.jsx index c7e4b16d..777ceb8d 100644 --- a/src/sections/Profile/Admin/Form/NewForm/NewForm.jsx +++ b/src/sections/Profile/Admin/Form/NewForm/NewForm.jsx @@ -722,6 +722,24 @@ function NewForm() { operator: "match", message: "UTR Number/Transaction ID must contain only numbers", }, + { + _id: nanoid(), + name: "Terms & Conditions", + type: "radio", + value: + "I acknowledge that all payments made are non-refundable once the form is submitted. For any further assistance contact fedkiit@gmail.com", + isRequired: true, + validations: [ + { + _id: nanoid(), + type: "length", + value: 1, + operator: "===", + message: + "You need to agree to the terms and conditions to proceed.", + }, + ], + }, ], }, ], From 3a928545c1d966d832bff7e4bfcace3acc52bbc2 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sat, 9 Aug 2025 13:07:05 +0530 Subject: [PATCH 12/44] no refund policy --- src/features/Modals/Profile/Admin/PreviewForm.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/features/Modals/Profile/Admin/PreviewForm.jsx b/src/features/Modals/Profile/Admin/PreviewForm.jsx index 298b2f8c..1d4ce420 100644 --- a/src/features/Modals/Profile/Admin/PreviewForm.jsx +++ b/src/features/Modals/Profile/Admin/PreviewForm.jsx @@ -574,7 +574,7 @@ const PreviewForm = ({ Make the payment of{" "} ₹{eventAmount}{" "} using QR-Code or Pay using UPI ID:{" "} - {receiverDetails.upi} + {receiverDetails.upi} (No Refund Policy)

); From 14a7969828e52027525a29a63e8d427074f0d65c Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Sat, 9 Aug 2025 22:57:32 +0530 Subject: [PATCH 13/44] omega static updates2 --- src/data/liveEvents/omega/Speakers.json | 12 +++++ src/data/liveEvents/omega/Sponsor.json | 2 +- .../LiveEvents/Omega/FedShow/FedShow.jsx | 22 ++++++++ .../Omega/FedShow/styles/FedShow.module.scss | 51 +++++++++++++++++++ src/sections/LiveEvents/Omega/Hero/Hero.jsx | 7 ++- 5 files changed, 92 insertions(+), 2 deletions(-) create mode 100644 src/data/liveEvents/omega/Speakers.json diff --git a/src/data/liveEvents/omega/Speakers.json b/src/data/liveEvents/omega/Speakers.json new file mode 100644 index 00000000..986b2158 --- /dev/null +++ b/src/data/liveEvents/omega/Speakers.json @@ -0,0 +1,12 @@ +[ + { + "name": "Navan Jaiswal", + "designation": "Co-Founder, CirclePe", + "image": "https://cdn.prod.website-files.com/663d1907e337de23e83c30b2/6896dceb9827aec266ae2793_navan2%201.png" + }, + { + "name": "Akhil Tripathi", + "designation": "Co-Founder, SciAstra", + "image": "https://ucarecdn.com/1643a559-39ba-481c-9ef4-2cfbcb4a405e/" + } +] \ No newline at end of file diff --git a/src/data/liveEvents/omega/Sponsor.json b/src/data/liveEvents/omega/Sponsor.json index 1326e4e9..b9f40ee0 100644 --- a/src/data/liveEvents/omega/Sponsor.json +++ b/src/data/liveEvents/omega/Sponsor.json @@ -20,7 +20,7 @@ }, { - "image": "https://ucarecdn.com/5a1423e5-656b-4f8b-9c29-470e3c95f640/" + "image": "https://ucarecdn.com/9c25edbf-d060-4740-bf3a-46538c412aca/" } diff --git a/src/sections/LiveEvents/Omega/FedShow/FedShow.jsx b/src/sections/LiveEvents/Omega/FedShow/FedShow.jsx index f50886e2..0a32a1a0 100644 --- a/src/sections/LiveEvents/Omega/FedShow/FedShow.jsx +++ b/src/sections/LiveEvents/Omega/FedShow/FedShow.jsx @@ -6,6 +6,8 @@ import { FaCalendarAlt, FaClock, FaMapMarkerAlt } from "react-icons/fa"; import { parse, differenceInMilliseconds } from "date-fns"; import fedShowImg from "../../../../assets/images/fedShow.svg"; import styles from "./styles/FedShow.module.scss"; +import speakersData from "../../../../data/liveEvents/omega/Speakers.json"; + function FedShow() { const [remainingTime, setRemainingTime] = useState(""); @@ -142,9 +144,29 @@ function FedShow() { {remainingTime ? `${remainingTime}` : btnTxt} +
+ +

+ OUR SPEAKERS +

+
+ + {speakersData.map((speaker, index) => ( +
+ {speaker.name} +

{speaker.name}

+

{speaker.designation}

+
+ ))} +
+ ); } diff --git a/src/sections/LiveEvents/Omega/FedShow/styles/FedShow.module.scss b/src/sections/LiveEvents/Omega/FedShow/styles/FedShow.module.scss index a1748205..34769efe 100644 --- a/src/sections/LiveEvents/Omega/FedShow/styles/FedShow.module.scss +++ b/src/sections/LiveEvents/Omega/FedShow/styles/FedShow.module.scss @@ -280,3 +280,54 @@ font-size: 85%; } } +.speakersContainer { + display: flex; + flex-wrap: wrap; + gap: 20px; + justify-content: center; // Center the cards in the row +} + +.speakerCard { + width: 250px; + padding: 40px; + border-radius: 10px; + text-align: center; + box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1); +} + +.speakerImage { + width: 100%; + height: auto; + border-radius: 8px; +} + +.speakerName { + font-size: 18px; + margin: 10px 0 5px; + font-weight: bold; +} + +.speakerDesignation { + font-size: 14px; + color: #828282; +} +.heading { + font-size: 2rem; + font-weight: bold; + margin-bottom: 20px; + padding-top: 60px; +} + +.our { + color: white; + padding-right: 2px; +} + +.speakers { + background: linear-gradient( + rgba(244, 43, 3, 0.84) 0%, + rgba(255, 190, 11, 0.84) 100% + ); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; +} \ No newline at end of file diff --git a/src/sections/LiveEvents/Omega/Hero/Hero.jsx b/src/sections/LiveEvents/Omega/Hero/Hero.jsx index 11603d36..c288ec03 100644 --- a/src/sections/LiveEvents/Omega/Hero/Hero.jsx +++ b/src/sections/LiveEvents/Omega/Hero/Hero.jsx @@ -232,14 +232,19 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) {
Remax Logo + +
REMAX From 328e4ef3b23f17ffc72ba4e186261a003150f6c6 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Sun, 10 Aug 2025 01:16:12 +0530 Subject: [PATCH 14/44] speakers omega --- src/App.jsx | 26 +++++++++++++++++++++++++ src/data/liveEvents/omega/Speakers.json | 11 +++++++++++ 2 files changed, 37 insertions(+) diff --git a/src/App.jsx b/src/App.jsx index 905dbaa5..6163bf62 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -140,6 +140,32 @@ function App() { authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && ( } /> )} + {/* Certificates Route */} + + {authCtx.user.access === "ADMIN" && ( + } /> + )} + + {authCtx.user.access === "ADMIN" && ( + } + /> + )} + + {authCtx.user.access === "ADMIN" && ( + } + /> + )} + + {authCtx.user.access === "ADMIN" && ( + } + /> + )} Date: Sun, 10 Aug 2025 19:51:51 +0530 Subject: [PATCH 15/44] omega static updates3 --- src/data/liveEvents/omega/Speakers.json | 2 +- src/data/liveEvents/omega/Sponsor.json | 10 +++++----- src/sections/LiveEvents/Omega/Hero/Hero.jsx | 2 +- 3 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/data/liveEvents/omega/Speakers.json b/src/data/liveEvents/omega/Speakers.json index 986b2158..0aa118a3 100644 --- a/src/data/liveEvents/omega/Speakers.json +++ b/src/data/liveEvents/omega/Speakers.json @@ -7,6 +7,6 @@ { "name": "Akhil Tripathi", "designation": "Co-Founder, SciAstra", - "image": "https://ucarecdn.com/1643a559-39ba-481c-9ef4-2cfbcb4a405e/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898aad13c4123f89f32e2f7_spkr.png" } ] \ No newline at end of file diff --git a/src/data/liveEvents/omega/Sponsor.json b/src/data/liveEvents/omega/Sponsor.json index b9f40ee0..b9781063 100644 --- a/src/data/liveEvents/omega/Sponsor.json +++ b/src/data/liveEvents/omega/Sponsor.json @@ -4,23 +4,23 @@ "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c270e31a5b614a55a4e8_unstop.png" }, { - "image": "https://ucarecdn.com/954dedb5-e0ae-490c-a91e-8811e65aaf0c/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898a8fe9671b22673e0f203_6894c26fb6206100bba45491_unlox.png" }, { - "image": "https://ucarecdn.com/f6d3ea35-b99c-436b-bc8d-59b23cf6cc62/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898aa1700b8583e9b0cea09_9a90e8c4f7933718410931fff16e1d67d0b1a728%20(1)-modified.png" }, { - "image": "https://ucarecdn.com/cd6865b6-ad3a-45c0-b0dc-08c47774b5f7/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898aa9f5a40aef2c05eb0ff_5c8f6c0dde7851b7ca6196a64c62a990e3c0f152-modified.png" }, { - "image": "https://ucarecdn.com/8516d64f-1ecb-4747-a971-98265f992fa6/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898a9a97a1a9e6121d28cfb_988e7f74979dc9924fdc07590a81526d0d19ddc4.png" }, { - "image": "https://ucarecdn.com/9c25edbf-d060-4740-bf3a-46538c412aca/" + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898a93894f03e50b49808ed_59482e2954cee1953c2f73d2989e3936c8e5e863.png" } diff --git a/src/sections/LiveEvents/Omega/Hero/Hero.jsx b/src/sections/LiveEvents/Omega/Hero/Hero.jsx index c288ec03..bbcaded0 100644 --- a/src/sections/LiveEvents/Omega/Hero/Hero.jsx +++ b/src/sections/LiveEvents/Omega/Hero/Hero.jsx @@ -238,7 +238,7 @@ function Hero({ ongoingEvents, isRegisteredInRelatedEvents, eventName }) { transform: "translateX(15px)" }}> Remax Logo Date: Tue, 12 Aug 2025 16:39:48 +0530 Subject: [PATCH 16/44] Attendance Page --- package-lock.json | 63 ++++ package.json | 2 + src/App.jsx | 2 + src/layouts/Profile/Sidebar/Sidebar.jsx | 65 ++-- src/pages/AttendancePage/AttendancePage.jsx | 296 ++++++++++++++++++ .../styles/AttendancePage.module.scss | 130 ++++++++ 6 files changed, 536 insertions(+), 22 deletions(-) create mode 100644 src/pages/AttendancePage/AttendancePage.jsx create mode 100644 src/pages/AttendancePage/styles/AttendancePage.module.scss diff --git a/package-lock.json b/package-lock.json index dcfd0b7b..676cc6b3 100644 --- a/package-lock.json +++ b/package-lock.json @@ -27,6 +27,7 @@ "date-fns": "^3.6.0", "framer-motion": "^11.2.10", "html2canvas": "^1.4.1", + "html5-qrcode": "^2.3.8", "js-confetti": "^0.12.0", "load-script": "^2.0.0", "lucide-react": "^0.379.0", @@ -50,6 +51,7 @@ "react-loading-indicators": "^0.2.3", "react-loading-skeleton": "^3.4.0", "react-oauth": "^0.0.1", + "react-qr-barcode-scanner": "^2.1.8", "react-quill": "^2.0.0", "react-router-dom": "^6.23.0", "react-router-hash-link": "^2.4.3", @@ -3426,6 +3428,28 @@ "url": "https://github.com/wojtekmaj/date-utils?sponsor=1" } }, + "node_modules/@zxing/library": { + "version": "0.21.3", + "resolved": "https://registry.npmjs.org/@zxing/library/-/library-0.21.3.tgz", + "integrity": "sha512-hZHqFe2JyH/ZxviJZosZjV+2s6EDSY0O24R+FQmlWZBZXP9IqMo7S3nb3+2LBWxodJQkSurdQGnqE7KXqrYgow==", + "license": "MIT", + "dependencies": { + "ts-custom-error": "^3.2.1" + }, + "engines": { + "node": ">= 10.4.0" + }, + "optionalDependencies": { + "@zxing/text-encoding": "~0.9.0" + } + }, + "node_modules/@zxing/text-encoding": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/@zxing/text-encoding/-/text-encoding-0.9.0.tgz", + "integrity": "sha512-U/4aVJ2mxI0aDNI8Uq0wEhMgY+u4CNtEb0om3+y3+niDAsoTCOB33UF0sxpzqzdqXLqmvc+vZyAt4O8pPdfkwA==", + "license": "(Unlicense OR Apache-2.0)", + "optional": true + }, "node_modules/abbrev": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", @@ -6620,6 +6644,12 @@ "node": ">=8.0.0" } }, + "node_modules/html5-qrcode": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/html5-qrcode/-/html5-qrcode-2.3.8.tgz", + "integrity": "sha512-jsr4vafJhwoLVEDW3n1KvPnCCXWaQfRng0/EEYk1vNcQGcG/htAdhJX0be8YyqMoSz7+hZvOZSTAepsabiuhiQ==", + "license": "Apache-2.0" + }, "node_modules/http-cache-semantics": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.1.tgz", @@ -11653,6 +11683,20 @@ "react-dom": "^15.5.x || ^16.x || ^17.x || ^18.x" } }, + "node_modules/react-qr-barcode-scanner": { + "version": "2.1.8", + "resolved": "https://registry.npmjs.org/react-qr-barcode-scanner/-/react-qr-barcode-scanner-2.1.8.tgz", + "integrity": "sha512-REbb+BWmPjvYIAZi6/iYrRupnK4e8d39m1YExhXk+XkKnz/aU/JembC1s+6ZO6jGVXnsGkh25Dwctcrm1HsK4g==", + "license": "MIT", + "dependencies": { + "@zxing/library": "^0.21.3", + "react-webcam": "^7.2.0" + }, + "peerDependencies": { + "react": ">=18.0.0", + "react-dom": ">=18.0.0" + } + }, "node_modules/react-quill": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/react-quill/-/react-quill-2.0.0.tgz", @@ -11863,6 +11907,16 @@ "react-dom": "^16.0.0 || ^17.0.0 || ^18.0.0" } }, + "node_modules/react-webcam": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/react-webcam/-/react-webcam-7.2.0.tgz", + "integrity": "sha512-xkrzYPqa1ag2DP+2Q/kLKBmCIfEx49bVdgCCCcZf88oF+0NPEbkwYk3/s/C7Zy0mhM8k+hpdNkBLzxg8H0aWcg==", + "license": "MIT", + "peerDependencies": { + "react": ">=16.2.0", + "react-dom": ">=16.2.0" + } + }, "node_modules/react-youtube": { "version": "10.1.0", "resolved": "https://registry.npmjs.org/react-youtube/-/react-youtube-10.1.0.tgz", @@ -13034,6 +13088,15 @@ "node": ">=0.10.0" } }, + "node_modules/ts-custom-error": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/ts-custom-error/-/ts-custom-error-3.3.1.tgz", + "integrity": "sha512-5OX1tzOjxWEgsr/YEUWSuPrQ00deKLh6D7OTWcvNHm12/7QPyRh8SYpyWvA4IZv8H/+GQWQEh/kwo95Q9OVW1A==", + "license": "MIT", + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/tslib": { "version": "2.6.2", "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz", diff --git a/package.json b/package.json index 9eb84216..cb088970 100644 --- a/package.json +++ b/package.json @@ -29,6 +29,7 @@ "date-fns": "^3.6.0", "framer-motion": "^11.2.10", "html2canvas": "^1.4.1", + "html5-qrcode": "^2.3.8", "js-confetti": "^0.12.0", "load-script": "^2.0.0", "lucide-react": "^0.379.0", @@ -52,6 +53,7 @@ "react-loading-indicators": "^0.2.3", "react-loading-skeleton": "^3.4.0", "react-oauth": "^0.0.1", + "react-qr-barcode-scanner": "^2.1.8", "react-quill": "^2.0.0", "react-router-dom": "^6.23.0", "react-router-hash-link": "^2.4.3", diff --git a/src/App.jsx b/src/App.jsx index 6163bf62..8f073d66 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -59,6 +59,7 @@ const Login = lazy(() => import("./pages/Authentication/Login/Login")); const OTPInput = lazy(() => import("./authentication/Login/ForgotPassword/OTPInput") ); +const AttendancePage = lazy(() => import('./pages/AttendancePage/AttendancePage')); const MainLayout = () => { const location = useLocation(); @@ -184,6 +185,7 @@ function App() { element={[]} /> )} + } /> )} { setimagePrv(url); }; - const renderBlogMenu = () => (
handleChange("Blogs")} + onClick={() => handleChange("Blogs")} + style={{ + background: activepage === "Blogs" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Blogs" ? "text" : "initial", + backgroundClip: activepage === "Blogs" ? "text" : "initial", + color: activepage === "Blogs" ? "transparent" : "inherit", + }} + > + - {" "} - Blogs -
- ) + />{" "} + Blogs +
+ ); const renderAdminMenu = () => ( <>
{ />{" "} Form
- +
handleChange("Members")} style={{ @@ -143,6 +143,27 @@ const Sidebar = ({ activepage, handleChange }) => { />{" "} Members
+ +
handleChange("Attendance")} + style={{ + background: + activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + marginLeft: "-6px", + }} + > + {" "} + Attendance +
); @@ -203,8 +224,8 @@ const Sidebar = ({ activepage, handleChange }) => {
- {designation === "Admin" && renderAdminMenu() } - {(designation === "Admin" || authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && renderBlogMenu() } + {designation === "Admin" && renderAdminMenu()} + {(designation === "Admin" || authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && renderBlogMenu()} {designation !== "Admin" && (
handleChange("events")} @@ -213,9 +234,9 @@ const Sidebar = ({ activepage, handleChange }) => { Event - +
- + )}
{ + const [ongoingEvents, setOngoingEvents] = useState([]); + const [pastEvents, setPastEvents] = useState([]); + const [isLoading, setIsLoading] = useState(true); + const [error, setError] = useState(null); + const [showScanner, setShowScanner] = useState(false); + const [selectedEventId, setSelectedEventId] = useState(null); + const [scanner, setScanner] = useState(null); + const authCtx = useContext(AuthContext); + + useEffect(() => { + const fetchEvents = async () => { + try { + const response = await api.get("/api/form/getAllForms"); + if (response.status === 200) { + const fetchedEvents = response.data.events; + + const sortedEvents = fetchedEvents.sort((a, b) => { + const priorityA = parseInt(a.info.eventPriority, 10); + const priorityB = parseInt(b.info.eventPriority, 10); + const dateA = new Date(a.info.eventDate); + const dateB = new Date(b.info.eventDate); + const titleA = a.info.eventTitle || ""; + const titleB = b.info.eventTitle || ""; + + if (priorityA !== priorityB) return priorityA - priorityB; + if (dateA.getTime() !== dateB.getTime()) return dateA - dateB; + return titleA.localeCompare(titleB); + }); + + const ongoing = sortedEvents.filter(e => !e.info.isEventPast); + const past = sortedEvents + .filter(e => e.info.isEventPast) + .sort((a, b) => new Date(b.info.eventDate) - new Date(a.info.eventDate)); + + setOngoingEvents(ongoing); + setPastEvents(past); + } else { + setError("Error fetching events"); + } + } catch (err) { + console.error("Error fetching events:", err); + setError("Error fetching events"); + } finally { + setIsLoading(false); + } + }; + fetchEvents(); + }, []); + + const initializeScanner = () => { + const qrScanner = new Html5QrcodeScanner( + "qr-reader", + { + fps: 10, + qrbox: { width: 250, height: 250 }, + aspectRatio: 1, + supportedScanTypes: [Html5QrcodeScanType.SCAN_TYPE_CAMERA] // ✅ FIXED + }, + false + ); + + qrScanner.render(onScanSuccess, onScanFailure); + setScanner(qrScanner); + }; + + const onScanSuccess = async (decodedText) => { + try { + const response = await api.post( + `/api/attendance/verify`, + { + eventId: selectedEventId, + qrData: decodedText, + }, + { + headers: { + Authorization: `Bearer ${authCtx.token}`, + }, + } + ); + + if (response.status === 200) { + Alert({ + type: "success", + message: "Attendance marked successfully!", + position: "top-right", + }); + if (scanner) { + scanner.clear(); + } + setShowScanner(false); + } + } catch (error) { + Alert({ + type: "error", + message: error.response?.data?.message || "Failed to verify QR code", + position: "top-right", + }); + } + }; + + const onScanFailure = (error) => { + console.warn(`QR Code scanning failed: ${error}`); + }; + + const handleScanQR = (eventId) => { + setSelectedEventId(eventId); + setShowScanner(true); + }; + + const handleDownloadAttendance = async (eventId) => { + try { + const response = await api.get(`/api/attendance/download/${eventId}`, { + headers: { Authorization: `Bearer ${authCtx.token}` }, + responseType: "blob", + }); + const blob = new Blob([response.data], { type: "text/csv" }); + const url = window.URL.createObjectURL(blob); + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", `attendance_${eventId}.csv`); + document.body.appendChild(link); + link.click(); + link.remove(); + window.URL.revokeObjectURL(url); + + Alert({ + type: "success", + message: "Attendance file downloaded successfully!", + position: "top-right", + }); + } catch (error) { + Alert({ + type: "error", + message: "Failed to download attendance file", + position: "top-right", + }); + console.error("Download error:", error); + } + }; + + const renderOngoingActions = (event) => ( +
+ + +
+ ); + + const renderPastActions = (event) => ( +
+ +
+ ); + + useEffect(() => { + if (showScanner) { + initializeScanner(); + } + return () => { + if (scanner) { + scanner.clear(); + } + }; + }, [showScanner]); + + if (isLoading) { + return ( + + ); + } + + if (error) { + return
{error}
; + } + + return ( +
+

Event Attendance

+ + {showScanner && ( +
+
+ +

Scan QR Code

+
+
+
+
+
+ )} + + {/* Ongoing Events */} + {ongoingEvents.length > 0 && ( + <> +

Ongoing Events

+
+ {ongoingEvents.map((event) => ( +
+ {}} // ✅ FIXED: Always pass a function + customStyles={{ + eventname: { fontSize: "1.2rem" }, + registerbtn: { width: "8rem", fontSize: ".721rem" }, + eventnamep: { fontSize: "0.7rem" }, + }} + /> +
+ ))} +
+ + )} + + {/* Past Events */} + {pastEvents.length > 0 && ( + <> +

Past Events

+
+ {pastEvents.map((event) => ( +
+ {}} // ✅ FIXED + customStyles={{ + eventname: { fontSize: "1.2rem" }, + registerbtn: { width: "8rem", fontSize: ".721rem" }, + eventnamep: { fontSize: "0.7rem" }, + }} + /> +
+ ))} +
+ + )} +
+ ); +}; + +export default AttendancePage; diff --git a/src/pages/AttendancePage/styles/AttendancePage.module.scss b/src/pages/AttendancePage/styles/AttendancePage.module.scss new file mode 100644 index 00000000..8bac619c --- /dev/null +++ b/src/pages/AttendancePage/styles/AttendancePage.module.scss @@ -0,0 +1,130 @@ +.container { + padding: 20px; + + h2 { + color: var(--primary); + margin-bottom: 20px; + } +} + +.eventGrid { + display: grid; + grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); + gap: 20px; + padding: 20px; +} + +.eventWrapper { + position: relative; +} + +.actionButtons { + display: flex; + justify-content: space-between; + gap: 10px; + margin-top: 10px; + padding: 10px; + + button { + flex: 1; + padding: 8px; + border-radius: 4px; + font-size: 14px; + + &:hover { + transform: translateY(-2px); + transition: transform 0.2s ease; + } + + &:last-child { + background: #FF8A00; + color: white; + border: none; + + &:hover { + background: rgba(255, 138, 0, 0.9); + } + } + } +} + +.scannerModal { + position: fixed; + top: 0; + left: 0; + right: 0; + bottom: 0; + background: rgba(0, 0, 0, 0.85); + display: flex; + justify-content: center; + align-items: center; + z-index: 1000; +} + +.scannerContent { + background: #1a1a1a; + padding: 2rem; + border-radius: 10px; + width: 90%; + max-width: 500px; + position: relative; + + .closeButton { + position: absolute; + top: -15px; + right: -15px; + background: var(--primary); + border: none; + border-radius: 50%; + width: 30px; + height: 30px; + display: flex; + align-items: center; + justify-content: center; + cursor: pointer; + color: white; + font-size: 1.2rem; + + &:hover { + transform: scale(1.1); + transition: transform 0.2s ease; + } + } + + .scannerTitle { + color: white; + text-align: center; + margin-bottom: 1rem; + font-size: 1.2rem; + } + + .scannerArea { + border: 2px solid var(--primary); + border-radius: 8px; + overflow: hidden; + margin: 1rem 0; + + #qr-reader { + width: 100%; + + video { + width: 100% !important; + border-radius: 6px; + } + + button { + padding: 8px 16px; + background: var(--primary); + color: white; + border: none; + border-radius: 4px; + margin: 8px; + cursor: pointer; + + &:hover { + opacity: 0.9; + } + } + } + } +} From fd941d855b316bd6b7469a7ccb64c0117b721dbd Mon Sep 17 00:00:00 2001 From: Rudrika Date: Tue, 12 Aug 2025 20:18:20 +0530 Subject: [PATCH 17/44] Update --- src/pages/AttendancePage/AttendancePage.jsx | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/src/pages/AttendancePage/AttendancePage.jsx b/src/pages/AttendancePage/AttendancePage.jsx index 19dd4181..e2d2b695 100644 --- a/src/pages/AttendancePage/AttendancePage.jsx +++ b/src/pages/AttendancePage/AttendancePage.jsx @@ -158,10 +158,18 @@ const AttendancePage = () => { +
); @@ -249,7 +257,7 @@ const AttendancePage = () => { showRegisterButton={false} showShareButton={false} additionalContent={renderOngoingActions(event)} - onOpen={() => {}} // ✅ FIXED: Always pass a function + onOpen={() => { }} // ✅ FIXED: Always pass a function customStyles={{ eventname: { fontSize: "1.2rem" }, registerbtn: { width: "8rem", fontSize: ".721rem" }, @@ -277,7 +285,7 @@ const AttendancePage = () => { showRegisterButton={false} showShareButton={false} additionalContent={renderPastActions(event)} - onOpen={() => {}} // ✅ FIXED + onOpen={() => { }} // ✅ FIXED customStyles={{ eventname: { fontSize: "1.2rem" }, registerbtn: { width: "8rem", fontSize: ".721rem" }, From 0f03dce29dc9bbe5e9932dea8d1d5185121541d7 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Tue, 12 Aug 2025 21:39:46 +0530 Subject: [PATCH 18/44] event card updates --- src/components/EventCard/EventCard.jsx | 29 +- .../EventCard/styles/EventCard.module.scss | 31 +- .../TeamDetailsModal/TeamDetailsModal.jsx | 221 +++++++++++ .../Modals/Event/TeamDetailsModal/index.jsx | 1 + .../style/TeamDetailsModal.module.scss | 373 ++++++++++++++++++ src/features/Modals/index.jsx | 2 +- 6 files changed, 649 insertions(+), 8 deletions(-) create mode 100644 src/features/Modals/Event/TeamDetailsModal/TeamDetailsModal.jsx create mode 100644 src/features/Modals/Event/TeamDetailsModal/index.jsx create mode 100644 src/features/Modals/Event/TeamDetailsModal/style/TeamDetailsModal.module.scss diff --git a/src/components/EventCard/EventCard.jsx b/src/components/EventCard/EventCard.jsx index 563f6e69..2e6b4548 100644 --- a/src/components/EventCard/EventCard.jsx +++ b/src/components/EventCard/EventCard.jsx @@ -9,13 +9,14 @@ import shareOutline from "../../assets/images/shareOutline.svg"; import { PiClockCountdownDuotone } from "react-icons/pi"; import { IoIosLock, IoIosStats } from "react-icons/io"; import { MdGroups } from "react-icons/md"; -import { FaUser, FaRupeeSign } from "react-icons/fa"; +import { FaUser, FaRupeeSign, FaEye } from "react-icons/fa"; import { parse, differenceInMilliseconds, formatDistanceToNow } from "date-fns"; import { Button } from "../Core"; import AuthContext from "../../context/AuthContext"; import EventCardSkeleton from "../../layouts/Skeleton/EventCard/EventCardSkeleton"; import { Blurhash } from "react-blurhash"; import { Alert, MicroLoading } from "../../microInteraction"; +import { TeamDetailsModal } from "../../features/Modals"; // import useUnixTimestamp from "../../utils/hooks/useUnixTimeStamp"; const EventCard = (props) => { @@ -51,6 +52,7 @@ const EventCard = (props) => { const [navigatePath, setNavigatePath] = useState("/"); const [isLocked, setIsLocked] = useState(false); const [alert, setAlert] = useState(null); + const [isTeamDetailsOpen, setIsTeamDetailsOpen] = useState(false); useEffect(() => { if (shouldNavigate) { @@ -509,6 +511,22 @@ const EventCard = (props) => {
)} + + {/* See Team Details Button - Only show for team events when user is registered */} + {type === "ongoing" && + info.participationType === "Team" && + btnTxt === "Already Registered" && + authCtx.isLoggedIn && ( +
+ +
+ )}
@@ -578,6 +596,15 @@ const EventCard = (props) => { />
)} + + {/* Team Details Modal */} + setIsTeamDetailsOpen(false)} + formId={data.id} + eventTitle={info.eventTitle} + /> +
); diff --git a/src/components/EventCard/styles/EventCard.module.scss b/src/components/EventCard/styles/EventCard.module.scss index c8b70801..e9c384d9 100644 --- a/src/components/EventCard/styles/EventCard.module.scss +++ b/src/components/EventCard/styles/EventCard.module.scss @@ -180,16 +180,14 @@ ) ); display: inline-flex; - padding: 0.6rem 0.8rem; + padding: 0.4rem 0.8rem; justify-content: center; align-items: center; - margin-top: 1rem; - gap: 0.3rem; - // width: 10rem; + margin-left: 0.5rem; /* 👈 gap between "Free" and button */ cursor: progress; outline: none; border: none; - font-size: 0.9rem; + font-size: 0.85rem; color: #fff; } @@ -245,6 +243,27 @@ a { width: 44%; } +.teamDetailsBtn { +width: 30px; + height: 35px; + padding-bottom: 10px; + background-color: transparent; + border: none; + border-radius: 50%; + display: flex; + align-items: center; + justify-content: center; + cursor: pointer; + &:hover { + + transform: translateY(-1px); + } + + &:active { + transform: translateY(0); + } +} + @media (max-width: 600px) { .backbtn { margin-top: 0.2rem; @@ -286,4 +305,4 @@ a { align-items: center; margin-top: 0.1rem; } -} +} \ No newline at end of file diff --git a/src/features/Modals/Event/TeamDetailsModal/TeamDetailsModal.jsx b/src/features/Modals/Event/TeamDetailsModal/TeamDetailsModal.jsx new file mode 100644 index 00000000..0315153d --- /dev/null +++ b/src/features/Modals/Event/TeamDetailsModal/TeamDetailsModal.jsx @@ -0,0 +1,221 @@ +import React, { useState, useEffect } from "react"; +import PropTypes from "prop-types"; +import { MdClose, MdGroups, MdPerson, MdEmail, MdSchool, MdCalendarToday } from "react-icons/md"; +import { FaCopy, FaCheck } from "react-icons/fa"; +import { api } from "../../../../services"; +import { Alert, MicroLoading } from "../../../../microInteraction"; +import styles from "./style/TeamDetailsModal.module.scss"; + +const TeamDetailsModal = ({ isOpen, onClose, formId, eventTitle }) => { + const [teamDetails, setTeamDetails] = useState(null); + const [isLoading, setIsLoading] = useState(false); + const [error, setError] = useState(null); + const [copiedCode, setCopiedCode] = useState(false); + + useEffect(() => { + if (isOpen && formId) { + fetchTeamDetails(); + } + }, [isOpen, formId]); + + useEffect(() => { + if (error) { + Alert({ + type: "error", + message: error, + position: "bottom-right", + duration: 3000, + }); + setError(null); + } + }, [error]); + + const fetchTeamDetails = async () => { + try { + setIsLoading(true); + setError(null); + + const response = await api.get(`/api/form/teamDetails/${formId}`, { + headers: { + Authorization: `Bearer ${localStorage.getItem("token")}`, + }, + }); + + if (response.status === 200) { + setTeamDetails(response.data.data); + } else { + setError(response.data.message || "Failed to fetch team details"); + } + } catch (err) { + console.error("Error fetching team details:", err); + setError( + err.response?.data?.message || "Failed to fetch team details. Please try again." + ); + } finally { + setIsLoading(false); + } + }; + + const copyTeamCode = async () => { + try { + await navigator.clipboard.writeText(teamDetails.teamCode); + setCopiedCode(true); + setTimeout(() => setCopiedCode(false), 2000); + + Alert({ + type: "success", + message: "Team code copied to clipboard!", + position: "bottom-right", + duration: 2000, + }); + } catch (err) { + console.error("Failed to copy team code:", err); + setError("Failed to copy team code to clipboard"); + } + }; + + const handleBackdropClick = (e) => { + if (e.target === e.currentTarget) { + onClose(); + } + }; + + if (!isOpen) return null; + + return ( +
+
+
+

Team Details

+ +
+ +
+ {isLoading ? ( +
+ +

Loading team details...

+
+ ) : teamDetails ? ( + <> +
+

{eventTitle || teamDetails.eventTitle}

+
+ +
+
+ +

Team Information

+
+ +
+
+ Team Name: + {teamDetails.teamName} +
+ +
+ Team Code: +
+ {teamDetails.teamCode} + +
+
+ +
+ Team Size: + + {teamDetails.teamSize} / {teamDetails.maxTeamSize} + +
+
+
+ +
+
+ +

Team Members ({teamDetails.members.length})

+
+ +
+ {teamDetails.members.map((member, index) => ( +
+
+ {member.img ? ( + {member.name} + ) : ( +
+ {member.name?.charAt(0)?.toUpperCase() || "?"} +
+ )} +
+ +
+
{member.name || "Unknown"}
+ +
+
+ + {member.email} +
+ + {member.rollNumber && ( +
+ + Roll: {member.rollNumber} +
+ )} + + {member.college && ( +
+ + {member.college} +
+ )} + + {member.year && ( +
+ + Year: {member.year} +
+ )} +
+
+
+ ))} +
+
+ + ) : ( +
+

No team details available

+
+ )} +
+ +
+ +
+
+
+ ); +}; + +TeamDetailsModal.propTypes = { + isOpen: PropTypes.bool.isRequired, + onClose: PropTypes.func.isRequired, + formId: PropTypes.string.isRequired, + eventTitle: PropTypes.string, +}; + +export default TeamDetailsModal; \ No newline at end of file diff --git a/src/features/Modals/Event/TeamDetailsModal/index.jsx b/src/features/Modals/Event/TeamDetailsModal/index.jsx new file mode 100644 index 00000000..4e2040b1 --- /dev/null +++ b/src/features/Modals/Event/TeamDetailsModal/index.jsx @@ -0,0 +1 @@ +export { default } from './TeamDetailsModal'; \ No newline at end of file diff --git a/src/features/Modals/Event/TeamDetailsModal/style/TeamDetailsModal.module.scss b/src/features/Modals/Event/TeamDetailsModal/style/TeamDetailsModal.module.scss new file mode 100644 index 00000000..e82c50f0 --- /dev/null +++ b/src/features/Modals/Event/TeamDetailsModal/style/TeamDetailsModal.module.scss @@ -0,0 +1,373 @@ +.modalOverlay { + position: fixed; + top: 0; + left: 0; + right: 0; + bottom: 0; + background-color: rgba(0, 0, 0, 0.7); + display: flex; + justify-content: center; + align-items: center; + z-index: 1000; + padding: 20px; +} + +.modal { + background: rgb(28, 28, 28); + border-radius: 12px; + max-width: 600px; + width: 100%; + max-height: 90vh; + overflow-y: auto; + scrollbar-width: none; + box-shadow: 0 20px 40px rgba(0, 0, 0, 0.3); + animation: slideIn 0.3s ease-out; +} + +@keyframes slideIn { + from { + opacity: 0; + transform: translateY(-20px) scale(0.95); + } + to { + opacity: 1; + transform: translateY(0) scale(1); + } +} + +.modalHeader { + display: flex; + justify-content: space-between; + align-items: center; + padding: 0px 15px; + border-bottom: 1px solid #000000; + background: linear-gradient(135deg, #f97507 0%, #ff6b35 100%); + color: white; + border-radius: 12px 12px 0 0; + + h2 { + margin: 0; + font-size: 1.5rem; + font-weight: 600; + } +} + +.closeButton { + background: none; + border: none; + color: rgb(0, 0, 0); + cursor: pointer; + padding: 8px ; + border-radius: 50%; + transition: background-color 0.2s; + display: flex; + align-items: center; + justify-content: center; + + &:hover { + background-color: rgba(255, 255, 255, 0.2); + } +} + +.modalContent { + padding: 24px; +} + +.loadingContainer { + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; + padding: 40px 20px; + text-align: center; + + p { + margin-top: 16px; + color: #6b7280; + font-size: 1rem; + } +} + +.eventInfo { + text-align: center; + margin-bottom: 24px; + padding: 16px; + background: none; + border-radius: 8px; + + h3 { + margin: 0; + background: linear-gradient( + rgba(244, 43, 3, 0.84) 0%, + rgba(255, 190, 11, 0.84) 100% + ); + -webkit-background-clip: text; + -webkit-text-fill-color: transparent; + font-size: 1.25rem; + font-weight: 600; + } +} + +.teamInfo { + margin-bottom: 24px; + padding: 20px; + background: #232323; + border-radius: 8px; + border: 1px solid #dd5c00; +} + +.teamHeader { + display: flex; + align-items: center; + gap: 12px; + margin-bottom: 16px; + + h4 { + margin: 0; + color: #c8c8c8; + font-size: 1.125rem; + font-weight: 600; + } +} + +.teamDetails { + display: flex; + flex-direction: column; + gap: 16px; +} + +.teamDetailItem { + display: flex; + justify-content: space-between; + align-items: center; + padding: 12px 16px; + background: rgb(29, 29, 29); + border-radius: 6px; + border: 1px solid #585858; + + .label { + font-weight: 600; + color: #777676; + min-width: 100px; + } + + .value { + color: #cc5c06; + font-weight: 500; + } +} + +.teamCodeContainer { + display: flex; + align-items: center; + gap: 12px; +} + +.teamCode { + font-family: 'Courier New', monospace; + font-weight: 600; + color: #f97507; + background: #474747; + padding: 6px 12px; + border-radius: 4px; + border: 1px solid #da7603; + font-size: 0.875rem; +} + +.copyButton { + background: #f97507; + color: white; + border: none; + padding: 8px; + border-radius: 4px; + cursor: pointer; + transition: background-color 0.2s; + display: flex; + align-items: center; + justify-content: center; + + &:hover { + background: #ea580c; + } + + &:active { + transform: scale(0.95); + } +} + +.membersSection { + margin-bottom: 24px; +} + +.membersHeader { + display: flex; + align-items: center; + gap: 12px; + margin-bottom: 16px; + + h4 { + margin: 0; + color: #d3d1d1; + font-size: 1.125rem; + font-weight: 600; + } +} + +.membersList { + display: flex; + flex-direction: column; + gap: 16px; +} + +.memberCard { + display: flex; + gap: 16px; + padding: 16px; + background: #232323; + border-radius: 8px; + border: 1px solid #e27100; + transition: box-shadow 0.2s; + + &:hover { + box-shadow: 0 4px 12px rgba(0, 0, 0, 0.1); + } +} + +.memberAvatar { + flex-shrink: 0; + width: 60px; + height: 60px; + border-radius: 50%; + overflow: hidden; + border: 2px solid #f97507; + + img { + width: 100%; + height: 100%; + object-fit: cover; + } +} + +.avatarPlaceholder { + width: 100%; + height: 100%; + background: linear-gradient(135deg, #f97507 0%, #ff6b35 100%); + color: white; + display: flex; + align-items: center; + justify-content: center; + font-size: 1.5rem; + font-weight: 600; +} + +.memberInfo { + flex: 1; + min-width: 0; +} + +.memberName { + margin: 0 0 8px 0; + color: #afafaf; + font-size: 1.125rem; + font-weight: 600; +} + +.memberDetails { + display: flex; + flex-direction: column; + gap: 6px; +} + +.memberDetail { + display: flex; + align-items: center; + gap: 8px; + color: #6b7280; + font-size: 0.875rem; + + svg { + color: #9ca3af; + flex-shrink: 0; + } +} + +.errorContainer { + text-align: center; + padding: 40px 20px; + color: #6b7280; + + p { + margin: 0; + font-size: 1rem; + } +} + +.modalFooter { + padding: 20px 24px; + border-top: 1px solid #202020; + display: flex; + justify-content: flex-end; + background: #131313; + border-radius: 0 0 12px 12px; +} + +.closeBtn { + background: #d06202; + color: white; + border: none; + padding: 10px 20px; + border-radius: 6px; + cursor: pointer; + font-size: 0.875rem; + font-weight: 500; + transition: background-color 0.2s; + + &:hover { + background: #be4f01; + } +} + +// Responsive design +@media (max-width: 640px) { + .modal { + max-width: 95vw; + max-height: 65vh; + margin: 10px; + } + + .modalContent { + padding: 16px; + } + + .modalHeader { + padding: 0px 20px; + + h2 { + font-size: 1.25rem; + } + } + + .teamDetailItem { + flex-direction: column; + align-items: flex-start; + gap: 8px; + + .label { + min-width: auto; + } + } + + .memberCard { + flex-direction: column; + text-align: center; + gap: 12px; + } + + .memberAvatar { + align-self: center; + } + + .memberDetails { + align-items: center; + } +} \ No newline at end of file diff --git a/src/features/Modals/index.jsx b/src/features/Modals/index.jsx index 6f0fc365..cdb77e37 100644 --- a/src/features/Modals/index.jsx +++ b/src/features/Modals/index.jsx @@ -9,9 +9,9 @@ export { default as EventModal } from './Event/EventModal/EventModal'; export { default as LiveEventPopup } from './Event/LiveEventPopup/LiveEventPopup'; export { default as ShareModal } from './Event/ShareModal/ShareModal'; export { default as EventStats } from './Event/EventStats/EventStats'; +export { default as TeamDetailsModal } from './Event/TeamDetailsModal'; // Admin and Form Modals export { default as PreviewForm } from './Profile/Admin/PreviewForm'; export { default as SectionModal } from './Profile/Admin/SectionModal'; - From 878774868ae7b20059e608fa5474c80d68f84b98 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Wed, 13 Aug 2025 11:55:04 +0530 Subject: [PATCH 19/44] attendancepageandverification --- FED-Backend | 1 + package-lock.json | 908 +++++------------- package.json | 2 + src/components/EventCard/EventCard.jsx | 45 + .../EventCard/styles/EventCard.module.scss | 27 + .../Modals/Event/QRCodeModal/QRCodeModal.jsx | 156 +++ .../Modals/Event/QRCodeModal/index.jsx | 1 + .../styles/QRCodeModal.module.scss | 396 ++++++++ src/features/Modals/index.jsx | 1 + src/pages/AttendancePage/AttendancePage.jsx | 97 +- 10 files changed, 921 insertions(+), 713 deletions(-) create mode 160000 FED-Backend create mode 100644 src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx create mode 100644 src/features/Modals/Event/QRCodeModal/index.jsx create mode 100644 src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss diff --git a/FED-Backend b/FED-Backend new file mode 160000 index 00000000..4258de3d --- /dev/null +++ b/FED-Backend @@ -0,0 +1 @@ +Subproject commit 4258de3d3387ad763c4e6ee77d51e94be28c44c4 diff --git a/package-lock.json b/package-lock.json index 676cc6b3..c5098011 100644 --- a/package-lock.json +++ b/package-lock.json @@ -35,6 +35,8 @@ "motion": "^11.13.1", "nanoid": "^5.0.7", "prop-types": "^15.8.1", + "qrcode": "^1.5.4", + "qrcode.react": "^4.2.0", "react": "^18.2.0", "react-avatar-editor": "^13.0.2", "react-blurhash": "^0.3.0", @@ -1543,20 +1545,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/console/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/console/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1572,22 +1560,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/console/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/console/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/console/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1654,20 +1626,6 @@ } } }, - "node_modules/@jest/core/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/core/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1683,22 +1641,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/core/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/core/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/core/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1827,20 +1769,6 @@ } } }, - "node_modules/@jest/reporters/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/reporters/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1856,22 +1784,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/reporters/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/reporters/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/reporters/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1968,20 +1880,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/transform/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/transform/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1997,22 +1895,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/transform/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/transform/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/transform/node_modules/convert-source-map": { "version": "1.9.0", "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", @@ -2053,20 +1935,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/types/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/types/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -2082,22 +1950,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/types/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/types/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/types/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -3575,6 +3427,21 @@ "node": ">=8" } }, + "node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "license": "MIT", + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, "node_modules/anymatch": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", @@ -3835,20 +3702,6 @@ "@babel/core": "^7.8.0" } }, - "node_modules/babel-jest/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/babel-jest/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -3864,22 +3717,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/babel-jest/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/babel-jest/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/babel-jest/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -4589,36 +4426,6 @@ "node": ">=12" } }, - "node_modules/cliui/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/cliui/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/cliui/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/cliui/node_modules/wrap-ansi": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", @@ -4674,6 +4481,24 @@ "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz", "integrity": "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==" }, + "node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "license": "MIT", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "license": "MIT" + }, "node_modules/color-support": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz", @@ -4957,6 +4782,15 @@ } } }, + "node_modules/decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/decompress-response": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", @@ -5115,6 +4949,12 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, + "node_modules/dijkstrajs": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/dijkstrajs/-/dijkstrajs-1.0.3.tgz", + "integrity": "sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==", + "license": "MIT" + }, "node_modules/dir-glob": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", @@ -5603,21 +5443,6 @@ "url": "https://opencollective.com/eslint" } }, - "node_modules/eslint/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/eslint/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -5634,24 +5459,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/eslint/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/eslint/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, "node_modules/eslint/node_modules/escape-string-regexp": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", @@ -7569,20 +7376,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-circus/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-circus/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7598,22 +7391,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-circus/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-circus/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-circus/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7666,20 +7443,6 @@ } } }, - "node_modules/jest-cli/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-cli/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7695,22 +7458,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-cli/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-cli/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-cli/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7774,20 +7521,6 @@ } } }, - "node_modules/jest-config/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-config/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7803,22 +7536,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-config/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-config/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-config/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7852,20 +7569,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-diff/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-diff/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7881,22 +7584,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-diff/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-diff/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-diff/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7942,20 +7629,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-each/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-each/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7971,22 +7644,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-each/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-each/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-each/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8080,20 +7737,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-matcher-utils/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8109,22 +7752,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-matcher-utils/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-matcher-utils/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-matcher-utils/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8163,20 +7790,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-message-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-message-util/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8192,22 +7805,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-message-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-message-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-message-util/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8294,20 +7891,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-resolve/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-resolve/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8323,22 +7906,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-resolve/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-resolve/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-resolve/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8405,20 +7972,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-runner/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-runner/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8434,22 +7987,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-runner/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runner/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-runner/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8501,20 +8038,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-runtime/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-runtime/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8530,22 +8053,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-runtime/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runtime/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-runtime/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8598,20 +8105,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-snapshot/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-snapshot/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8627,22 +8120,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-snapshot/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-snapshot/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-snapshot/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8689,20 +8166,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-util/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8718,22 +8181,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-util/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8769,20 +8216,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-validate/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-validate/node_modules/camelcase": { "version": "6.3.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", @@ -8809,22 +8242,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-validate/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-validate/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-validate/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8862,20 +8279,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-watcher/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-watcher/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8891,22 +8294,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-watcher/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-watcher/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-watcher/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -11104,6 +10491,15 @@ "node": ">=8" } }, + "node_modules/pngjs": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/pngjs/-/pngjs-5.0.0.tgz", + "integrity": "sha512-40QW5YalBNfQo5yRYmiw7Yz6TKKVr3h6970B2YE+3fQpsWcrbj1PzJgxeJ19DRQjhMbKPIuMY8rFaXc8moolVw==", + "license": "MIT", + "engines": { + "node": ">=10.13.0" + } + }, "node_modules/possible-typed-array-names": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz", @@ -11310,6 +10706,150 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/qrcode": { + "version": "1.5.4", + "resolved": "https://registry.npmjs.org/qrcode/-/qrcode-1.5.4.tgz", + "integrity": "sha512-1ca71Zgiu6ORjHqFBDpnSMTR2ReToX4l1Au1VFLyVeBTFavzQnv5JxMFr3ukHVKpSrSA2MCk0lNJSykjUfz7Zg==", + "license": "MIT", + "dependencies": { + "dijkstrajs": "^1.0.1", + "pngjs": "^5.0.0", + "yargs": "^15.3.1" + }, + "bin": { + "qrcode": "bin/qrcode" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/qrcode.react": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/qrcode.react/-/qrcode.react-4.2.0.tgz", + "integrity": "sha512-QpgqWi8rD9DsS9EP3z7BT+5lY5SFhsqGjpgW5DY/i3mK4M9DTBNz3ErMi8BWYEfI3L0d8GIbGmcdFAS1uIRGjA==", + "license": "ISC", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, + "node_modules/qrcode/node_modules/cliui": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-6.0.0.tgz", + "integrity": "sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==", + "license": "ISC", + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^6.2.0" + } + }, + "node_modules/qrcode/node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "license": "MIT", + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "license": "MIT", + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "license": "MIT", + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/qrcode/node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "license": "MIT", + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/wrap-ansi": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz", + "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==", + "license": "MIT", + "dependencies": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/y18n": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.3.tgz", + "integrity": "sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==", + "license": "ISC" + }, + "node_modules/qrcode/node_modules/yargs": { + "version": "15.4.1", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.4.1.tgz", + "integrity": "sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==", + "license": "MIT", + "dependencies": { + "cliui": "^6.0.0", + "decamelize": "^1.2.0", + "find-up": "^4.1.0", + "get-caller-file": "^2.0.1", + "require-directory": "^2.1.1", + "require-main-filename": "^2.0.0", + "set-blocking": "^2.0.0", + "string-width": "^4.2.0", + "which-module": "^2.0.0", + "y18n": "^4.0.0", + "yargs-parser": "^18.1.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/yargs-parser": { + "version": "18.1.3", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.3.tgz", + "integrity": "sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==", + "license": "ISC", + "dependencies": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -12139,6 +11679,12 @@ "node": ">=0.10.0" } }, + "node_modules/require-main-filename": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz", + "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==", + "license": "ISC" + }, "node_modules/resolve": { "version": "2.0.0-next.5", "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", @@ -13689,6 +13235,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/which-module": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.1.tgz", + "integrity": "sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==", + "license": "ISC" + }, "node_modules/which-typed-array": { "version": "1.1.15", "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.15.tgz", @@ -13834,36 +13386,6 @@ "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/wrap-ansi-cjs/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/wrap-ansi-cjs/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/wrap-ansi-cjs/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/wrap-ansi/node_modules/ansi-regex": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", diff --git a/package.json b/package.json index cb088970..ebe1627f 100644 --- a/package.json +++ b/package.json @@ -37,6 +37,8 @@ "motion": "^11.13.1", "nanoid": "^5.0.7", "prop-types": "^15.8.1", + "qrcode": "^1.5.4", + "qrcode.react": "^4.2.0", "react": "^18.2.0", "react-avatar-editor": "^13.0.2", "react-blurhash": "^0.3.0", diff --git a/src/components/EventCard/EventCard.jsx b/src/components/EventCard/EventCard.jsx index 563f6e69..5f0bfb73 100644 --- a/src/components/EventCard/EventCard.jsx +++ b/src/components/EventCard/EventCard.jsx @@ -5,11 +5,13 @@ import AOS from "aos"; import "aos/dist/aos.css"; import { Link, useNavigate } from "react-router-dom"; import Share from "../../features/Modals/Event/ShareModal/ShareModal"; +import QRCodeModal from "../../features/Modals/Event/QRCodeModal"; import shareOutline from "../../assets/images/shareOutline.svg"; import { PiClockCountdownDuotone } from "react-icons/pi"; import { IoIosLock, IoIosStats } from "react-icons/io"; import { MdGroups } from "react-icons/md"; import { FaUser, FaRupeeSign } from "react-icons/fa"; +import { QrCode } from "lucide-react"; import { parse, differenceInMilliseconds, formatDistanceToNow } from "date-fns"; import { Button } from "../Core"; import AuthContext from "../../context/AuthContext"; @@ -40,6 +42,7 @@ const EventCard = (props) => { const { info } = data; const authCtx = useContext(AuthContext); const [isOpen, setOpen] = useState(false); + const [isQRModalOpen, setQRModalOpen] = useState(false); const [isHovered, setisHovered] = useState(false); const [remainingTime, setRemainingTime] = useState(""); const [btnTxt, setBtnTxt] = useState("Register Now"); @@ -258,6 +261,30 @@ const EventCard = (props) => { setOpen(false); }; + const handleQRCode = () => { + if (authCtx.isLoggedIn && authCtx.user.regForm && authCtx.user.regForm.includes(data.id)) { + setQRModalOpen(!isQRModalOpen); + } else if (!authCtx.isLoggedIn) { + setAlert({ + type: "info", + message: "Please login to access attendance QR code.", + position: "bottom-right", + duration: 3000, + }); + } else { + setAlert({ + type: "info", + message: "You need to register for this event first to get the attendance QR code.", + position: "bottom-right", + duration: 3000, + }); + } + }; + + const handleCloseQRModal = () => { + setQRModalOpen(false); + }; + const isValiedState = () => { if ( btnTxt === "Closed" || @@ -383,6 +410,21 @@ const EventCard = (props) => { /> )} + {type === "ongoing" && authCtx.isLoggedIn && authCtx.user.regForm && authCtx.user.regForm.includes(data.id) && ( +
+ +
+ )}
@@ -536,6 +578,9 @@ const EventCard = (props) => { {isOpen && type === "ongoing" && ( )} + {isQRModalOpen && type === "ongoing" && ( + + )} {enableEdit && isHovered && authCtx.user.access === "ADMIN" && (
setisHovered(true)} diff --git a/src/components/EventCard/styles/EventCard.module.scss b/src/components/EventCard/styles/EventCard.module.scss index c8b70801..125dabb7 100644 --- a/src/components/EventCard/styles/EventCard.module.scss +++ b/src/components/EventCard/styles/EventCard.module.scss @@ -114,6 +114,33 @@ width: 1rem; } +.qrCode { + background: rgba(15, 15, 15, 0.5); + backdrop-filter: blur(1.8663231134414673px); + border: 1px solid rgb(143, 139, 139); + color: #f97507; + position: absolute; + top: 3.5rem; + right: 1rem; + text-align: center; + border-radius: 7px; + font-size: 0.75rem; + font-weight: 800; + padding: 0.5rem; + display: flex; + align-items: center; + justify-content: center; + cursor: pointer; + transition: all 0.3s ease; + + +} + +.qrIcon { + height: 1rem; + width: 1rem; +} + .price p { display: flex; align-items: center; diff --git a/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx new file mode 100644 index 00000000..c9e115ba --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx @@ -0,0 +1,156 @@ +import React, { useState, useEffect, useContext } from 'react'; +import { X } from 'lucide-react'; +import { QRCodeSVG } from 'qrcode.react'; +import AuthContext from '../../../../context/AuthContext'; +import { RecoveryContext } from '../../../../context/RecoveryContext'; +import { api } from '../../../../services'; +import { Alert } from '../../../../microInteraction'; +import style from './styles/QRCodeModal.module.scss'; + +const QRCodeModal = ({ onClose, eventId, onAttendanceMarked }) => { + const [qrCodeData, setQrCodeData] = useState(null); + const [isLoading, setIsLoading] = useState(true); + const [error, setError] = useState(null); + const [attendanceMarked, setAttendanceMarked] = useState(false); + const authCtx = useContext(AuthContext); + const recoveryCtx = useContext(RecoveryContext); + + useEffect(() => { + fetchAttendanceCode(); + }, [eventId]); + + useEffect(() => { + if (onAttendanceMarked) { + setAttendanceMarked(true); + } + }, [onAttendanceMarked]); + + const fetchAttendanceCode = async () => { + try { + setIsLoading(true); + setError(null); + + const teamCode = recoveryCtx.teamCode; + + let url = `/api/form/attendanceCode/${eventId}`; + if (teamCode && teamCode.trim() !== '') { + url += `?teamCode=${encodeURIComponent(teamCode)}`; + } + + const token = localStorage.getItem('token'); + + const response = await api.get(url, { + headers: { + 'Authorization': token + } + }); + + if (response.status === 200) { + setQrCodeData(response.data.attendanceToken); + } else { + throw new Error('Failed to fetch attendance code'); + } + } catch (error) { + setError(error?.response?.data?.message || 'Failed to generate QR code. Please try again.'); + } finally { + setIsLoading(false); + } + }; + + const handleClose = () => { + onClose(); + }; + + const handleRetry = () => { + fetchAttendanceCode(); + }; + + const handleAttendanceMarked = () => { + setAttendanceMarked(true); + }; + + const handleOK = () => { + onClose(); + }; + + const handleScanNewAttendee = () => { + setAttendanceMarked(false); + setQrCodeData(null); + fetchAttendanceCode(); + }; + + return ( +
+
+
+
+
+ +
+
Attendance QR Code
+
+ +
+ {isLoading ? ( +
+
+

Generating QR Code...

+
+ ) : error ? ( +
+

{error}

+ +
+ ) : attendanceMarked ? ( +
+
+

Attendance Marked Successfully!

+

The attendee's presence has been recorded.

+
+ + +
+
+ ) : qrCodeData ? ( +
+
+ +
+ +
+

+ Show this QR code to event organizers for attendance verification. +

+

+ This attendance QR code can be used only once. Do not share it with others.

+
+
+ ) : ( +
+

No attendance code available

+
+ )} +
+
+
+ ); +}; + +export default QRCodeModal; \ No newline at end of file diff --git a/src/features/Modals/Event/QRCodeModal/index.jsx b/src/features/Modals/Event/QRCodeModal/index.jsx new file mode 100644 index 00000000..94894e0b --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/index.jsx @@ -0,0 +1 @@ +export { default } from './QRCodeModal'; \ No newline at end of file diff --git a/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss b/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss new file mode 100644 index 00000000..18b8f56e --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss @@ -0,0 +1,396 @@ +.qrContainer { + position: fixed; + top: 0; + left: 0; + width: 100%; + height: 100%; + z-index: 50; + display: flex; + justify-content: center; + align-items: center; + padding: 1rem; +} + +.overlay { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + background: rgba(0, 0, 0, 0.5); + backdrop-filter: blur(5px); + z-index: 5; +} + +.maindiv { + z-index: 1000; + border-radius: 16px; + padding: 2rem; + position: relative; + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + background: rgba(42, 42, 42, 0.95); + border: 2px solid #444; + width: 100%; + max-width: 450px; + min-height: 400px; + box-shadow: 0 8px 32px rgba(0, 0, 0, 0.3); +} + +.header { + position: relative; + display: flex; + justify-content: space-between; + align-items: center; + margin-bottom: 2rem; + width: 100%; +} + +.closebtn { + cursor: pointer; + position: absolute; + right: 0; + top: 0; + z-index: 20; + font-size: 1.2rem; + color: #ffffff; + transition: color 0.3s ease; + padding: 0.5rem; + + &:hover { + color: #D14206; + transition: .2s linear; + } +} + +.title{ + font-weight:700; + margin-left:6.5rem; + font-size:1rem; + background: linear-gradient( + 260deg, + rgba(255, 190, 11, 0.84) -29.7%, + rgba(244, 43, 3, 0.84) 128.34% +); +color: transparent; +-webkit-background-clip: text; +background-clip: text; +} + + +.content { + flex: 1; + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + text-align: center; + width: 100%; +} + +.loadingContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #f97507; + + p { + margin: 0; + font-size: 1rem; + } +} + +.spinner { + width: 40px; + height: 40px; + border: 3px solid rgba(249, 117, 7, 0.3); + border-top: 3px solid #f97507; + border-radius: 50%; + animation: spin 1s linear infinite; +} + +@keyframes spin { + 0% { transform: rotate(0deg); } + 100% { transform: rotate(360deg); } +} + +.errorContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #ff6b6b; + + p { + margin: 0; + font-size: 1rem; + } +} + +.retryBtn { + background: linear-gradient(135deg, #f97507, #ff8c42); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + +} + +.qrContent { + display: flex; + flex-direction: column; + align-items: center; + gap: 1.5rem; + width: 100%; +} + +.qrWrapper { + padding: 1.5rem; + border-radius: 12px; + display: flex; + justify-content: center; + background-color: #ffffff; + align-items: center; + backdrop-filter: blur(10px); +} + +.qrCode { + display: block; +} + +.codeInfo { + display: flex; + flex-direction: column; + align-items: center; + gap: 0.5rem; + background: rgba(250, 250, 250, 0.1); + padding: 1rem; + border-radius: 8px; + width: 100%; +} + +.codeLabel { + margin: 0; + font-size: 0.9rem; + color: #f97507; + font-weight: 600; +} + +.codeValue { + margin: 0; + font-size: 1.2rem; + font-weight: 700; + color: #f97507; + letter-spacing: 1px; + font-family: 'Courier New', monospace; + transition: color 0.2s ease; + + &:hover { + color: #ff8c42; + } +} + +.instruction { + margin: 0; + font-size: 0.9rem; + color: #ccc; + line-height: 1.4; +} + +.noCodeContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #ffa500; + + p { + margin: 0; + font-size: 1rem; + } +} + +.successContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1.5rem; + color: #4CAF50; + text-align: center; + + h3 { + margin: 0; + font-size: 1.5rem; + font-weight: 600; + color: #4CAF50; + } + + p { + margin: 0; + font-size: 1rem; + color: #ccc; + } +} + +.successIcon { + font-size: 3rem; + color: #4CAF50; + background: rgba(76, 175, 80, 0.1); + border-radius: 50%; + width: 80px; + height: 80px; + display: flex; + align-items: center; + justify-content: center; + border: 3px solid #4CAF50; +} + +.buttonGroup { + display: flex; + gap: 1rem; + margin-top: 1rem; +} + +.okBtn { + background: linear-gradient(135deg, #4CAF50, #45a049); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + &:hover { + transform: translateY(-2px); + } +} + +.scanNewBtn { + background: linear-gradient(135deg, #f97507, #ff8c42); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + &:hover { + transform: translateY(-2px); + } +} + +// Responsive design +@media (max-width: 768px) { + .qrContainer { + padding: 0.5rem; + } + + .maindiv { + width: 100%; + padding: 1.5rem; + min-height: 350px; + border-radius: 12px; + } + + .title { + font-size: 1.3rem; + } + + .qrWrapper { + padding: 1rem; + } + + .qrCode { + width: 180px; + height: 180px; + } +} + +@media (max-width: 480px) { + .qrContainer { + padding: 0.25rem; + } + + .maindiv { + padding: 1rem; + min-height: 320px; + } + + .title { + font-size: 1.2rem; + } + + .header { + margin-bottom: 1.5rem; + } + + .qrWrapper { + padding: 0.75rem; + } + + .qrCode { + width: 160px; + height: 160px; + } + + .codeInfo { + padding: 0.75rem; + } + + .instruction { + font-size: 0.85rem; + } + + .successContainer { + gap: 1rem; + + h3 { + font-size: 1.3rem; + } + + p { + font-size: 0.9rem; + } + } + + .successIcon { + width: 60px; + height: 60px; + font-size: 2rem; + } + + .buttonGroup { + flex-direction: column; + gap: 0.75rem; + } + + .okBtn, .scanNewBtn { + padding: 0.6rem 1.2rem; + font-size: 0.9rem; + } +} + +@media (max-width: 360px) { + .maindiv { + padding: 0.75rem; + min-height: 300px; + } + + .title { + font-size: 1.1rem; + } + + .qrCode { + width: 140px; + height: 140px; + } +} \ No newline at end of file diff --git a/src/features/Modals/index.jsx b/src/features/Modals/index.jsx index 6f0fc365..40f1e790 100644 --- a/src/features/Modals/index.jsx +++ b/src/features/Modals/index.jsx @@ -9,6 +9,7 @@ export { default as EventModal } from './Event/EventModal/EventModal'; export { default as LiveEventPopup } from './Event/LiveEventPopup/LiveEventPopup'; export { default as ShareModal } from './Event/ShareModal/ShareModal'; export { default as EventStats } from './Event/EventStats/EventStats'; +export { default as QRCodeModal } from './Event/QRCodeModal/QRCodeModal'; // Admin and Form Modals export { default as PreviewForm } from './Profile/Admin/PreviewForm'; diff --git a/src/pages/AttendancePage/AttendancePage.jsx b/src/pages/AttendancePage/AttendancePage.jsx index e2d2b695..43d78267 100644 --- a/src/pages/AttendancePage/AttendancePage.jsx +++ b/src/pages/AttendancePage/AttendancePage.jsx @@ -17,6 +17,7 @@ const AttendancePage = () => { const [showScanner, setShowScanner] = useState(false); const [selectedEventId, setSelectedEventId] = useState(null); const [scanner, setScanner] = useState(null); + const [isScanning, setIsScanning] = useState(false); const authCtx = useContext(AuthContext); useEffect(() => { @@ -60,28 +61,43 @@ const AttendancePage = () => { }, []); const initializeScanner = () => { - const qrScanner = new Html5QrcodeScanner( - "qr-reader", - { - fps: 10, - qrbox: { width: 250, height: 250 }, - aspectRatio: 1, - supportedScanTypes: [Html5QrcodeScanType.SCAN_TYPE_CAMERA] // ✅ FIXED - }, - false - ); + try { + const qrScanner = new Html5QrcodeScanner( + "qr-reader", + { + fps: 10, + qrbox: { width: 250, height: 250 }, + aspectRatio: 1, + supportedScanTypes: [Html5QrcodeScanType.SCAN_TYPE_CAMERA] + }, + false + ); - qrScanner.render(onScanSuccess, onScanFailure); - setScanner(qrScanner); + qrScanner.render(onScanSuccess, onScanFailure); + setScanner(qrScanner); + } catch (error) { + console.error("Error initializing scanner:", error); + Alert({ + type: "error", + message: "Failed to initialize QR scanner", + position: "top-right", + }); + setShowScanner(false); + } }; const onScanSuccess = async (decodedText) => { try { + setIsScanning(true); + console.log("QR Code scanned successfully:", decodedText); + console.log("Selected Event ID:", selectedEventId); + + // The decodedText contains the JWT token from the QR code const response = await api.post( - `/api/attendance/verify`, + `/api/form/markAttendance`, { - eventId: selectedEventId, - qrData: decodedText, + formId: selectedEventId, + token: decodedText, }, { headers: { @@ -102,11 +118,28 @@ const AttendancePage = () => { setShowScanner(false); } } catch (error) { + console.error("Error marking attendance:", error); + let errorMessage = "Failed to verify QR code"; + + if (error.response?.status === 401) { + errorMessage = "Invalid or expired QR code"; + } else if (error.response?.status === 400) { + errorMessage = error.response?.data?.message || "Invalid request"; + } else if (error.response?.status === 404) { + errorMessage = "Attendance record not found"; + } else if (error.response?.status === 403) { + errorMessage = "You don't have permission to mark attendance"; + } else if (error.response?.data?.message) { + errorMessage = error.response.data.message; + } + Alert({ type: "error", - message: error.response?.data?.message || "Failed to verify QR code", + message: errorMessage, position: "top-right", }); + } finally { + setIsScanning(false); } }; @@ -121,7 +154,7 @@ const AttendancePage = () => { const handleDownloadAttendance = async (eventId) => { try { - const response = await api.get(`/api/attendance/download/${eventId}`, { + const response = await api.get(`/api/form/download/${eventId}`, { headers: { Authorization: `Bearer ${authCtx.token}` }, responseType: "blob", }); @@ -141,9 +174,19 @@ const AttendancePage = () => { position: "top-right", }); } catch (error) { + let errorMessage = "Failed to download attendance file"; + + if (error.response?.status === 403) { + errorMessage = "You don't have permission to download attendance data"; + } else if (error.response?.status === 404) { + errorMessage = "Attendance data not found for this event"; + } else if (error.response?.data?.message) { + errorMessage = error.response.data.message; + } + Alert({ type: "error", - message: "Failed to download attendance file", + message: errorMessage, position: "top-right", }); console.error("Download error:", error); @@ -191,7 +234,11 @@ const AttendancePage = () => { } return () => { if (scanner) { - scanner.clear(); + try { + scanner.clear(); + } catch (error) { + console.error("Error clearing scanner in cleanup:", error); + } } }; }, [showScanner]); @@ -227,15 +274,25 @@ const AttendancePage = () => { className={styles.closeButton} onClick={() => { if (scanner) { - scanner.clear(); + try { + scanner.clear(); + } catch (error) { + console.error("Error clearing scanner:", error); + } } setShowScanner(false); + setScanner(null); }} >

Scan QR Code

+ {isScanning && ( +
+
Processing QR Code...
+
+ )}
From 033c26999a7779f71b55d32834bea2ecbaf2256d Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Wed, 13 Aug 2025 12:00:07 +0530 Subject: [PATCH 20/44] Updated --- FED-Backend | 1 - 1 file changed, 1 deletion(-) delete mode 160000 FED-Backend diff --git a/FED-Backend b/FED-Backend deleted file mode 160000 index 4258de3d..00000000 --- a/FED-Backend +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 4258de3d3387ad763c4e6ee77d51e94be28c44c4 From 3ee6c14bf01309f3e710d070ec849b125c8f74c2 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Wed, 13 Aug 2025 14:18:54 +0530 Subject: [PATCH 21/44] team details button change --- src/components/EventCard/EventCard.jsx | 39 ++++++++++++------- .../EventCard/styles/EventCard.module.scss | 31 ++++----------- 2 files changed, 33 insertions(+), 37 deletions(-) diff --git a/src/components/EventCard/EventCard.jsx b/src/components/EventCard/EventCard.jsx index 2e6b4548..ad25c96d 100644 --- a/src/components/EventCard/EventCard.jsx +++ b/src/components/EventCard/EventCard.jsx @@ -469,17 +469,30 @@ const EventCard = (props) => { // } > {btnTxt === "Closed" ? ( - <> -
Closed
- - - ) : btnTxt === "Already Registered" ? ( - <> -
Registered
- + <> +
Closed
+ + +) : btnTxt === "Already Registered" ? ( + info.participationType === "Team" ? ( // Show Team Details only for team events + <> +
setIsTeamDetailsOpen(true)} + > + Team Details +
+ + ) : ( + <> +
Registered
+ + ) + + ) : btnTxt === "Locked" ? ( <>
Locked
@@ -512,7 +525,7 @@ const EventCard = (props) => {
)} - {/* See Team Details Button - Only show for team events when user is registered */} + {/* See Team Details Button - Only show for team events when user is registered {type === "ongoing" && info.participationType === "Team" && btnTxt === "Already Registered" && @@ -526,7 +539,7 @@ const EventCard = (props) => {
- )} + )} */}
diff --git a/src/components/EventCard/styles/EventCard.module.scss b/src/components/EventCard/styles/EventCard.module.scss index e9c384d9..e9bd74cc 100644 --- a/src/components/EventCard/styles/EventCard.module.scss +++ b/src/components/EventCard/styles/EventCard.module.scss @@ -180,17 +180,19 @@ ) ); display: inline-flex; - padding: 0.4rem 0.8rem; + padding: 0.6rem ; justify-content: center; align-items: center; - margin-left: 0.5rem; /* 👈 gap between "Free" and button */ + margin-top: 0rem; + gap: 0rem; cursor: progress; outline: none; border: none; - font-size: 0.85rem; - color: #fff; + font-size: 0.9rem; + color: #ffffff; } + .backtxt { width: 90%; margin-inline: auto; @@ -243,26 +245,7 @@ a { width: 44%; } -.teamDetailsBtn { -width: 30px; - height: 35px; - padding-bottom: 10px; - background-color: transparent; - border: none; - border-radius: 50%; - display: flex; - align-items: center; - justify-content: center; - cursor: pointer; - &:hover { - - transform: translateY(-1px); - } - - &:active { - transform: translateY(0); - } -} + @media (max-width: 600px) { .backbtn { From 022e87e18c6d835465523bd8a3708c1852dc675f Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Wed, 13 Aug 2025 23:09:38 +0530 Subject: [PATCH 22/44] QR attendance functionality --- .../Modals/Event/QRCodeModal/QRCodeModal.jsx | 14 --- src/pages/AttendancePage/AttendancePage.jsx | 119 ++++++++++++++---- .../styles/AttendancePage.module.scss | 86 +++++++++++-- 3 files changed, 169 insertions(+), 50 deletions(-) diff --git a/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx index c9e115ba..46e3b5b2 100644 --- a/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx +++ b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx @@ -106,20 +106,6 @@ const QRCodeModal = ({ onClose, eventId, onAttendanceMarked }) => { Try Again
- ) : attendanceMarked ? ( -
-
-

Attendance Marked Successfully!

-

The attendee's presence has been recorded.

-
- - -
-
) : qrCodeData ? (
diff --git a/src/pages/AttendancePage/AttendancePage.jsx b/src/pages/AttendancePage/AttendancePage.jsx index 43d78267..fdd75151 100644 --- a/src/pages/AttendancePage/AttendancePage.jsx +++ b/src/pages/AttendancePage/AttendancePage.jsx @@ -18,6 +18,10 @@ const AttendancePage = () => { const [selectedEventId, setSelectedEventId] = useState(null); const [scanner, setScanner] = useState(null); const [isScanning, setIsScanning] = useState(false); + const [showSuccessModal, setShowSuccessModal] = useState(false); + const [attendedUser, setAttendedUser] = useState(null); + const [hasShownAlert, setHasShownAlert] = useState(false); + const [isSuccess, setIsSuccess] = useState(false); const authCtx = useContext(AuthContext); useEffect(() => { @@ -27,6 +31,7 @@ const AttendancePage = () => { if (response.status === 200) { const fetchedEvents = response.data.events; + // sort events by priority, date, and title const sortedEvents = fetchedEvents.sort((a, b) => { const priorityA = parseInt(a.info.eventPriority, 10); const priorityB = parseInt(b.info.eventPriority, 10); @@ -77,22 +82,25 @@ const AttendancePage = () => { setScanner(qrScanner); } catch (error) { console.error("Error initializing scanner:", error); - Alert({ - type: "error", - message: "Failed to initialize QR scanner", - position: "top-right", - }); + if (!hasShownAlert) { + Alert({ + type: "error", + message: "Failed to initialize QR scanner", + position: "top-right", + }); + setHasShownAlert(true); + } setShowScanner(false); } }; const onScanSuccess = async (decodedText) => { + setIsScanning(true); + console.log("QR Code scanned successfully:", decodedText); + console.log("Selected Event ID:", selectedEventId); + try { - setIsScanning(true); - console.log("QR Code scanned successfully:", decodedText); - console.log("Selected Event ID:", selectedEventId); - - // The decodedText contains the JWT token from the QR code + // jwt token from qr code const response = await api.post( `/api/form/markAttendance`, { @@ -107,15 +115,23 @@ const AttendancePage = () => { ); if (response.status === 200) { + // store user details + setAttendedUser(response.data.user || response.data); + setIsSuccess(true); + if (scanner) { + scanner.clear(); + } + setShowSuccessModal(true); + setIsScanning(false); + + // show success alert Alert({ type: "success", message: "Attendance marked successfully!", position: "top-right", }); - if (scanner) { - scanner.clear(); - } - setShowScanner(false); + + return; // exit early } } catch (error) { console.error("Error marking attendance:", error); @@ -133,11 +149,15 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - Alert({ - type: "error", - message: errorMessage, - position: "top-right", - }); + // show error alert + if (!hasShownAlert) { + Alert({ + type: "error", + message: errorMessage, + position: "top-right", + }); + setHasShownAlert(true); + } } finally { setIsScanning(false); } @@ -150,8 +170,23 @@ const AttendancePage = () => { const handleScanQR = (eventId) => { setSelectedEventId(eventId); setShowScanner(true); + setHasShownAlert(false); // reset alert state + setIsSuccess(false); // reset success state + }; + + const handleCloseSuccessModal = () => { + setShowSuccessModal(false); + setAttendedUser(null); + // auto open scanner for next scan + setTimeout(() => { + setShowScanner(true); + setHasShownAlert(false); // reset alert state + setIsSuccess(false); // reset success state + }, 100); }; + + const handleDownloadAttendance = async (eventId) => { try { const response = await api.get(`/api/form/download/${eventId}`, { @@ -184,11 +219,15 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - Alert({ - type: "error", - message: errorMessage, - position: "top-right", - }); + // show error alert + if (!isSuccess && !hasShownAlert) { + Alert({ + type: "error", + message: errorMessage, + position: "top-right", + }); + setHasShownAlert(true); + } console.error("Download error:", error); } }; @@ -299,6 +338,34 @@ const AttendancePage = () => {
)} + {/* Success Modal */} + {showSuccessModal && attendedUser && ( +
+
+ +
+
+

Attendance Marked Successfully!

+ +
+ +
+
+
+
+ )} + {/* Ongoing Events */} {ongoingEvents.length > 0 && ( <> @@ -314,7 +381,7 @@ const AttendancePage = () => { showRegisterButton={false} showShareButton={false} additionalContent={renderOngoingActions(event)} - onOpen={() => { }} // ✅ FIXED: Always pass a function + onOpen={() => { }} // fixed customStyles={{ eventname: { fontSize: "1.2rem" }, registerbtn: { width: "8rem", fontSize: ".721rem" }, @@ -342,7 +409,7 @@ const AttendancePage = () => { showRegisterButton={false} showShareButton={false} additionalContent={renderPastActions(event)} - onOpen={() => { }} // ✅ FIXED + onOpen={() => { }} // fixed customStyles={{ eventname: { fontSize: "1.2rem" }, registerbtn: { width: "8rem", fontSize: ".721rem" }, diff --git a/src/pages/AttendancePage/styles/AttendancePage.module.scss b/src/pages/AttendancePage/styles/AttendancePage.module.scss index 8bac619c..d8031fb0 100644 --- a/src/pages/AttendancePage/styles/AttendancePage.module.scss +++ b/src/pages/AttendancePage/styles/AttendancePage.module.scss @@ -39,7 +39,6 @@ &:last-child { background: #FF8A00; color: white; - border: none; &:hover { background: rgba(255, 138, 0, 0.9); @@ -71,25 +70,26 @@ .closeButton { position: absolute; - top: -15px; - right: -15px; - background: var(--primary); + top: 4px; + right: 6px; border: none; border-radius: 50%; - width: 30px; - height: 30px; + width: 34px; + height: 34px; display: flex; align-items: center; justify-content: center; cursor: pointer; color: white; font-size: 1.2rem; - + background: transparent; + &:hover { - transform: scale(1.1); - transition: transform 0.2s ease; - } + color: #D14206; + transition: .2s linear; + } +} .scannerTitle { color: white; @@ -128,3 +128,69 @@ } } } + +.successContent { + text-align: center; + color: white; + + .successIcon { + font-size: 3rem; + color: #FF8A00; + margin-bottom: 1rem; + } + + .successTitle { + color: white; + margin-bottom: 1.5rem; + font-size: 1.3rem; + } + + + + .buttonGroup { + display: flex; + gap: 1rem; + justify-content: center; + margin-top: 2rem; + + button { + min-width: 120px; + border-radius: 6px; + font-weight: 600; + transition: all 0.2s ease; + + + } + } +} + +.scanningOverlay { + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + background: rgba(0, 0, 0, 0.8); + display: flex; + align-items: center; + justify-content: center; + z-index: 10; + border-radius: 8px; + + .scanningText { + color: white; + font-size: 1.1rem; + font-weight: 600; + } +} + +@keyframes fadeInScale { + 0% { + opacity: 0; + transform: scale(0.5); + } + 100% { + opacity: 1; + transform: scale(1); + } +} From 4acb044469e4e6abb69f074fc1ccf229242755e2 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 14 Aug 2025 21:20:32 +0530 Subject: [PATCH 23/44] Update index.jsx --- src/features/Modals/index.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/features/Modals/index.jsx b/src/features/Modals/index.jsx index 40f1e790..7117d278 100644 --- a/src/features/Modals/index.jsx +++ b/src/features/Modals/index.jsx @@ -9,7 +9,7 @@ export { default as EventModal } from './Event/EventModal/EventModal'; export { default as LiveEventPopup } from './Event/LiveEventPopup/LiveEventPopup'; export { default as ShareModal } from './Event/ShareModal/ShareModal'; export { default as EventStats } from './Event/EventStats/EventStats'; -export { default as QRCodeModal } from './Event/QRCodeModal/QRCodeModal'; +export { default as TeamDetailsModal } from './Event/TeamDetailsModal'; // Admin and Form Modals export { default as PreviewForm } from './Profile/Admin/PreviewForm'; From 448cdfde0cbcdbdb38bb695aed23d2a2574b8e61 Mon Sep 17 00:00:00 2001 From: Rudrika Date: Thu, 14 Aug 2025 21:36:52 +0530 Subject: [PATCH 24/44] Pnpm i --- pnpm-lock.yaml | 161 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 161 insertions(+) diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 6db197a2..85b5a747 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -65,6 +65,9 @@ importers: html2canvas: specifier: ^1.4.1 version: 1.4.1 + html5-qrcode: + specifier: ^2.3.8 + version: 2.3.8 js-confetti: specifier: ^0.12.0 version: 0.12.0 @@ -86,6 +89,12 @@ importers: prop-types: specifier: ^15.8.1 version: 15.8.1 + qrcode: + specifier: ^1.5.4 + version: 1.5.4 + qrcode.react: + specifier: ^4.2.0 + version: 4.2.0(react@18.3.1) react: specifier: ^18.2.0 version: 18.3.1 @@ -134,6 +143,9 @@ importers: react-oauth: specifier: ^0.0.1 version: 0.0.1 + react-qr-barcode-scanner: + specifier: ^2.1.8 + version: 2.1.8(react-dom@18.3.1(react@18.3.1))(react@18.3.1) react-quill: specifier: ^2.0.0 version: 2.0.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1) @@ -1212,6 +1224,13 @@ packages: '@wojtekmaj/date-utils@1.5.1': resolution: {integrity: sha512-+i7+JmNiE/3c9FKxzWFi2IjRJ+KzZl1QPu6QNrsgaa2MuBgXvUy4gA1TVzf/JMdIIloB76xSKikTWuyYAIVLww==} + '@zxing/library@0.21.3': + resolution: {integrity: sha512-hZHqFe2JyH/ZxviJZosZjV+2s6EDSY0O24R+FQmlWZBZXP9IqMo7S3nb3+2LBWxodJQkSurdQGnqE7KXqrYgow==} + engines: {node: '>= 10.4.0'} + + '@zxing/text-encoding@0.9.0': + resolution: {integrity: sha512-U/4aVJ2mxI0aDNI8Uq0wEhMgY+u4CNtEb0om3+y3+niDAsoTCOB33UF0sxpzqzdqXLqmvc+vZyAt4O8pPdfkwA==} + abbrev@1.1.1: resolution: {integrity: sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==} @@ -1550,6 +1569,9 @@ packages: resolution: {integrity: sha512-+W/5efTR7y5HRD7gACw9yQjqMVvEMLBHmboM/kPWam+H+Hmyrgjh6YncVKK122YZkXrLudzTuAukUw9FnMf7IQ==} engines: {node: 10.* || >= 12.*} + cliui@6.0.0: + resolution: {integrity: sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==} + cliui@8.0.1: resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} engines: {node: '>=12'} @@ -1692,6 +1714,10 @@ packages: supports-color: optional: true + decamelize@1.2.0: + resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==} + engines: {node: '>=0.10.0'} + decompress-response@6.0.0: resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==} engines: {node: '>=10'} @@ -1748,6 +1774,9 @@ packages: resolution: {integrity: sha512-FU0iFaH/E23a+a718l8Qa/19bF9p06kgE0KipMOMadwa3SjnaElKzPaUC0vnibs6/B/9ni97s61mcejk8W1fQw==} engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} + dijkstrajs@1.0.3: + resolution: {integrity: sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==} + dir-glob@3.0.1: resolution: {integrity: sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==} engines: {node: '>=8'} @@ -2284,6 +2313,9 @@ packages: resolution: {integrity: sha512-fPU6BHNpsyIhr8yyMpTLLxAbkaK8ArIBcmZIRiBLiDhjeqvXolaEmDGmELFuX9I4xDcaKKcJl+TKZLqruBbmWA==} engines: {node: '>=8.0.0'} + html5-qrcode@2.3.8: + resolution: {integrity: sha512-jsr4vafJhwoLVEDW3n1KvPnCCXWaQfRng0/EEYk1vNcQGcG/htAdhJX0be8YyqMoSz7+hZvOZSTAepsabiuhiQ==} + http-cache-semantics@4.1.1: resolution: {integrity: sha512-er295DKPVsV82j5kw1Gjt+ADA/XYHsajl82cGNQG2eyoPkvgUhX+nDIyelzhIWbbsXP39EHcI6l5tYs2FYqYXQ==} @@ -3287,6 +3319,10 @@ packages: resolution: {integrity: sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==} engines: {node: '>=8'} + pngjs@5.0.0: + resolution: {integrity: sha512-40QW5YalBNfQo5yRYmiw7Yz6TKKVr3h6970B2YE+3fQpsWcrbj1PzJgxeJ19DRQjhMbKPIuMY8rFaXc8moolVw==} + engines: {node: '>=10.13.0'} + possible-typed-array-names@1.0.0: resolution: {integrity: sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==} engines: {node: '>= 0.4'} @@ -3351,6 +3387,16 @@ packages: resolution: {integrity: sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==} engines: {node: '>=12.20'} + qrcode.react@4.2.0: + resolution: {integrity: sha512-QpgqWi8rD9DsS9EP3z7BT+5lY5SFhsqGjpgW5DY/i3mK4M9DTBNz3ErMi8BWYEfI3L0d8GIbGmcdFAS1uIRGjA==} + peerDependencies: + react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 + + qrcode@1.5.4: + resolution: {integrity: sha512-1ca71Zgiu6ORjHqFBDpnSMTR2ReToX4l1Au1VFLyVeBTFavzQnv5JxMFr3ukHVKpSrSA2MCk0lNJSykjUfz7Zg==} + engines: {node: '>=10.13.0'} + hasBin: true + queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} @@ -3501,6 +3547,12 @@ packages: react: ^15.5.x || ^16.x || ^17.x || ^18.x react-dom: ^15.5.x || ^16.x || ^17.x || ^18.x + react-qr-barcode-scanner@2.1.8: + resolution: {integrity: sha512-REbb+BWmPjvYIAZi6/iYrRupnK4e8d39m1YExhXk+XkKnz/aU/JembC1s+6ZO6jGVXnsGkh25Dwctcrm1HsK4g==} + peerDependencies: + react: '>=18.0.0' + react-dom: '>=18.0.0' + react-quill@2.0.0: resolution: {integrity: sha512-4qQtv1FtCfLgoD3PXAur5RyxuUbPXQGOHgTlFie3jtxp43mXDtzCKaOgQ3mLyZfi1PUlyjycfivKelFhy13QUg==} peerDependencies: @@ -3589,6 +3641,12 @@ packages: react: ^16.0.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.0.0 || ^17.0.0 || ^18.0.0 + react-webcam@7.2.0: + resolution: {integrity: sha512-xkrzYPqa1ag2DP+2Q/kLKBmCIfEx49bVdgCCCcZf88oF+0NPEbkwYk3/s/C7Zy0mhM8k+hpdNkBLzxg8H0aWcg==} + peerDependencies: + react: '>=16.2.0' + react-dom: '>=16.2.0' + react-youtube@10.1.0: resolution: {integrity: sha512-ZfGtcVpk0SSZtWCSTYOQKhfx5/1cfyEW1JN/mugGNfAxT3rmVJeMbGpA9+e78yG21ls5nc/5uZJETE3cm3knBg==} engines: {node: '>= 14.x'} @@ -3647,6 +3705,9 @@ packages: resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} engines: {node: '>=0.10.0'} + require-main-filename@2.0.0: + resolution: {integrity: sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==} + resolve-alpn@1.2.1: resolution: {integrity: sha512-0a1F4l73/ZFZOakJnQ3FvkJ2+gSTQWz/r2KE5OdDY0TxPm5h4GkqkWWfM47T7HsbnOtcJVEF4epCVy6u7Q3K+g==} @@ -4004,6 +4065,10 @@ packages: resolution: {integrity: sha512-pkonvlKk8/ZuR0D5tLW8ljt5I8kmxp2XKymhepUeOdCEfKpZaktSArkLHZt76OB1ZvO9bssUsDty4SWhLvZpLg==} engines: {node: '>=0.10.0'} + ts-custom-error@3.3.1: + resolution: {integrity: sha512-5OX1tzOjxWEgsr/YEUWSuPrQ00deKLh6D7OTWcvNHm12/7QPyRh8SYpyWvA4IZv8H/+GQWQEh/kwo95Q9OVW1A==} + engines: {node: '>=14.0.0'} + tslib@2.6.2: resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} @@ -4193,6 +4258,9 @@ packages: resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} engines: {node: '>= 0.4'} + which-module@2.0.1: + resolution: {integrity: sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==} + which-typed-array@1.1.15: resolution: {integrity: sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==} engines: {node: '>= 0.4'} @@ -4226,6 +4294,10 @@ packages: resolution: {integrity: sha512-OELeY0Q61OXpdUfTp+oweA/vtLVg5VDOXh+3he3PNzLGG/y0oylSOC1xRVj0+l4vQ3tj/bB1HVHv1ocXkQceFA==} engines: {node: '>=0.8'} + wrap-ansi@6.2.0: + resolution: {integrity: sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==} + engines: {node: '>=8'} + wrap-ansi@7.0.0: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} engines: {node: '>=10'} @@ -4253,6 +4325,9 @@ packages: engines: {node: '>=0.8'} hasBin: true + y18n@4.0.3: + resolution: {integrity: sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==} + y18n@5.0.8: resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==} engines: {node: '>=10'} @@ -4267,10 +4342,18 @@ packages: resolution: {integrity: sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==} engines: {node: '>= 6'} + yargs-parser@18.1.3: + resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==} + engines: {node: '>=6'} + yargs-parser@21.1.1: resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} engines: {node: '>=12'} + yargs@15.4.1: + resolution: {integrity: sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==} + engines: {node: '>=8'} + yargs@17.7.2: resolution: {integrity: sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==} engines: {node: '>=12'} @@ -5392,6 +5475,15 @@ snapshots: '@wojtekmaj/date-utils@1.5.1': {} + '@zxing/library@0.21.3': + dependencies: + ts-custom-error: 3.3.1 + optionalDependencies: + '@zxing/text-encoding': 0.9.0 + + '@zxing/text-encoding@0.9.0': + optional: true + abbrev@1.1.1: {} acorn-jsx@5.3.2(acorn@8.12.0): @@ -5833,6 +5925,12 @@ snapshots: optionalDependencies: '@colors/colors': 1.5.0 + cliui@6.0.0: + dependencies: + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi: 6.2.0 + cliui@8.0.1: dependencies: string-width: 4.2.3 @@ -5965,6 +6063,8 @@ snapshots: dependencies: ms: 2.1.2 + decamelize@1.2.0: {} + decompress-response@6.0.0: dependencies: mimic-response: 3.1.0 @@ -6012,6 +6112,8 @@ snapshots: diff-sequences@28.1.1: {} + dijkstrajs@1.0.3: {} + dir-glob@3.0.1: dependencies: path-type: 4.0.0 @@ -6696,6 +6798,8 @@ snapshots: css-line-break: 2.1.0 text-segmentation: 1.0.3 + html5-qrcode@2.3.8: {} + http-cache-semantics@4.1.1: {} http-proxy-agent@5.0.0: @@ -7928,6 +8032,8 @@ snapshots: dependencies: find-up: 4.1.0 + pngjs@5.0.0: {} + possible-typed-array-names@1.0.0: {} postcss-value-parser@4.2.0: {} @@ -7984,6 +8090,16 @@ snapshots: dependencies: escape-goat: 4.0.0 + qrcode.react@4.2.0(react@18.3.1): + dependencies: + react: 18.3.1 + + qrcode@1.5.4: + dependencies: + dijkstrajs: 1.0.3 + pngjs: 5.0.0 + yargs: 15.4.1 + queue-microtask@1.2.3: {} quick-lru@5.1.1: {} @@ -8154,6 +8270,13 @@ snapshots: react: 18.3.1 react-dom: 18.3.1(react@18.3.1) + react-qr-barcode-scanner@2.1.8(react-dom@18.3.1(react@18.3.1))(react@18.3.1): + dependencies: + '@zxing/library': 0.21.3 + react: 18.3.1 + react-dom: 18.3.1(react@18.3.1) + react-webcam: 7.2.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1) + react-quill@2.0.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1): dependencies: '@types/quill': 1.3.10 @@ -8280,6 +8403,11 @@ snapshots: react-dom: 18.3.1(react@18.3.1) scriptjs: 2.5.9 + react-webcam@7.2.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1): + dependencies: + react: 18.3.1 + react-dom: 18.3.1(react@18.3.1) + react-youtube@10.1.0(react@18.3.1): dependencies: fast-deep-equal: 3.1.3 @@ -8348,6 +8476,8 @@ snapshots: require-from-string@2.0.2: {} + require-main-filename@2.0.0: {} + resolve-alpn@1.2.1: {} resolve-cwd@3.0.0: @@ -8738,6 +8868,8 @@ snapshots: dependencies: escape-string-regexp: 1.0.5 + ts-custom-error@3.3.1: {} + tslib@2.6.2: {} tslib@2.6.3: {} @@ -8946,6 +9078,8 @@ snapshots: is-weakmap: 2.0.2 is-weakset: 2.0.3 + which-module@2.0.1: {} + which-typed-array@1.1.15: dependencies: available-typed-arrays: 1.0.7 @@ -8976,6 +9110,12 @@ snapshots: word@0.3.0: {} + wrap-ansi@6.2.0: + dependencies: + ansi-styles: 4.3.0 + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi@7.0.0: dependencies: ansi-styles: 4.3.0 @@ -9014,6 +9154,8 @@ snapshots: wmf: 1.0.2 word: 0.3.0 + y18n@4.0.3: {} + y18n@5.0.8: {} yallist@3.1.1: {} @@ -9022,8 +9164,27 @@ snapshots: yaml@1.10.2: {} + yargs-parser@18.1.3: + dependencies: + camelcase: 5.3.1 + decamelize: 1.2.0 + yargs-parser@21.1.1: {} + yargs@15.4.1: + dependencies: + cliui: 6.0.0 + decamelize: 1.2.0 + find-up: 4.1.0 + get-caller-file: 2.0.5 + require-directory: 2.1.1 + require-main-filename: 2.0.0 + set-blocking: 2.0.0 + string-width: 4.2.3 + which-module: 2.0.1 + y18n: 4.0.3 + yargs-parser: 18.1.3 + yargs@17.7.2: dependencies: cliui: 8.0.1 From dd523f1b983490b477673df35debf238a0f9655c Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Thu, 14 Aug 2025 22:12:45 +0530 Subject: [PATCH 25/44] omega5 --- package-lock.json | 991 +++++------------- package.json | 4 + pnpm-lock.yaml | 161 +++ src/App.jsx | 2 + src/components/EventCard/EventCard.jsx | 48 +- .../EventCard/styles/EventCard.module.scss | 27 + .../Modals/Event/QRCodeModal/QRCodeModal.jsx | 142 +++ .../Modals/Event/QRCodeModal/index.jsx | 1 + .../styles/QRCodeModal.module.scss | 396 +++++++ src/layouts/Profile/Sidebar/Sidebar.jsx | 65 +- src/pages/AttendancePage/AttendancePage.jsx | 428 ++++++++ .../styles/AttendancePage.module.scss | 196 ++++ 12 files changed, 1735 insertions(+), 726 deletions(-) create mode 100644 src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx create mode 100644 src/features/Modals/Event/QRCodeModal/index.jsx create mode 100644 src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss create mode 100644 src/pages/AttendancePage/AttendancePage.jsx create mode 100644 src/pages/AttendancePage/styles/AttendancePage.module.scss diff --git a/package-lock.json b/package-lock.json index dcfd0b7b..c5098011 100644 --- a/package-lock.json +++ b/package-lock.json @@ -27,6 +27,7 @@ "date-fns": "^3.6.0", "framer-motion": "^11.2.10", "html2canvas": "^1.4.1", + "html5-qrcode": "^2.3.8", "js-confetti": "^0.12.0", "load-script": "^2.0.0", "lucide-react": "^0.379.0", @@ -34,6 +35,8 @@ "motion": "^11.13.1", "nanoid": "^5.0.7", "prop-types": "^15.8.1", + "qrcode": "^1.5.4", + "qrcode.react": "^4.2.0", "react": "^18.2.0", "react-avatar-editor": "^13.0.2", "react-blurhash": "^0.3.0", @@ -50,6 +53,7 @@ "react-loading-indicators": "^0.2.3", "react-loading-skeleton": "^3.4.0", "react-oauth": "^0.0.1", + "react-qr-barcode-scanner": "^2.1.8", "react-quill": "^2.0.0", "react-router-dom": "^6.23.0", "react-router-hash-link": "^2.4.3", @@ -1541,20 +1545,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/console/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/console/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1570,22 +1560,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/console/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/console/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/console/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1652,20 +1626,6 @@ } } }, - "node_modules/@jest/core/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/core/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1681,22 +1641,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/core/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/core/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/core/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1825,20 +1769,6 @@ } } }, - "node_modules/@jest/reporters/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/reporters/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1854,22 +1784,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/reporters/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/reporters/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/reporters/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -1966,20 +1880,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/transform/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/transform/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -1995,22 +1895,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/transform/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/transform/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/transform/node_modules/convert-source-map": { "version": "1.9.0", "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.9.0.tgz", @@ -2051,20 +1935,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/@jest/types/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/@jest/types/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -2080,22 +1950,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/@jest/types/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/@jest/types/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/@jest/types/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -3426,6 +3280,28 @@ "url": "https://github.com/wojtekmaj/date-utils?sponsor=1" } }, + "node_modules/@zxing/library": { + "version": "0.21.3", + "resolved": "https://registry.npmjs.org/@zxing/library/-/library-0.21.3.tgz", + "integrity": "sha512-hZHqFe2JyH/ZxviJZosZjV+2s6EDSY0O24R+FQmlWZBZXP9IqMo7S3nb3+2LBWxodJQkSurdQGnqE7KXqrYgow==", + "license": "MIT", + "dependencies": { + "ts-custom-error": "^3.2.1" + }, + "engines": { + "node": ">= 10.4.0" + }, + "optionalDependencies": { + "@zxing/text-encoding": "~0.9.0" + } + }, + "node_modules/@zxing/text-encoding": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/@zxing/text-encoding/-/text-encoding-0.9.0.tgz", + "integrity": "sha512-U/4aVJ2mxI0aDNI8Uq0wEhMgY+u4CNtEb0om3+y3+niDAsoTCOB33UF0sxpzqzdqXLqmvc+vZyAt4O8pPdfkwA==", + "license": "(Unlicense OR Apache-2.0)", + "optional": true + }, "node_modules/abbrev": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.1.1.tgz", @@ -3551,6 +3427,21 @@ "node": ">=8" } }, + "node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "license": "MIT", + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, "node_modules/anymatch": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.3.tgz", @@ -3811,20 +3702,6 @@ "@babel/core": "^7.8.0" } }, - "node_modules/babel-jest/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/babel-jest/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -3840,22 +3717,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/babel-jest/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/babel-jest/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/babel-jest/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -4565,36 +4426,6 @@ "node": ">=12" } }, - "node_modules/cliui/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/cliui/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/cliui/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/cliui/node_modules/wrap-ansi": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-7.0.0.tgz", @@ -4650,6 +4481,24 @@ "resolved": "https://registry.npmjs.org/collect-v8-coverage/-/collect-v8-coverage-1.0.2.tgz", "integrity": "sha512-lHl4d5/ONEbLlJvaJNtsF/Lz+WvB07u2ycqTYbdrq7UypDXailES4valYb2eWiJFxZlVmpGekfqoxQhzyFdT4Q==" }, + "node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "license": "MIT", + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "license": "MIT" + }, "node_modules/color-support": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/color-support/-/color-support-1.1.3.tgz", @@ -4933,6 +4782,15 @@ } } }, + "node_modules/decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==", + "license": "MIT", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/decompress-response": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-6.0.0.tgz", @@ -5091,6 +4949,12 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, + "node_modules/dijkstrajs": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/dijkstrajs/-/dijkstrajs-1.0.3.tgz", + "integrity": "sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==", + "license": "MIT" + }, "node_modules/dir-glob": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-3.0.1.tgz", @@ -5579,21 +5443,6 @@ "url": "https://opencollective.com/eslint" } }, - "node_modules/eslint/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dev": true, - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/eslint/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -5610,28 +5459,10 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/eslint/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dev": true, - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/eslint/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", - "dev": true - }, - "node_modules/eslint/node_modules/escape-string-regexp": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", - "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", + "node_modules/eslint/node_modules/escape-string-regexp": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", + "integrity": "sha512-TtpcNJ3XAzx3Gq8sWRzJaVajRs0uVxA2YAkdb1jm2YkPz4G6egUFAyA3n5vtEIZefPk5Wa4UXbKuS5fKkJWdgA==", "dev": true, "engines": { "node": ">=10" @@ -6620,6 +6451,12 @@ "node": ">=8.0.0" } }, + "node_modules/html5-qrcode": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/html5-qrcode/-/html5-qrcode-2.3.8.tgz", + "integrity": "sha512-jsr4vafJhwoLVEDW3n1KvPnCCXWaQfRng0/EEYk1vNcQGcG/htAdhJX0be8YyqMoSz7+hZvOZSTAepsabiuhiQ==", + "license": "Apache-2.0" + }, "node_modules/http-cache-semantics": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-4.1.1.tgz", @@ -7539,20 +7376,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-circus/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-circus/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7568,22 +7391,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-circus/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-circus/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-circus/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7636,20 +7443,6 @@ } } }, - "node_modules/jest-cli/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-cli/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7665,22 +7458,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-cli/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-cli/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-cli/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7744,20 +7521,6 @@ } } }, - "node_modules/jest-config/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-config/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7773,22 +7536,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-config/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-config/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-config/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7822,20 +7569,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-diff/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-diff/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7851,22 +7584,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-diff/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-diff/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-diff/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7912,20 +7629,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-each/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-each/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -7941,22 +7644,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-each/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-each/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-each/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8050,20 +7737,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-matcher-utils/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-matcher-utils/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8079,22 +7752,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-matcher-utils/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-matcher-utils/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-matcher-utils/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8133,20 +7790,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-message-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-message-util/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8162,22 +7805,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-message-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-message-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-message-util/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8264,20 +7891,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-resolve/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-resolve/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8293,22 +7906,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-resolve/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-resolve/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-resolve/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8375,20 +7972,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-runner/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-runner/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8404,22 +7987,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-runner/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runner/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-runner/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8471,20 +8038,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-runtime/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-runtime/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8500,22 +8053,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-runtime/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-runtime/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-runtime/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8558,28 +8095,14 @@ "jest-get-type": "^28.0.2", "jest-haste-map": "^28.1.3", "jest-matcher-utils": "^28.1.3", - "jest-message-util": "^28.1.3", - "jest-util": "^28.1.3", - "natural-compare": "^1.4.0", - "pretty-format": "^28.1.3", - "semver": "^7.3.5" - }, - "engines": { - "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" - } - }, - "node_modules/jest-snapshot/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" + "jest-message-util": "^28.1.3", + "jest-util": "^28.1.3", + "natural-compare": "^1.4.0", + "pretty-format": "^28.1.3", + "semver": "^7.3.5" }, "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" + "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, "node_modules/jest-snapshot/node_modules/chalk": { @@ -8597,22 +8120,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-snapshot/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-snapshot/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-snapshot/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8659,20 +8166,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-util/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-util/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8688,22 +8181,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-util/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-util/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-util/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8739,20 +8216,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-validate/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-validate/node_modules/camelcase": { "version": "6.3.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-6.3.0.tgz", @@ -8779,22 +8242,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-validate/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-validate/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-validate/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -8832,20 +8279,6 @@ "node": "^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0" } }, - "node_modules/jest-watcher/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, "node_modules/jest-watcher/node_modules/chalk": { "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", @@ -8861,22 +8294,6 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, - "node_modules/jest-watcher/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/jest-watcher/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/jest-watcher/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -11074,6 +10491,15 @@ "node": ">=8" } }, + "node_modules/pngjs": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/pngjs/-/pngjs-5.0.0.tgz", + "integrity": "sha512-40QW5YalBNfQo5yRYmiw7Yz6TKKVr3h6970B2YE+3fQpsWcrbj1PzJgxeJ19DRQjhMbKPIuMY8rFaXc8moolVw==", + "license": "MIT", + "engines": { + "node": ">=10.13.0" + } + }, "node_modules/possible-typed-array-names": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/possible-typed-array-names/-/possible-typed-array-names-1.0.0.tgz", @@ -11280,6 +10706,150 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/qrcode": { + "version": "1.5.4", + "resolved": "https://registry.npmjs.org/qrcode/-/qrcode-1.5.4.tgz", + "integrity": "sha512-1ca71Zgiu6ORjHqFBDpnSMTR2ReToX4l1Au1VFLyVeBTFavzQnv5JxMFr3ukHVKpSrSA2MCk0lNJSykjUfz7Zg==", + "license": "MIT", + "dependencies": { + "dijkstrajs": "^1.0.1", + "pngjs": "^5.0.0", + "yargs": "^15.3.1" + }, + "bin": { + "qrcode": "bin/qrcode" + }, + "engines": { + "node": ">=10.13.0" + } + }, + "node_modules/qrcode.react": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/qrcode.react/-/qrcode.react-4.2.0.tgz", + "integrity": "sha512-QpgqWi8rD9DsS9EP3z7BT+5lY5SFhsqGjpgW5DY/i3mK4M9DTBNz3ErMi8BWYEfI3L0d8GIbGmcdFAS1uIRGjA==", + "license": "ISC", + "peerDependencies": { + "react": "^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0" + } + }, + "node_modules/qrcode/node_modules/cliui": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-6.0.0.tgz", + "integrity": "sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==", + "license": "ISC", + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.0", + "wrap-ansi": "^6.2.0" + } + }, + "node_modules/qrcode/node_modules/find-up": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-4.1.0.tgz", + "integrity": "sha512-PpOwAdQ/YlXQ2vj8a3h8IipDuYRi3wceVQQGYWxNINccq40Anw7BlsEXCMbt1Zt+OLA6Fq9suIpIWD0OsnISlw==", + "license": "MIT", + "dependencies": { + "locate-path": "^5.0.0", + "path-exists": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/locate-path": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-5.0.0.tgz", + "integrity": "sha512-t7hw9pI+WvuwNJXwk5zVHpyhIqzg2qTlklJOf0mVxGSbe3Fp2VieZcduNYjaLDoy6p9uGpQEGWG87WpMKlNq8g==", + "license": "MIT", + "dependencies": { + "p-locate": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/p-limit": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.3.0.tgz", + "integrity": "sha512-//88mFWSJx8lxCzwdAABTJL2MyWB12+eIY7MDL2SqLmAkeKU9qxRvWuSyTjm3FUmpBEMuFfckAIqEaVGUDxb6w==", + "license": "MIT", + "dependencies": { + "p-try": "^2.0.0" + }, + "engines": { + "node": ">=6" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/qrcode/node_modules/p-locate": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-4.1.0.tgz", + "integrity": "sha512-R79ZZ/0wAxKGu3oYMlz8jy/kbhsNrS7SKZ7PxEHBgJ5+F2mtFW2fK2cOtBh1cHYkQsbzFV7I+EoRKe6Yt0oK7A==", + "license": "MIT", + "dependencies": { + "p-limit": "^2.2.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/wrap-ansi": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-6.2.0.tgz", + "integrity": "sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==", + "license": "MIT", + "dependencies": { + "ansi-styles": "^4.0.0", + "string-width": "^4.1.0", + "strip-ansi": "^6.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/y18n": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-4.0.3.tgz", + "integrity": "sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==", + "license": "ISC" + }, + "node_modules/qrcode/node_modules/yargs": { + "version": "15.4.1", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-15.4.1.tgz", + "integrity": "sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==", + "license": "MIT", + "dependencies": { + "cliui": "^6.0.0", + "decamelize": "^1.2.0", + "find-up": "^4.1.0", + "get-caller-file": "^2.0.1", + "require-directory": "^2.1.1", + "require-main-filename": "^2.0.0", + "set-blocking": "^2.0.0", + "string-width": "^4.2.0", + "which-module": "^2.0.0", + "y18n": "^4.0.0", + "yargs-parser": "^18.1.2" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/qrcode/node_modules/yargs-parser": { + "version": "18.1.3", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-18.1.3.tgz", + "integrity": "sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==", + "license": "ISC", + "dependencies": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/queue-microtask": { "version": "1.2.3", "resolved": "https://registry.npmjs.org/queue-microtask/-/queue-microtask-1.2.3.tgz", @@ -11653,6 +11223,20 @@ "react-dom": "^15.5.x || ^16.x || ^17.x || ^18.x" } }, + "node_modules/react-qr-barcode-scanner": { + "version": "2.1.8", + "resolved": "https://registry.npmjs.org/react-qr-barcode-scanner/-/react-qr-barcode-scanner-2.1.8.tgz", + "integrity": "sha512-REbb+BWmPjvYIAZi6/iYrRupnK4e8d39m1YExhXk+XkKnz/aU/JembC1s+6ZO6jGVXnsGkh25Dwctcrm1HsK4g==", + "license": "MIT", + "dependencies": { + "@zxing/library": "^0.21.3", + "react-webcam": "^7.2.0" + }, + "peerDependencies": { + "react": ">=18.0.0", + "react-dom": ">=18.0.0" + } + }, "node_modules/react-quill": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/react-quill/-/react-quill-2.0.0.tgz", @@ -11863,6 +11447,16 @@ "react-dom": "^16.0.0 || ^17.0.0 || ^18.0.0" } }, + "node_modules/react-webcam": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/react-webcam/-/react-webcam-7.2.0.tgz", + "integrity": "sha512-xkrzYPqa1ag2DP+2Q/kLKBmCIfEx49bVdgCCCcZf88oF+0NPEbkwYk3/s/C7Zy0mhM8k+hpdNkBLzxg8H0aWcg==", + "license": "MIT", + "peerDependencies": { + "react": ">=16.2.0", + "react-dom": ">=16.2.0" + } + }, "node_modules/react-youtube": { "version": "10.1.0", "resolved": "https://registry.npmjs.org/react-youtube/-/react-youtube-10.1.0.tgz", @@ -12085,6 +11679,12 @@ "node": ">=0.10.0" } }, + "node_modules/require-main-filename": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-2.0.0.tgz", + "integrity": "sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==", + "license": "ISC" + }, "node_modules/resolve": { "version": "2.0.0-next.5", "resolved": "https://registry.npmjs.org/resolve/-/resolve-2.0.0-next.5.tgz", @@ -13034,6 +12634,15 @@ "node": ">=0.10.0" } }, + "node_modules/ts-custom-error": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/ts-custom-error/-/ts-custom-error-3.3.1.tgz", + "integrity": "sha512-5OX1tzOjxWEgsr/YEUWSuPrQ00deKLh6D7OTWcvNHm12/7QPyRh8SYpyWvA4IZv8H/+GQWQEh/kwo95Q9OVW1A==", + "license": "MIT", + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/tslib": { "version": "2.6.2", "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.6.2.tgz", @@ -13626,6 +13235,12 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/which-module": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.1.tgz", + "integrity": "sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==", + "license": "ISC" + }, "node_modules/which-typed-array": { "version": "1.1.15", "resolved": "https://registry.npmjs.org/which-typed-array/-/which-typed-array-1.1.15.tgz", @@ -13771,36 +13386,6 @@ "url": "https://github.com/chalk/wrap-ansi?sponsor=1" } }, - "node_modules/wrap-ansi-cjs/node_modules/ansi-styles": { - "version": "4.3.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", - "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", - "dependencies": { - "color-convert": "^2.0.1" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/chalk/ansi-styles?sponsor=1" - } - }, - "node_modules/wrap-ansi-cjs/node_modules/color-convert": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", - "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", - "dependencies": { - "color-name": "~1.1.4" - }, - "engines": { - "node": ">=7.0.0" - } - }, - "node_modules/wrap-ansi-cjs/node_modules/color-name": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" - }, "node_modules/wrap-ansi/node_modules/ansi-regex": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-6.0.1.tgz", diff --git a/package.json b/package.json index 9eb84216..ebe1627f 100644 --- a/package.json +++ b/package.json @@ -29,6 +29,7 @@ "date-fns": "^3.6.0", "framer-motion": "^11.2.10", "html2canvas": "^1.4.1", + "html5-qrcode": "^2.3.8", "js-confetti": "^0.12.0", "load-script": "^2.0.0", "lucide-react": "^0.379.0", @@ -36,6 +37,8 @@ "motion": "^11.13.1", "nanoid": "^5.0.7", "prop-types": "^15.8.1", + "qrcode": "^1.5.4", + "qrcode.react": "^4.2.0", "react": "^18.2.0", "react-avatar-editor": "^13.0.2", "react-blurhash": "^0.3.0", @@ -52,6 +55,7 @@ "react-loading-indicators": "^0.2.3", "react-loading-skeleton": "^3.4.0", "react-oauth": "^0.0.1", + "react-qr-barcode-scanner": "^2.1.8", "react-quill": "^2.0.0", "react-router-dom": "^6.23.0", "react-router-hash-link": "^2.4.3", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 6db197a2..85b5a747 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -65,6 +65,9 @@ importers: html2canvas: specifier: ^1.4.1 version: 1.4.1 + html5-qrcode: + specifier: ^2.3.8 + version: 2.3.8 js-confetti: specifier: ^0.12.0 version: 0.12.0 @@ -86,6 +89,12 @@ importers: prop-types: specifier: ^15.8.1 version: 15.8.1 + qrcode: + specifier: ^1.5.4 + version: 1.5.4 + qrcode.react: + specifier: ^4.2.0 + version: 4.2.0(react@18.3.1) react: specifier: ^18.2.0 version: 18.3.1 @@ -134,6 +143,9 @@ importers: react-oauth: specifier: ^0.0.1 version: 0.0.1 + react-qr-barcode-scanner: + specifier: ^2.1.8 + version: 2.1.8(react-dom@18.3.1(react@18.3.1))(react@18.3.1) react-quill: specifier: ^2.0.0 version: 2.0.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1) @@ -1212,6 +1224,13 @@ packages: '@wojtekmaj/date-utils@1.5.1': resolution: {integrity: sha512-+i7+JmNiE/3c9FKxzWFi2IjRJ+KzZl1QPu6QNrsgaa2MuBgXvUy4gA1TVzf/JMdIIloB76xSKikTWuyYAIVLww==} + '@zxing/library@0.21.3': + resolution: {integrity: sha512-hZHqFe2JyH/ZxviJZosZjV+2s6EDSY0O24R+FQmlWZBZXP9IqMo7S3nb3+2LBWxodJQkSurdQGnqE7KXqrYgow==} + engines: {node: '>= 10.4.0'} + + '@zxing/text-encoding@0.9.0': + resolution: {integrity: sha512-U/4aVJ2mxI0aDNI8Uq0wEhMgY+u4CNtEb0om3+y3+niDAsoTCOB33UF0sxpzqzdqXLqmvc+vZyAt4O8pPdfkwA==} + abbrev@1.1.1: resolution: {integrity: sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==} @@ -1550,6 +1569,9 @@ packages: resolution: {integrity: sha512-+W/5efTR7y5HRD7gACw9yQjqMVvEMLBHmboM/kPWam+H+Hmyrgjh6YncVKK122YZkXrLudzTuAukUw9FnMf7IQ==} engines: {node: 10.* || >= 12.*} + cliui@6.0.0: + resolution: {integrity: sha512-t6wbgtoCXvAzst7QgXxJYqPt0usEfbgQdftEPbLL/cvv6HPE5VgvqCuAIDR0NgU52ds6rFwqrgakNLrHEjCbrQ==} + cliui@8.0.1: resolution: {integrity: sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==} engines: {node: '>=12'} @@ -1692,6 +1714,10 @@ packages: supports-color: optional: true + decamelize@1.2.0: + resolution: {integrity: sha512-z2S+W9X73hAUUki+N+9Za2lBlun89zigOyGrsax+KUQ6wKW4ZoWpEYBkGhQjwAjjDCkWxhY0VKEhk8wzY7F5cA==} + engines: {node: '>=0.10.0'} + decompress-response@6.0.0: resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==} engines: {node: '>=10'} @@ -1748,6 +1774,9 @@ packages: resolution: {integrity: sha512-FU0iFaH/E23a+a718l8Qa/19bF9p06kgE0KipMOMadwa3SjnaElKzPaUC0vnibs6/B/9ni97s61mcejk8W1fQw==} engines: {node: ^12.13.0 || ^14.15.0 || ^16.10.0 || >=17.0.0} + dijkstrajs@1.0.3: + resolution: {integrity: sha512-qiSlmBq9+BCdCA/L46dw8Uy93mloxsPSbwnm5yrKn2vMPiy8KyAskTF6zuV/j5BMsmOGZDPs7KjU+mjb670kfA==} + dir-glob@3.0.1: resolution: {integrity: sha512-WkrWp9GR4KXfKGYzOLmTuGVi1UWFfws377n9cc55/tb6DuqyF6pcQ5AbiHEshaDpY9v6oaSr2XCDidGmMwdzIA==} engines: {node: '>=8'} @@ -2284,6 +2313,9 @@ packages: resolution: {integrity: sha512-fPU6BHNpsyIhr8yyMpTLLxAbkaK8ArIBcmZIRiBLiDhjeqvXolaEmDGmELFuX9I4xDcaKKcJl+TKZLqruBbmWA==} engines: {node: '>=8.0.0'} + html5-qrcode@2.3.8: + resolution: {integrity: sha512-jsr4vafJhwoLVEDW3n1KvPnCCXWaQfRng0/EEYk1vNcQGcG/htAdhJX0be8YyqMoSz7+hZvOZSTAepsabiuhiQ==} + http-cache-semantics@4.1.1: resolution: {integrity: sha512-er295DKPVsV82j5kw1Gjt+ADA/XYHsajl82cGNQG2eyoPkvgUhX+nDIyelzhIWbbsXP39EHcI6l5tYs2FYqYXQ==} @@ -3287,6 +3319,10 @@ packages: resolution: {integrity: sha512-HRDzbaKjC+AOWVXxAU/x54COGeIv9eb+6CkDSQoNTt4XyWoIJvuPsXizxu/Fr23EiekbtZwmh1IcIG/l/a10GQ==} engines: {node: '>=8'} + pngjs@5.0.0: + resolution: {integrity: sha512-40QW5YalBNfQo5yRYmiw7Yz6TKKVr3h6970B2YE+3fQpsWcrbj1PzJgxeJ19DRQjhMbKPIuMY8rFaXc8moolVw==} + engines: {node: '>=10.13.0'} + possible-typed-array-names@1.0.0: resolution: {integrity: sha512-d7Uw+eZoloe0EHDIYoe+bQ5WXnGMOpmiZFTuMWCwpjzzkL2nTjcKiAk4hh8TjnGye2TwWOk3UXucZ+3rbmBa8Q==} engines: {node: '>= 0.4'} @@ -3351,6 +3387,16 @@ packages: resolution: {integrity: sha512-FLpr4flz5xZTSJxSeaheeMKN/EDzMdK7b8PTOC6a5PYFKTucWbdqjgqaEyH0shFiSJrVB1+Qqi4Tk19ccU6Aug==} engines: {node: '>=12.20'} + qrcode.react@4.2.0: + resolution: {integrity: sha512-QpgqWi8rD9DsS9EP3z7BT+5lY5SFhsqGjpgW5DY/i3mK4M9DTBNz3ErMi8BWYEfI3L0d8GIbGmcdFAS1uIRGjA==} + peerDependencies: + react: ^16.8.0 || ^17.0.0 || ^18.0.0 || ^19.0.0 + + qrcode@1.5.4: + resolution: {integrity: sha512-1ca71Zgiu6ORjHqFBDpnSMTR2ReToX4l1Au1VFLyVeBTFavzQnv5JxMFr3ukHVKpSrSA2MCk0lNJSykjUfz7Zg==} + engines: {node: '>=10.13.0'} + hasBin: true + queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} @@ -3501,6 +3547,12 @@ packages: react: ^15.5.x || ^16.x || ^17.x || ^18.x react-dom: ^15.5.x || ^16.x || ^17.x || ^18.x + react-qr-barcode-scanner@2.1.8: + resolution: {integrity: sha512-REbb+BWmPjvYIAZi6/iYrRupnK4e8d39m1YExhXk+XkKnz/aU/JembC1s+6ZO6jGVXnsGkh25Dwctcrm1HsK4g==} + peerDependencies: + react: '>=18.0.0' + react-dom: '>=18.0.0' + react-quill@2.0.0: resolution: {integrity: sha512-4qQtv1FtCfLgoD3PXAur5RyxuUbPXQGOHgTlFie3jtxp43mXDtzCKaOgQ3mLyZfi1PUlyjycfivKelFhy13QUg==} peerDependencies: @@ -3589,6 +3641,12 @@ packages: react: ^16.0.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.0.0 || ^17.0.0 || ^18.0.0 + react-webcam@7.2.0: + resolution: {integrity: sha512-xkrzYPqa1ag2DP+2Q/kLKBmCIfEx49bVdgCCCcZf88oF+0NPEbkwYk3/s/C7Zy0mhM8k+hpdNkBLzxg8H0aWcg==} + peerDependencies: + react: '>=16.2.0' + react-dom: '>=16.2.0' + react-youtube@10.1.0: resolution: {integrity: sha512-ZfGtcVpk0SSZtWCSTYOQKhfx5/1cfyEW1JN/mugGNfAxT3rmVJeMbGpA9+e78yG21ls5nc/5uZJETE3cm3knBg==} engines: {node: '>= 14.x'} @@ -3647,6 +3705,9 @@ packages: resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} engines: {node: '>=0.10.0'} + require-main-filename@2.0.0: + resolution: {integrity: sha512-NKN5kMDylKuldxYLSUfrbo5Tuzh4hd+2E8NPPX02mZtn1VuREQToYe/ZdlJy+J3uCpfaiGF05e7B8W0iXbQHmg==} + resolve-alpn@1.2.1: resolution: {integrity: sha512-0a1F4l73/ZFZOakJnQ3FvkJ2+gSTQWz/r2KE5OdDY0TxPm5h4GkqkWWfM47T7HsbnOtcJVEF4epCVy6u7Q3K+g==} @@ -4004,6 +4065,10 @@ packages: resolution: {integrity: sha512-pkonvlKk8/ZuR0D5tLW8ljt5I8kmxp2XKymhepUeOdCEfKpZaktSArkLHZt76OB1ZvO9bssUsDty4SWhLvZpLg==} engines: {node: '>=0.10.0'} + ts-custom-error@3.3.1: + resolution: {integrity: sha512-5OX1tzOjxWEgsr/YEUWSuPrQ00deKLh6D7OTWcvNHm12/7QPyRh8SYpyWvA4IZv8H/+GQWQEh/kwo95Q9OVW1A==} + engines: {node: '>=14.0.0'} + tslib@2.6.2: resolution: {integrity: sha512-AEYxH93jGFPn/a2iVAwW87VuUIkR1FVUKB77NwMF7nBTDkDrrT/Hpt/IrCJ0QXhW27jTBDcf5ZY7w6RiqTMw2Q==} @@ -4193,6 +4258,9 @@ packages: resolution: {integrity: sha512-K4jVyjnBdgvc86Y6BkaLZEN933SwYOuBFkdmBu9ZfkcAbdVbpITnDmjvZ/aQjRXQrv5EPkTnD1s39GiiqbngCw==} engines: {node: '>= 0.4'} + which-module@2.0.1: + resolution: {integrity: sha512-iBdZ57RDvnOR9AGBhML2vFZf7h8vmBjhoaZqODJBFWHVtKkDmKuHai3cx5PgVMrX5YDNp27AofYbAwctSS+vhQ==} + which-typed-array@1.1.15: resolution: {integrity: sha512-oV0jmFtUky6CXfkqehVvBP/LSWJ2sy4vWMioiENyJLePrBO/yKyV9OyJySfAKosh+RYkIl5zJCNZ8/4JncrpdA==} engines: {node: '>= 0.4'} @@ -4226,6 +4294,10 @@ packages: resolution: {integrity: sha512-OELeY0Q61OXpdUfTp+oweA/vtLVg5VDOXh+3he3PNzLGG/y0oylSOC1xRVj0+l4vQ3tj/bB1HVHv1ocXkQceFA==} engines: {node: '>=0.8'} + wrap-ansi@6.2.0: + resolution: {integrity: sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==} + engines: {node: '>=8'} + wrap-ansi@7.0.0: resolution: {integrity: sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==} engines: {node: '>=10'} @@ -4253,6 +4325,9 @@ packages: engines: {node: '>=0.8'} hasBin: true + y18n@4.0.3: + resolution: {integrity: sha512-JKhqTOwSrqNA1NY5lSztJ1GrBiUodLMmIZuLiDaMRJ+itFd+ABVE8XBjOvIWL+rSqNDC74LCSFmlb/U4UZ4hJQ==} + y18n@5.0.8: resolution: {integrity: sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==} engines: {node: '>=10'} @@ -4267,10 +4342,18 @@ packages: resolution: {integrity: sha512-r3vXyErRCYJ7wg28yvBY5VSoAF8ZvlcW9/BwUzEtUsjvX/DKs24dIkuwjtuprwJJHsbyUbLApepYTR1BN4uHrg==} engines: {node: '>= 6'} + yargs-parser@18.1.3: + resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==} + engines: {node: '>=6'} + yargs-parser@21.1.1: resolution: {integrity: sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==} engines: {node: '>=12'} + yargs@15.4.1: + resolution: {integrity: sha512-aePbxDmcYW++PaqBsJ+HYUFwCdv4LVvdnhBy78E57PIor8/OVvhMrADFFEDh8DHDFRv/O9i3lPhsENjO7QX0+A==} + engines: {node: '>=8'} + yargs@17.7.2: resolution: {integrity: sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==} engines: {node: '>=12'} @@ -5392,6 +5475,15 @@ snapshots: '@wojtekmaj/date-utils@1.5.1': {} + '@zxing/library@0.21.3': + dependencies: + ts-custom-error: 3.3.1 + optionalDependencies: + '@zxing/text-encoding': 0.9.0 + + '@zxing/text-encoding@0.9.0': + optional: true + abbrev@1.1.1: {} acorn-jsx@5.3.2(acorn@8.12.0): @@ -5833,6 +5925,12 @@ snapshots: optionalDependencies: '@colors/colors': 1.5.0 + cliui@6.0.0: + dependencies: + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi: 6.2.0 + cliui@8.0.1: dependencies: string-width: 4.2.3 @@ -5965,6 +6063,8 @@ snapshots: dependencies: ms: 2.1.2 + decamelize@1.2.0: {} + decompress-response@6.0.0: dependencies: mimic-response: 3.1.0 @@ -6012,6 +6112,8 @@ snapshots: diff-sequences@28.1.1: {} + dijkstrajs@1.0.3: {} + dir-glob@3.0.1: dependencies: path-type: 4.0.0 @@ -6696,6 +6798,8 @@ snapshots: css-line-break: 2.1.0 text-segmentation: 1.0.3 + html5-qrcode@2.3.8: {} + http-cache-semantics@4.1.1: {} http-proxy-agent@5.0.0: @@ -7928,6 +8032,8 @@ snapshots: dependencies: find-up: 4.1.0 + pngjs@5.0.0: {} + possible-typed-array-names@1.0.0: {} postcss-value-parser@4.2.0: {} @@ -7984,6 +8090,16 @@ snapshots: dependencies: escape-goat: 4.0.0 + qrcode.react@4.2.0(react@18.3.1): + dependencies: + react: 18.3.1 + + qrcode@1.5.4: + dependencies: + dijkstrajs: 1.0.3 + pngjs: 5.0.0 + yargs: 15.4.1 + queue-microtask@1.2.3: {} quick-lru@5.1.1: {} @@ -8154,6 +8270,13 @@ snapshots: react: 18.3.1 react-dom: 18.3.1(react@18.3.1) + react-qr-barcode-scanner@2.1.8(react-dom@18.3.1(react@18.3.1))(react@18.3.1): + dependencies: + '@zxing/library': 0.21.3 + react: 18.3.1 + react-dom: 18.3.1(react@18.3.1) + react-webcam: 7.2.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1) + react-quill@2.0.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1): dependencies: '@types/quill': 1.3.10 @@ -8280,6 +8403,11 @@ snapshots: react-dom: 18.3.1(react@18.3.1) scriptjs: 2.5.9 + react-webcam@7.2.0(react-dom@18.3.1(react@18.3.1))(react@18.3.1): + dependencies: + react: 18.3.1 + react-dom: 18.3.1(react@18.3.1) + react-youtube@10.1.0(react@18.3.1): dependencies: fast-deep-equal: 3.1.3 @@ -8348,6 +8476,8 @@ snapshots: require-from-string@2.0.2: {} + require-main-filename@2.0.0: {} + resolve-alpn@1.2.1: {} resolve-cwd@3.0.0: @@ -8738,6 +8868,8 @@ snapshots: dependencies: escape-string-regexp: 1.0.5 + ts-custom-error@3.3.1: {} + tslib@2.6.2: {} tslib@2.6.3: {} @@ -8946,6 +9078,8 @@ snapshots: is-weakmap: 2.0.2 is-weakset: 2.0.3 + which-module@2.0.1: {} + which-typed-array@1.1.15: dependencies: available-typed-arrays: 1.0.7 @@ -8976,6 +9110,12 @@ snapshots: word@0.3.0: {} + wrap-ansi@6.2.0: + dependencies: + ansi-styles: 4.3.0 + string-width: 4.2.3 + strip-ansi: 6.0.1 + wrap-ansi@7.0.0: dependencies: ansi-styles: 4.3.0 @@ -9014,6 +9154,8 @@ snapshots: wmf: 1.0.2 word: 0.3.0 + y18n@4.0.3: {} + y18n@5.0.8: {} yallist@3.1.1: {} @@ -9022,8 +9164,27 @@ snapshots: yaml@1.10.2: {} + yargs-parser@18.1.3: + dependencies: + camelcase: 5.3.1 + decamelize: 1.2.0 + yargs-parser@21.1.1: {} + yargs@15.4.1: + dependencies: + cliui: 6.0.0 + decamelize: 1.2.0 + find-up: 4.1.0 + get-caller-file: 2.0.5 + require-directory: 2.1.1 + require-main-filename: 2.0.0 + set-blocking: 2.0.0 + string-width: 4.2.3 + which-module: 2.0.1 + y18n: 4.0.3 + yargs-parser: 18.1.3 + yargs@17.7.2: dependencies: cliui: 8.0.1 diff --git a/src/App.jsx b/src/App.jsx index 6163bf62..8f073d66 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -59,6 +59,7 @@ const Login = lazy(() => import("./pages/Authentication/Login/Login")); const OTPInput = lazy(() => import("./authentication/Login/ForgotPassword/OTPInput") ); +const AttendancePage = lazy(() => import('./pages/AttendancePage/AttendancePage')); const MainLayout = () => { const location = useLocation(); @@ -184,6 +185,7 @@ function App() { element={[]} /> )} + } /> )} { const { info } = data; const authCtx = useContext(AuthContext); const [isOpen, setOpen] = useState(false); + const [isQRModalOpen, setQRModalOpen] = useState(false); const [isHovered, setisHovered] = useState(false); const [remainingTime, setRemainingTime] = useState(""); const [btnTxt, setBtnTxt] = useState("Register Now"); @@ -260,6 +264,30 @@ const EventCard = (props) => { setOpen(false); }; + const handleQRCode = () => { + if (authCtx.isLoggedIn && authCtx.user.regForm && authCtx.user.regForm.includes(data.id)) { + setQRModalOpen(!isQRModalOpen); + } else if (!authCtx.isLoggedIn) { + setAlert({ + type: "info", + message: "Please login to access attendance QR code.", + position: "bottom-right", + duration: 3000, + }); + } else { + setAlert({ + type: "info", + message: "You need to register for this event first to get the attendance QR code.", + position: "bottom-right", + duration: 3000, + }); + } + }; + + const handleCloseQRModal = () => { + setQRModalOpen(false); + }; + const isValiedState = () => { if ( btnTxt === "Closed" || @@ -385,6 +413,21 @@ const EventCard = (props) => { />
)} + {type === "ongoing" && authCtx.isLoggedIn && authCtx.user.regForm && authCtx.user.regForm.includes(data.id) && ( +
+ +
+ )}
@@ -567,6 +610,9 @@ const EventCard = (props) => { {isOpen && type === "ongoing" && ( )} + {isQRModalOpen && type === "ongoing" && ( + + )} {enableEdit && isHovered && authCtx.user.access === "ADMIN" && (
setisHovered(true)} diff --git a/src/components/EventCard/styles/EventCard.module.scss b/src/components/EventCard/styles/EventCard.module.scss index e9bd74cc..1ed1b89d 100644 --- a/src/components/EventCard/styles/EventCard.module.scss +++ b/src/components/EventCard/styles/EventCard.module.scss @@ -114,6 +114,33 @@ width: 1rem; } +.qrCode { + background: rgba(15, 15, 15, 0.5); + backdrop-filter: blur(1.8663231134414673px); + border: 1px solid rgb(143, 139, 139); + color: #f97507; + position: absolute; + top: 3.5rem; + right: 1rem; + text-align: center; + border-radius: 7px; + font-size: 0.75rem; + font-weight: 800; + padding: 0.5rem; + display: flex; + align-items: center; + justify-content: center; + cursor: pointer; + transition: all 0.3s ease; + + +} + +.qrIcon { + height: 1rem; + width: 1rem; +} + .price p { display: flex; align-items: center; diff --git a/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx new file mode 100644 index 00000000..46e3b5b2 --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/QRCodeModal.jsx @@ -0,0 +1,142 @@ +import React, { useState, useEffect, useContext } from 'react'; +import { X } from 'lucide-react'; +import { QRCodeSVG } from 'qrcode.react'; +import AuthContext from '../../../../context/AuthContext'; +import { RecoveryContext } from '../../../../context/RecoveryContext'; +import { api } from '../../../../services'; +import { Alert } from '../../../../microInteraction'; +import style from './styles/QRCodeModal.module.scss'; + +const QRCodeModal = ({ onClose, eventId, onAttendanceMarked }) => { + const [qrCodeData, setQrCodeData] = useState(null); + const [isLoading, setIsLoading] = useState(true); + const [error, setError] = useState(null); + const [attendanceMarked, setAttendanceMarked] = useState(false); + const authCtx = useContext(AuthContext); + const recoveryCtx = useContext(RecoveryContext); + + useEffect(() => { + fetchAttendanceCode(); + }, [eventId]); + + useEffect(() => { + if (onAttendanceMarked) { + setAttendanceMarked(true); + } + }, [onAttendanceMarked]); + + const fetchAttendanceCode = async () => { + try { + setIsLoading(true); + setError(null); + + const teamCode = recoveryCtx.teamCode; + + let url = `/api/form/attendanceCode/${eventId}`; + if (teamCode && teamCode.trim() !== '') { + url += `?teamCode=${encodeURIComponent(teamCode)}`; + } + + const token = localStorage.getItem('token'); + + const response = await api.get(url, { + headers: { + 'Authorization': token + } + }); + + if (response.status === 200) { + setQrCodeData(response.data.attendanceToken); + } else { + throw new Error('Failed to fetch attendance code'); + } + } catch (error) { + setError(error?.response?.data?.message || 'Failed to generate QR code. Please try again.'); + } finally { + setIsLoading(false); + } + }; + + const handleClose = () => { + onClose(); + }; + + const handleRetry = () => { + fetchAttendanceCode(); + }; + + const handleAttendanceMarked = () => { + setAttendanceMarked(true); + }; + + const handleOK = () => { + onClose(); + }; + + const handleScanNewAttendee = () => { + setAttendanceMarked(false); + setQrCodeData(null); + fetchAttendanceCode(); + }; + + return ( +
+
+
+
+
+ +
+
Attendance QR Code
+
+ +
+ {isLoading ? ( +
+
+

Generating QR Code...

+
+ ) : error ? ( +
+

{error}

+ +
+ ) : qrCodeData ? ( +
+
+ +
+ +
+

+ Show this QR code to event organizers for attendance verification. +

+

+ This attendance QR code can be used only once. Do not share it with others.

+
+
+ ) : ( +
+

No attendance code available

+
+ )} +
+
+
+ ); +}; + +export default QRCodeModal; \ No newline at end of file diff --git a/src/features/Modals/Event/QRCodeModal/index.jsx b/src/features/Modals/Event/QRCodeModal/index.jsx new file mode 100644 index 00000000..94894e0b --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/index.jsx @@ -0,0 +1 @@ +export { default } from './QRCodeModal'; \ No newline at end of file diff --git a/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss b/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss new file mode 100644 index 00000000..18b8f56e --- /dev/null +++ b/src/features/Modals/Event/QRCodeModal/styles/QRCodeModal.module.scss @@ -0,0 +1,396 @@ +.qrContainer { + position: fixed; + top: 0; + left: 0; + width: 100%; + height: 100%; + z-index: 50; + display: flex; + justify-content: center; + align-items: center; + padding: 1rem; +} + +.overlay { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + background: rgba(0, 0, 0, 0.5); + backdrop-filter: blur(5px); + z-index: 5; +} + +.maindiv { + z-index: 1000; + border-radius: 16px; + padding: 2rem; + position: relative; + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + background: rgba(42, 42, 42, 0.95); + border: 2px solid #444; + width: 100%; + max-width: 450px; + min-height: 400px; + box-shadow: 0 8px 32px rgba(0, 0, 0, 0.3); +} + +.header { + position: relative; + display: flex; + justify-content: space-between; + align-items: center; + margin-bottom: 2rem; + width: 100%; +} + +.closebtn { + cursor: pointer; + position: absolute; + right: 0; + top: 0; + z-index: 20; + font-size: 1.2rem; + color: #ffffff; + transition: color 0.3s ease; + padding: 0.5rem; + + &:hover { + color: #D14206; + transition: .2s linear; + } +} + +.title{ + font-weight:700; + margin-left:6.5rem; + font-size:1rem; + background: linear-gradient( + 260deg, + rgba(255, 190, 11, 0.84) -29.7%, + rgba(244, 43, 3, 0.84) 128.34% +); +color: transparent; +-webkit-background-clip: text; +background-clip: text; +} + + +.content { + flex: 1; + display: flex; + flex-direction: column; + justify-content: center; + align-items: center; + text-align: center; + width: 100%; +} + +.loadingContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #f97507; + + p { + margin: 0; + font-size: 1rem; + } +} + +.spinner { + width: 40px; + height: 40px; + border: 3px solid rgba(249, 117, 7, 0.3); + border-top: 3px solid #f97507; + border-radius: 50%; + animation: spin 1s linear infinite; +} + +@keyframes spin { + 0% { transform: rotate(0deg); } + 100% { transform: rotate(360deg); } +} + +.errorContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #ff6b6b; + + p { + margin: 0; + font-size: 1rem; + } +} + +.retryBtn { + background: linear-gradient(135deg, #f97507, #ff8c42); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + +} + +.qrContent { + display: flex; + flex-direction: column; + align-items: center; + gap: 1.5rem; + width: 100%; +} + +.qrWrapper { + padding: 1.5rem; + border-radius: 12px; + display: flex; + justify-content: center; + background-color: #ffffff; + align-items: center; + backdrop-filter: blur(10px); +} + +.qrCode { + display: block; +} + +.codeInfo { + display: flex; + flex-direction: column; + align-items: center; + gap: 0.5rem; + background: rgba(250, 250, 250, 0.1); + padding: 1rem; + border-radius: 8px; + width: 100%; +} + +.codeLabel { + margin: 0; + font-size: 0.9rem; + color: #f97507; + font-weight: 600; +} + +.codeValue { + margin: 0; + font-size: 1.2rem; + font-weight: 700; + color: #f97507; + letter-spacing: 1px; + font-family: 'Courier New', monospace; + transition: color 0.2s ease; + + &:hover { + color: #ff8c42; + } +} + +.instruction { + margin: 0; + font-size: 0.9rem; + color: #ccc; + line-height: 1.4; +} + +.noCodeContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1rem; + color: #ffa500; + + p { + margin: 0; + font-size: 1rem; + } +} + +.successContainer { + display: flex; + flex-direction: column; + align-items: center; + gap: 1.5rem; + color: #4CAF50; + text-align: center; + + h3 { + margin: 0; + font-size: 1.5rem; + font-weight: 600; + color: #4CAF50; + } + + p { + margin: 0; + font-size: 1rem; + color: #ccc; + } +} + +.successIcon { + font-size: 3rem; + color: #4CAF50; + background: rgba(76, 175, 80, 0.1); + border-radius: 50%; + width: 80px; + height: 80px; + display: flex; + align-items: center; + justify-content: center; + border: 3px solid #4CAF50; +} + +.buttonGroup { + display: flex; + gap: 1rem; + margin-top: 1rem; +} + +.okBtn { + background: linear-gradient(135deg, #4CAF50, #45a049); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + &:hover { + transform: translateY(-2px); + } +} + +.scanNewBtn { + background: linear-gradient(135deg, #f97507, #ff8c42); + border: none; + border-radius: 8px; + padding: 0.75rem 1.5rem; + color: white; + font-weight: 600; + cursor: pointer; + transition: transform 0.2s ease; + + &:hover { + transform: translateY(-2px); + } +} + +// Responsive design +@media (max-width: 768px) { + .qrContainer { + padding: 0.5rem; + } + + .maindiv { + width: 100%; + padding: 1.5rem; + min-height: 350px; + border-radius: 12px; + } + + .title { + font-size: 1.3rem; + } + + .qrWrapper { + padding: 1rem; + } + + .qrCode { + width: 180px; + height: 180px; + } +} + +@media (max-width: 480px) { + .qrContainer { + padding: 0.25rem; + } + + .maindiv { + padding: 1rem; + min-height: 320px; + } + + .title { + font-size: 1.2rem; + } + + .header { + margin-bottom: 1.5rem; + } + + .qrWrapper { + padding: 0.75rem; + } + + .qrCode { + width: 160px; + height: 160px; + } + + .codeInfo { + padding: 0.75rem; + } + + .instruction { + font-size: 0.85rem; + } + + .successContainer { + gap: 1rem; + + h3 { + font-size: 1.3rem; + } + + p { + font-size: 0.9rem; + } + } + + .successIcon { + width: 60px; + height: 60px; + font-size: 2rem; + } + + .buttonGroup { + flex-direction: column; + gap: 0.75rem; + } + + .okBtn, .scanNewBtn { + padding: 0.6rem 1.2rem; + font-size: 0.9rem; + } +} + +@media (max-width: 360px) { + .maindiv { + padding: 0.75rem; + min-height: 300px; + } + + .title { + font-size: 1.1rem; + } + + .qrCode { + width: 140px; + height: 140px; + } +} \ No newline at end of file diff --git a/src/layouts/Profile/Sidebar/Sidebar.jsx b/src/layouts/Profile/Sidebar/Sidebar.jsx index 054c1613..f669f927 100644 --- a/src/layouts/Profile/Sidebar/Sidebar.jsx +++ b/src/layouts/Profile/Sidebar/Sidebar.jsx @@ -5,6 +5,7 @@ import { TbUserEdit } from "react-icons/tb"; import { SlCalender } from "react-icons/sl"; import { SiReacthookform } from "react-icons/si"; import { FaRegNewspaper } from "react-icons/fa"; +import { LuClipboardList } from "react-icons/lu"; import AuthContext from "../../../context/AuthContext"; import styles from "./styles/Sidebar.module.scss"; @@ -62,27 +63,26 @@ const Sidebar = ({ activepage, handleChange }) => { setimagePrv(url); }; - const renderBlogMenu = () => (
handleChange("Blogs")} + onClick={() => handleChange("Blogs")} + style={{ + background: activepage === "Blogs" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Blogs" ? "text" : "initial", + backgroundClip: activepage === "Blogs" ? "text" : "initial", + color: activepage === "Blogs" ? "transparent" : "inherit", + }} + > + - {" "} - Blogs -
- ) + />{" "} + Blogs +
+ ); const renderAdminMenu = () => ( <>
{ />{" "} Form
- +
handleChange("Members")} style={{ @@ -143,6 +143,27 @@ const Sidebar = ({ activepage, handleChange }) => { />{" "} Members
+ +
handleChange("Attendance")} + style={{ + background: + activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + marginLeft: "-6px", + }} + > + {" "} + Attendance +
); @@ -203,8 +224,8 @@ const Sidebar = ({ activepage, handleChange }) => {
- {designation === "Admin" && renderAdminMenu() } - {(designation === "Admin" || authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && renderBlogMenu() } + {designation === "Admin" && renderAdminMenu()} + {(designation === "Admin" || authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && renderBlogMenu()} {designation !== "Admin" && (
handleChange("events")} @@ -213,9 +234,9 @@ const Sidebar = ({ activepage, handleChange }) => { Event - +
- + )}
{ + const [ongoingEvents, setOngoingEvents] = useState([]); + const [pastEvents, setPastEvents] = useState([]); + const [isLoading, setIsLoading] = useState(true); + const [error, setError] = useState(null); + const [showScanner, setShowScanner] = useState(false); + const [selectedEventId, setSelectedEventId] = useState(null); + const [scanner, setScanner] = useState(null); + const [isScanning, setIsScanning] = useState(false); + const [showSuccessModal, setShowSuccessModal] = useState(false); + const [attendedUser, setAttendedUser] = useState(null); + const [hasShownAlert, setHasShownAlert] = useState(false); + const [isSuccess, setIsSuccess] = useState(false); + const authCtx = useContext(AuthContext); + + useEffect(() => { + const fetchEvents = async () => { + try { + const response = await api.get("/api/form/getAllForms"); + if (response.status === 200) { + const fetchedEvents = response.data.events; + + // sort events by priority, date, and title + const sortedEvents = fetchedEvents.sort((a, b) => { + const priorityA = parseInt(a.info.eventPriority, 10); + const priorityB = parseInt(b.info.eventPriority, 10); + const dateA = new Date(a.info.eventDate); + const dateB = new Date(b.info.eventDate); + const titleA = a.info.eventTitle || ""; + const titleB = b.info.eventTitle || ""; + + if (priorityA !== priorityB) return priorityA - priorityB; + if (dateA.getTime() !== dateB.getTime()) return dateA - dateB; + return titleA.localeCompare(titleB); + }); + + const ongoing = sortedEvents.filter(e => !e.info.isEventPast); + const past = sortedEvents + .filter(e => e.info.isEventPast) + .sort((a, b) => new Date(b.info.eventDate) - new Date(a.info.eventDate)); + + setOngoingEvents(ongoing); + setPastEvents(past); + } else { + setError("Error fetching events"); + } + } catch (err) { + console.error("Error fetching events:", err); + setError("Error fetching events"); + } finally { + setIsLoading(false); + } + }; + fetchEvents(); + }, []); + + const initializeScanner = () => { + try { + const qrScanner = new Html5QrcodeScanner( + "qr-reader", + { + fps: 10, + qrbox: { width: 250, height: 250 }, + aspectRatio: 1, + supportedScanTypes: [Html5QrcodeScanType.SCAN_TYPE_CAMERA] + }, + false + ); + + qrScanner.render(onScanSuccess, onScanFailure); + setScanner(qrScanner); + } catch (error) { + console.error("Error initializing scanner:", error); + if (!hasShownAlert) { + Alert({ + type: "error", + message: "Failed to initialize QR scanner", + position: "top-right", + }); + setHasShownAlert(true); + } + setShowScanner(false); + } + }; + + const onScanSuccess = async (decodedText) => { + setIsScanning(true); + console.log("QR Code scanned successfully:", decodedText); + console.log("Selected Event ID:", selectedEventId); + + try { + // jwt token from qr code + const response = await api.post( + `/api/form/markAttendance`, + { + formId: selectedEventId, + token: decodedText, + }, + { + headers: { + Authorization: `Bearer ${authCtx.token}`, + }, + } + ); + + if (response.status === 200) { + // store user details + setAttendedUser(response.data.user || response.data); + setIsSuccess(true); + if (scanner) { + scanner.clear(); + } + setShowSuccessModal(true); + setIsScanning(false); + + // show success alert + Alert({ + type: "success", + message: "Attendance marked successfully!", + position: "top-right", + }); + + return; // exit early + } + } catch (error) { + console.error("Error marking attendance:", error); + let errorMessage = "Failed to verify QR code"; + + if (error.response?.status === 401) { + errorMessage = "Invalid or expired QR code"; + } else if (error.response?.status === 400) { + errorMessage = error.response?.data?.message || "Invalid request"; + } else if (error.response?.status === 404) { + errorMessage = "Attendance record not found"; + } else if (error.response?.status === 403) { + errorMessage = "You don't have permission to mark attendance"; + } else if (error.response?.data?.message) { + errorMessage = error.response.data.message; + } + + // show error alert + if (!hasShownAlert) { + Alert({ + type: "error", + message: errorMessage, + position: "top-right", + }); + setHasShownAlert(true); + } + } finally { + setIsScanning(false); + } + }; + + const onScanFailure = (error) => { + console.warn(`QR Code scanning failed: ${error}`); + }; + + const handleScanQR = (eventId) => { + setSelectedEventId(eventId); + setShowScanner(true); + setHasShownAlert(false); // reset alert state + setIsSuccess(false); // reset success state + }; + + const handleCloseSuccessModal = () => { + setShowSuccessModal(false); + setAttendedUser(null); + // auto open scanner for next scan + setTimeout(() => { + setShowScanner(true); + setHasShownAlert(false); // reset alert state + setIsSuccess(false); // reset success state + }, 100); + }; + + + + const handleDownloadAttendance = async (eventId) => { + try { + const response = await api.get(`/api/form/download/${eventId}`, { + headers: { Authorization: `Bearer ${authCtx.token}` }, + responseType: "blob", + }); + const blob = new Blob([response.data], { type: "text/csv" }); + const url = window.URL.createObjectURL(blob); + const link = document.createElement("a"); + link.href = url; + link.setAttribute("download", `attendance_${eventId}.csv`); + document.body.appendChild(link); + link.click(); + link.remove(); + window.URL.revokeObjectURL(url); + + Alert({ + type: "success", + message: "Attendance file downloaded successfully!", + position: "top-right", + }); + } catch (error) { + let errorMessage = "Failed to download attendance file"; + + if (error.response?.status === 403) { + errorMessage = "You don't have permission to download attendance data"; + } else if (error.response?.status === 404) { + errorMessage = "Attendance data not found for this event"; + } else if (error.response?.data?.message) { + errorMessage = error.response.data.message; + } + + // show error alert + if (!isSuccess && !hasShownAlert) { + Alert({ + type: "error", + message: errorMessage, + position: "top-right", + }); + setHasShownAlert(true); + } + console.error("Download error:", error); + } + }; + + const renderOngoingActions = (event) => ( +
+ + + +
+ ); + + const renderPastActions = (event) => ( +
+ +
+ ); + + useEffect(() => { + if (showScanner) { + initializeScanner(); + } + return () => { + if (scanner) { + try { + scanner.clear(); + } catch (error) { + console.error("Error clearing scanner in cleanup:", error); + } + } + }; + }, [showScanner]); + + if (isLoading) { + return ( + + ); + } + + if (error) { + return
{error}
; + } + + return ( +
+

Event Attendance

+ + {showScanner && ( +
+
+ +

Scan QR Code

+
+ {isScanning && ( +
+
Processing QR Code...
+
+ )} +
+
+
+
+ )} + + {/* Success Modal */} + {showSuccessModal && attendedUser && ( +
+
+ +
+
+

Attendance Marked Successfully!

+ +
+ +
+
+
+
+ )} + + {/* Ongoing Events */} + {ongoingEvents.length > 0 && ( + <> +

Ongoing Events

+
+ {ongoingEvents.map((event) => ( +
+ { }} // fixed + customStyles={{ + eventname: { fontSize: "1.2rem" }, + registerbtn: { width: "8rem", fontSize: ".721rem" }, + eventnamep: { fontSize: "0.7rem" }, + }} + /> +
+ ))} +
+ + )} + + {/* Past Events */} + {pastEvents.length > 0 && ( + <> +

Past Events

+
+ {pastEvents.map((event) => ( +
+ { }} // fixed + customStyles={{ + eventname: { fontSize: "1.2rem" }, + registerbtn: { width: "8rem", fontSize: ".721rem" }, + eventnamep: { fontSize: "0.7rem" }, + }} + /> +
+ ))} +
+ + )} +
+ ); +}; + +export default AttendancePage; diff --git a/src/pages/AttendancePage/styles/AttendancePage.module.scss b/src/pages/AttendancePage/styles/AttendancePage.module.scss new file mode 100644 index 00000000..d8031fb0 --- /dev/null +++ b/src/pages/AttendancePage/styles/AttendancePage.module.scss @@ -0,0 +1,196 @@ +.container { + padding: 20px; + + h2 { + color: var(--primary); + margin-bottom: 20px; + } +} + +.eventGrid { + display: grid; + grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); + gap: 20px; + padding: 20px; +} + +.eventWrapper { + position: relative; +} + +.actionButtons { + display: flex; + justify-content: space-between; + gap: 10px; + margin-top: 10px; + padding: 10px; + + button { + flex: 1; + padding: 8px; + border-radius: 4px; + font-size: 14px; + + &:hover { + transform: translateY(-2px); + transition: transform 0.2s ease; + } + + &:last-child { + background: #FF8A00; + color: white; + + &:hover { + background: rgba(255, 138, 0, 0.9); + } + } + } +} + +.scannerModal { + position: fixed; + top: 0; + left: 0; + right: 0; + bottom: 0; + background: rgba(0, 0, 0, 0.85); + display: flex; + justify-content: center; + align-items: center; + z-index: 1000; +} + +.scannerContent { + background: #1a1a1a; + padding: 2rem; + border-radius: 10px; + width: 90%; + max-width: 500px; + position: relative; + + .closeButton { + position: absolute; + top: 4px; + right: 6px; + border: none; + border-radius: 50%; + width: 34px; + height: 34px; + display: flex; + align-items: center; + justify-content: center; + cursor: pointer; + color: white; + font-size: 1.2rem; + background: transparent; + + &:hover { + color: #D14206; + transition: .2s linear; + + } +} + + .scannerTitle { + color: white; + text-align: center; + margin-bottom: 1rem; + font-size: 1.2rem; + } + + .scannerArea { + border: 2px solid var(--primary); + border-radius: 8px; + overflow: hidden; + margin: 1rem 0; + + #qr-reader { + width: 100%; + + video { + width: 100% !important; + border-radius: 6px; + } + + button { + padding: 8px 16px; + background: var(--primary); + color: white; + border: none; + border-radius: 4px; + margin: 8px; + cursor: pointer; + + &:hover { + opacity: 0.9; + } + } + } + } +} + +.successContent { + text-align: center; + color: white; + + .successIcon { + font-size: 3rem; + color: #FF8A00; + margin-bottom: 1rem; + } + + .successTitle { + color: white; + margin-bottom: 1.5rem; + font-size: 1.3rem; + } + + + + .buttonGroup { + display: flex; + gap: 1rem; + justify-content: center; + margin-top: 2rem; + + button { + min-width: 120px; + border-radius: 6px; + font-weight: 600; + transition: all 0.2s ease; + + + } + } +} + +.scanningOverlay { + position: absolute; + top: 0; + left: 0; + right: 0; + bottom: 0; + background: rgba(0, 0, 0, 0.8); + display: flex; + align-items: center; + justify-content: center; + z-index: 10; + border-radius: 8px; + + .scanningText { + color: white; + font-size: 1.1rem; + font-weight: 600; + } +} + +@keyframes fadeInScale { + 0% { + opacity: 0; + transform: scale(0.5); + } + 100% { + opacity: 1; + transform: scale(1); + } +} From 9ef946abba2f3fc6fd13482007e5936dbbf5e526 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Thu, 14 Aug 2025 22:15:05 +0530 Subject: [PATCH 26/44] omega5 --- src/components/EventCard/EventCard.jsx | 16 +--------------- 1 file changed, 1 insertion(+), 15 deletions(-) diff --git a/src/components/EventCard/EventCard.jsx b/src/components/EventCard/EventCard.jsx index 1f6c1e0b..ce0399f3 100644 --- a/src/components/EventCard/EventCard.jsx +++ b/src/components/EventCard/EventCard.jsx @@ -568,21 +568,7 @@ const EventCard = (props) => {
)} - {/* See Team Details Button - Only show for team events when user is registered - {type === "ongoing" && - info.participationType === "Team" && - btnTxt === "Already Registered" && - authCtx.isLoggedIn && ( -
- -
- )} */} +
From 6da92e7db91498fb62145c7f0b5755132f66fc4f Mon Sep 17 00:00:00 2001 From: Rudrika Date: Fri, 15 Aug 2025 00:29:39 +0530 Subject: [PATCH 27/44] Download Attendance Issue Fixed --- src/layouts/Profile/Sidebar/Sidebar.jsx | 80 ++++++++++++++------- src/pages/AttendancePage/AttendancePage.jsx | 7 +- 2 files changed, 59 insertions(+), 28 deletions(-) diff --git a/src/layouts/Profile/Sidebar/Sidebar.jsx b/src/layouts/Profile/Sidebar/Sidebar.jsx index f669f927..4e8080d6 100644 --- a/src/layouts/Profile/Sidebar/Sidebar.jsx +++ b/src/layouts/Profile/Sidebar/Sidebar.jsx @@ -12,8 +12,7 @@ import styles from "./styles/Sidebar.module.scss"; import defaultImg from "../../../assets/images/defaultImg.jpg"; import camera from "../../../assets/images/camera.svg"; import { EditImage } from "../../../features"; -import { Link } from "react-router-dom"; -import { NavLink } from "react-router-dom"; +import { Link, NavLink } from "react-router-dom"; const Sidebar = ({ activepage, handleChange }) => { const [designation, setDesignation] = useState(""); @@ -63,26 +62,57 @@ const Sidebar = ({ activepage, handleChange }) => { setimagePrv(url); }; - const renderBlogMenu = () => ( -
handleChange("Blogs")} - style={{ - background: activepage === "Blogs" ? "var(--primary)" : "transparent", - WebkitBackgroundClip: activepage === "Blogs" ? "text" : "initial", - backgroundClip: activepage === "Blogs" ? "text" : "initial", - color: activepage === "Blogs" ? "transparent" : "inherit", - }} - > - { + const isMobile = window.innerWidth <= 768; + + if (isMobile) { + return ( +
handleChange("Attendance")} + style={{ + background: + activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: + activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + }} + > + {" "} + Attendance +
+ ); + } + + return ( +
handleChange("Blogs")} style={{ - color: activepage === "Blogs" ? "#FF8A00" : "white", - marginRight: "10px", + background: activepage === "Blogs" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Blogs" ? "text" : "initial", + backgroundClip: activepage === "Blogs" ? "text" : "initial", + color: activepage === "Blogs" ? "transparent" : "inherit", }} - />{" "} - Blogs -
- ); + > + {" "} + Blogs +
+ ); + }; + const renderAdminMenu = () => ( <>
{ style={{ background: activepage === "Attendance" ? "var(--primary)" : "transparent", - WebkitBackgroundClip: activepage === "Attendance" ? "text" : "initial", + WebkitBackgroundClip: + activepage === "Attendance" ? "text" : "initial", backgroundClip: activepage === "Attendance" ? "text" : "initial", color: activepage === "Attendance" ? "transparent" : "inherit", marginLeft: "-6px", @@ -171,7 +202,6 @@ const Sidebar = ({ activepage, handleChange }) => { <>
- {/* */}
handleChange("Profile")} @@ -225,7 +255,9 @@ const Sidebar = ({ activepage, handleChange }) => {
{designation === "Admin" && renderAdminMenu()} - {(designation === "Admin" || authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && renderBlogMenu()} + {(designation === "Admin" || + authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && + renderBlogMenu()} {designation !== "Admin" && (
handleChange("events")} @@ -234,9 +266,7 @@ const Sidebar = ({ activepage, handleChange }) => { Event -
- )}
{ const handleDownloadAttendance = async (eventId) => { try { - const response = await api.get(`/api/form/download/${eventId}`, { + const response = await api.get(`/api/form/export-attendance/${eventId}?format=xlsx`, { headers: { Authorization: `Bearer ${authCtx.token}` }, responseType: "blob", }); - const blob = new Blob([response.data], { type: "text/csv" }); + const blob = new Blob([response.data], { type: "text/xlsx" }); const url = window.URL.createObjectURL(blob); const link = document.createElement("a"); link.href = url; - link.setAttribute("download", `attendance_${eventId}.csv`); + link.setAttribute("download", `attendance_${eventId}.xlsx`); document.body.appendChild(link); link.click(); link.remove(); @@ -263,6 +263,7 @@ const AttendancePage = () => { style={{ padding: "8px 16px", backgroundColor: "rgba(255, 138, 0, 0.9)" }} > + Attendance
); From 2dd50ee9de1f8e24cff5fe66c24495b7ef820eb3 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Fri, 15 Aug 2025 12:24:36 +0530 Subject: [PATCH 28/44] attandace access --- src/App.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/App.jsx b/src/App.jsx index 8f073d66..92910646 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -179,7 +179,7 @@ function App() { /> )} {authCtx.user.access === "USER" && - authCtx.user.email == "srex@fedkiit.com" && ( + authCtx.user.email == "attendance@fedkiit.com" && ( ]} From ea6a635d09f249004a90a15a9fb6efc95a99023c Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Fri, 15 Aug 2025 12:35:55 +0530 Subject: [PATCH 29/44] sidebar attendance access --- src/layouts/Profile/Sidebar/Sidebar.jsx | 44 ++++++++++++++----------- 1 file changed, 24 insertions(+), 20 deletions(-) diff --git a/src/layouts/Profile/Sidebar/Sidebar.jsx b/src/layouts/Profile/Sidebar/Sidebar.jsx index 4e8080d6..00e278b6 100644 --- a/src/layouts/Profile/Sidebar/Sidebar.jsx +++ b/src/layouts/Profile/Sidebar/Sidebar.jsx @@ -118,7 +118,8 @@ const Sidebar = ({ activepage, handleChange }) => {
handleChange("Events")} style={{ - background: activepage === "Events" ? "var(--primary)" : "transparent", + background: + activepage === "Events" ? "var(--primary)" : "transparent", WebkitBackgroundClip: activepage === "Events" ? "text" : "initial", backgroundClip: activepage === "Events" ? "text" : "initial", color: activepage === "Events" ? "transparent" : "inherit", @@ -174,27 +175,30 @@ const Sidebar = ({ activepage, handleChange }) => { Members
-
handleChange("Attendance")} - style={{ - background: - activepage === "Attendance" ? "var(--primary)" : "transparent", - WebkitBackgroundClip: - activepage === "Attendance" ? "text" : "initial", - backgroundClip: activepage === "Attendance" ? "text" : "initial", - color: activepage === "Attendance" ? "transparent" : "inherit", - marginLeft: "-6px", - }} - > - handleChange("Attendance")} style={{ - color: activepage === "Attendance" ? "#FF8A00" : "white", - marginRight: "10px", + background: + activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: + activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + marginLeft: "-6px", }} - />{" "} - Attendance -
+ > + {" "} + Attendance +
+ )} ); From 098a6c23578fae529d8d78c0d654b44198abc2e4 Mon Sep 17 00:00:00 2001 From: Ritam-Vaskar Date: Fri, 15 Aug 2025 12:56:13 +0530 Subject: [PATCH 30/44] sidebar fix --- src/layouts/Profile/Sidebar/Sidebar.jsx | 118 ++++++++++++++++-------- 1 file changed, 77 insertions(+), 41 deletions(-) diff --git a/src/layouts/Profile/Sidebar/Sidebar.jsx b/src/layouts/Profile/Sidebar/Sidebar.jsx index 00e278b6..00d14b3e 100644 --- a/src/layouts/Profile/Sidebar/Sidebar.jsx +++ b/src/layouts/Profile/Sidebar/Sidebar.jsx @@ -26,7 +26,11 @@ const Sidebar = ({ activepage, handleChange }) => { useEffect(() => { const access = authCtx.user.access; - if (access === "ADMIN") { + const email = authCtx.user.email; // Assuming email is available in authCtx.user + + if (email === "attendance@fedkiit.com") { + setDesignation("Attendance Only"); + } else if (access === "ADMIN") { setDesignation("Admin"); } else if (access === "ALUMNI") { setDesignation("Alumni"); @@ -35,7 +39,7 @@ const Sidebar = ({ activepage, handleChange }) => { } else { setDesignation("Member"); } - }, [authCtx.user.access]); + }, [authCtx.user.access, authCtx.user.email]); const handleLogout = () => { navigate("/"); @@ -62,6 +66,9 @@ const Sidebar = ({ activepage, handleChange }) => { setimagePrv(url); }; + // Check if user is attendance-only + const isAttendanceOnly = authCtx.user.email === "attendance@fedkiit.com"; + // Modified: Now shows Attendance instead of Blogs in mobile view const renderBlogMenu = () => { const isMobile = window.innerWidth <= 768; @@ -118,8 +125,7 @@ const Sidebar = ({ activepage, handleChange }) => {
handleChange("Events")} style={{ - background: - activepage === "Events" ? "var(--primary)" : "transparent", + background: activepage === "Events" ? "var(--primary)" : "transparent", WebkitBackgroundClip: activepage === "Events" ? "text" : "initial", backgroundClip: activepage === "Events" ? "text" : "initial", color: activepage === "Events" ? "transparent" : "inherit", @@ -175,33 +181,52 @@ const Sidebar = ({ activepage, handleChange }) => { Members
- {(designation === "Admin" || - authCtx.user.email === "attendance@fedkiit.com") && ( -
handleChange("Attendance")} +
handleChange("Attendance")} + style={{ + background: + activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: + activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + marginLeft: "-6px", + }} + > + - {" "} - Attendance -
- )} + />{" "} + Attendance +
); + // Render attendance-only menu + const renderAttendanceOnlyMenu = () => ( +
handleChange("Attendance")} + style={{ + background: activepage === "Attendance" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Attendance" ? "text" : "initial", + backgroundClip: activepage === "Attendance" ? "text" : "initial", + color: activepage === "Attendance" ? "transparent" : "inherit", + }} + > + {" "} + Attendance +
+ ); + return ( <>
@@ -227,7 +252,7 @@ const Sidebar = ({ activepage, handleChange }) => { setFile={setSelectedFile} /> )} - {authCtx.user.access !== "USER" && ( + {authCtx.user.access !== "USER" && !isAttendanceOnly && ( <>
{

{designation}

+
- {designation === "Admin" && renderAdminMenu()} - {(designation === "Admin" || - authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && - renderBlogMenu()} - {designation !== "Admin" && ( -
handleChange("events")} - style={{ color: activepage === "events" ? "#FF8A00" : "white" }} - > - - Event - -
+ {isAttendanceOnly ? ( + // Show only Attendance menu for attendance@fedkiit.com + renderAttendanceOnlyMenu() + ) : ( + // Original menu logic for other users + <> + {designation === "Admin" && renderAdminMenu()} + {(designation === "Admin" || + authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && + renderBlogMenu()} + {designation !== "Admin" && ( +
handleChange("events")} + style={{ color: activepage === "events" ? "#FF8A00" : "white" }} + > + + Event + +
+ )} + )} + + {/* Logout is always available for all users */}
{ ); }; -export default Sidebar; +export default Sidebar; \ No newline at end of file From a7d6cd63f12f45a15f8dd82d8dada3864fe04e84 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Fri, 15 Aug 2025 23:14:48 +0530 Subject: [PATCH 31/44] udpatetoastlatest --- src/pages/AttendancePage/AttendancePage.jsx | 67 ++++++++++++++------- 1 file changed, 46 insertions(+), 21 deletions(-) diff --git a/src/pages/AttendancePage/AttendancePage.jsx b/src/pages/AttendancePage/AttendancePage.jsx index e5df8584..6e66df03 100644 --- a/src/pages/AttendancePage/AttendancePage.jsx +++ b/src/pages/AttendancePage/AttendancePage.jsx @@ -22,6 +22,7 @@ const AttendancePage = () => { const [attendedUser, setAttendedUser] = useState(null); const [hasShownAlert, setHasShownAlert] = useState(false); const [isSuccess, setIsSuccess] = useState(false); + const [alertShown, setAlertShown] = useState(false); const authCtx = useContext(AuthContext); useEffect(() => { @@ -82,19 +83,24 @@ const AttendancePage = () => { setScanner(qrScanner); } catch (error) { console.error("Error initializing scanner:", error); - if (!hasShownAlert) { + if (!alertShown) { Alert({ type: "error", message: "Failed to initialize QR scanner", position: "top-right", }); - setHasShownAlert(true); + setAlertShown(true); } setShowScanner(false); } }; const onScanSuccess = async (decodedText) => { + // Prevent multiple scans if already processing or alert shown + if (isScanning || alertShown) { + return; + } + setIsScanning(true); console.log("QR Code scanned successfully:", decodedText); console.log("Selected Event ID:", selectedEventId); @@ -118,18 +124,28 @@ const AttendancePage = () => { // store user details setAttendedUser(response.data.user || response.data); setIsSuccess(true); + + // Stop scanner and clear it if (scanner) { - scanner.clear(); + try { + scanner.clear(); + } catch (error) { + console.error("Error clearing scanner:", error); + } } + setShowSuccessModal(true); setIsScanning(false); - // show success alert - Alert({ - type: "success", - message: "Attendance marked successfully!", - position: "top-right", - }); + // show success alert only if no alert has been shown + if (!alertShown) { + Alert({ + type: "success", + message: "Attendance marked successfully!", + position: "top-right", + }); + setAlertShown(true); + } return; // exit early } @@ -149,14 +165,23 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - // show error alert - if (!hasShownAlert) { + // show error alert only if no alert has been shown + if (!alertShown) { Alert({ type: "error", message: errorMessage, position: "top-right", }); - setHasShownAlert(true); + setAlertShown(true); + } + + // Stop scanner after error to prevent multiple scans + if (scanner) { + try { + scanner.clear(); + } catch (error) { + console.error("Error clearing scanner:", error); + } } } finally { setIsScanning(false); @@ -170,7 +195,7 @@ const AttendancePage = () => { const handleScanQR = (eventId) => { setSelectedEventId(eventId); setShowScanner(true); - setHasShownAlert(false); // reset alert state + setAlertShown(false); // reset alert state setIsSuccess(false); // reset success state }; @@ -180,7 +205,7 @@ const AttendancePage = () => { // auto open scanner for next scan setTimeout(() => { setShowScanner(true); - setHasShownAlert(false); // reset alert state + setAlertShown(false); // reset alert state setIsSuccess(false); // reset success state }, 100); }; @@ -189,15 +214,15 @@ const AttendancePage = () => { const handleDownloadAttendance = async (eventId) => { try { - const response = await api.get(`/api/form/export-attendance/${eventId}?format=xlsx`, { + const response = await api.get(`/api/form/download/${eventId}`, { headers: { Authorization: `Bearer ${authCtx.token}` }, responseType: "blob", }); - const blob = new Blob([response.data], { type: "text/xlsx" }); + const blob = new Blob([response.data], { type: "text/csv" }); const url = window.URL.createObjectURL(blob); const link = document.createElement("a"); link.href = url; - link.setAttribute("download", `attendance_${eventId}.xlsx`); + link.setAttribute("download", `attendance_${eventId}.csv`); document.body.appendChild(link); link.click(); link.remove(); @@ -219,14 +244,14 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - // show error alert - if (!isSuccess && !hasShownAlert) { + // show error alert only if no alert has been shown + if (!alertShown) { Alert({ type: "error", message: errorMessage, position: "top-right", }); - setHasShownAlert(true); + setAlertShown(true); } console.error("Download error:", error); } @@ -263,7 +288,6 @@ const AttendancePage = () => { style={{ padding: "8px 16px", backgroundColor: "rgba(255, 138, 0, 0.9)" }} > - Attendance
); @@ -322,6 +346,7 @@ const AttendancePage = () => { } setShowScanner(false); setScanner(null); + setAlertShown(false); // reset alert state when closing scanner }} > From d4c4df33a5f3d6f55cc461fbc9bc319f9606b566 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Wed, 20 Aug 2025 20:20:44 +0530 Subject: [PATCH 32/44] remove omega page --- src/App.jsx | 7 +- src/layouts/Navbar/Navbar.jsx | 4 +- src/pages/LiveEvents/Omega/Omega.jsx | 350 +++++++++--------- .../LiveEvents/Omega/styles/Omega.module.scss | 30 +- 4 files changed, 195 insertions(+), 196 deletions(-) diff --git a/src/App.jsx b/src/App.jsx index 8f073d66..dcb29b41 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -40,8 +40,8 @@ const Team = lazy(() => import("./pages/Team/Team")); const Alumni = lazy(() => import("./pages/Alumni/Alumni")); const Profile = lazy(() => import("./pages/Profile/Profile")); const Blog = lazy(() => import("./pages/Blog/Blog")); -const Omega = lazy(() => import("./pages/LiveEvents/Omega/Omega")); -// const omega = lazy(() => import("./pages/LiveEvents/omega/omega")); +// const Omega = lazy(() => import("./pages/LiveEvents/Omega/Omega")); + const Signup = lazy(() => import("./pages/Authentication/Signup/Signup")); const ForgotPassword = lazy(() => @@ -112,8 +112,7 @@ function App() { {/* } /> */} } /> } /> - } /> - {/* }/> */} + {/* } /> */} {/* Route After Login */} {authCtx.isLoggedIn && ( }> diff --git a/src/layouts/Navbar/Navbar.jsx b/src/layouts/Navbar/Navbar.jsx index b688a8cd..896b78bf 100644 --- a/src/layouts/Navbar/Navbar.jsx +++ b/src/layouts/Navbar/Navbar.jsx @@ -212,7 +212,7 @@ useEffect(() => { Event -
  • + {/*
  • { > Omega -
  • + */}
  • { - window.scrollTo(0, 0); - }, []); - - useEffect(() => { - const originalBackgroundColor = document.body.style.backgroundColor; - document.body.style.backgroundColor = "#000000"; +// import { useContext, useEffect, useState } from "react"; +// import { api } from "../../../services/index.jsx"; +// import AuthContext from "../../../context/AuthContext.jsx"; +// import { motion } from "framer-motion"; +// import { Element } from "react-scroll"; +// import { useInView } from "react-intersection-observer"; +// import styles from "./styles/Omega.module.scss"; +// import Hero from "../../../sections/LiveEvents/Omega/Hero/Hero.jsx"; +// import Accordion from "../../../components/LiveEvents/Accordian/Accordian.jsx"; +// import data from "../../../data/liveEvents/omega/Accordion.json"; +// import Sponsors from "../../../sections/LiveEvents/Omega/Sponsors/Sponsors.jsx"; +// import Event from "../../../sections/LiveEvents/Omega/Event/Event.jsx"; +// import FedShow from "../../../sections/LiveEvents/Omega/FedShow/FedShow.jsx"; +// import TeamImage from "../../../sections/LiveEvents/Omega/TeamImage/TeamImage.jsx"; +// import Attend from "../../../sections/LiveEvents/Omega/Attend/Attend.jsx"; +// import ChatBot from "../../../features/ChatBot/ChatBot.jsx"; + +// function Omega() { +// useEffect(() => { +// window.scrollTo(0, 0); +// }, []); + +// useEffect(() => { +// const originalBackgroundColor = document.body.style.backgroundColor; +// document.body.style.backgroundColor = "#000000"; - return () => { - document.body.style.backgroundColor = originalBackgroundColor; - }; - }, []); - - const authCtx = useContext(AuthContext); - const [eventName, setEventName] = useState(""); - const [ongoingEvents, setOngoingEvents] = useState([]); - const [isRegisteredInRelatedEvents, setIsRegisteredInRelatedEvents] = - useState(false); - - const { ref: teamImageRef, inView: teamImageInView } = useInView({ - threshold: 0.1, - triggerOnce: true, - }); - - useEffect(() => { - const fetchEvents = async () => { - try { - const response = await api.get("/api/form/getAllForms"); - if (response.status === 200) { - const fetchedEvents = response.data.events; - const sortedEvents = fetchedEvents.sort((a, b) => { - // Extract priority and event dates - const priorityA = parseInt(a.info.eventPriority, 10); - const priorityB = parseInt(b.info.eventPriority, 10); - const dateA = new Date(a.info.eventDate); - const dateB = new Date(b.info.eventDate); - const titleA = a.info.eventTitle || ""; - const titleB = b.info.eventTitle || ""; - - // compare by priority (lower priority first) - if (priorityA !== priorityB) { - return priorityA - priorityB; - } - - // If priorities are the same, compare by date (earliest date first) - if (dateA.getTime() !== dateB.getTime()) { - return dateA.getTime() - dateB.getTime(); - } - - // If both priority and date are the same, compare alphabetically by title - return titleA.localeCompare(titleB); - }); - - // Separate ongoing and past events - const ongoing = sortedEvents.filter( - (event) => !event.info.isEventPast - ); - - // Set state with the sorted events - setOngoingEvents(ongoing); - } else { - console.error("Error fetching events:", response.data.message); - } - } catch (error) { - console.error("Error fetching events:", error); - } - }; - - fetchEvents(); - }, []); - - useEffect(() => { - const eventWithNullRelated = ongoingEvents.find( - (event) => event.info.relatedEvent === "null" - ); - - // Store the event's name or title for display - const eventName = eventWithNullRelated - ? eventWithNullRelated.info.eventTitle - : ""; - setEventName(eventName); - }, [ongoingEvents]); - - useEffect(() => { - const registeredEventIds = authCtx.user.regForm || []; - "Registered Events", registeredEventIds; - - const relatedEventIds = ongoingEvents - .map((event) => event.info.relatedEvent) // Extract relatedEvent IDs - .filter((id) => id !== null && id !== undefined && id !== "null") // Filter out null, undefined, and 'null' - .filter((id, index, self) => self.indexOf(id) === index); // Remove duplicates - - // console.log("Related Event IDs", relatedEventIds); - - let isRegisteredInRelatedEvents = false; - if (registeredEventIds.length > 0 && relatedEventIds.length > 0) { - isRegisteredInRelatedEvents = relatedEventIds.some((relatedEventId) => - registeredEventIds.includes(relatedEventId) - ); - } - - if (isRegisteredInRelatedEvents) { - setIsRegisteredInRelatedEvents(true); - } - }, [ongoingEvents, authCtx.user.regForm]); - - return ( -
    -
    - - { +// document.body.style.backgroundColor = originalBackgroundColor; +// }; +// }, []); + +// const authCtx = useContext(AuthContext); +// const [eventName, setEventName] = useState(""); +// const [ongoingEvents, setOngoingEvents] = useState([]); +// const [isRegisteredInRelatedEvents, setIsRegisteredInRelatedEvents] = +// useState(false); + +// const { ref: teamImageRef, inView: teamImageInView } = useInView({ +// threshold: 0.1, +// triggerOnce: true, +// }); + +// useEffect(() => { +// const fetchEvents = async () => { +// try { +// const response = await api.get("/api/form/getAllForms"); +// if (response.status === 200) { +// const fetchedEvents = response.data.events; +// const sortedEvents = fetchedEvents.sort((a, b) => { +// // Extract priority and event dates +// const priorityA = parseInt(a.info.eventPriority, 10); +// const priorityB = parseInt(b.info.eventPriority, 10); +// const dateA = new Date(a.info.eventDate); +// const dateB = new Date(b.info.eventDate); +// const titleA = a.info.eventTitle || ""; +// const titleB = b.info.eventTitle || ""; + +// // compare by priority (lower priority first) +// if (priorityA !== priorityB) { +// return priorityA - priorityB; +// } + +// // If priorities are the same, compare by date (earliest date first) +// if (dateA.getTime() !== dateB.getTime()) { +// return dateA.getTime() - dateB.getTime(); +// } + +// // If both priority and date are the same, compare alphabetically by title +// return titleA.localeCompare(titleB); +// }); + +// // Separate ongoing and past events +// const ongoing = sortedEvents.filter( +// (event) => !event.info.isEventPast +// ); + +// // Set state with the sorted events +// setOngoingEvents(ongoing); +// } else { +// console.error("Error fetching events:", response.data.message); +// } +// } catch (error) { +// console.error("Error fetching events:", error); +// } +// }; + +// fetchEvents(); +// }, []); + +// useEffect(() => { +// const eventWithNullRelated = ongoingEvents.find( +// (event) => event.info.relatedEvent === "null" +// ); + +// // Store the event's name or title for display +// const eventName = eventWithNullRelated +// ? eventWithNullRelated.info.eventTitle +// : ""; +// setEventName(eventName); +// }, [ongoingEvents]); + +// useEffect(() => { +// const registeredEventIds = authCtx.user.regForm || []; +// "Registered Events", registeredEventIds; + +// const relatedEventIds = ongoingEvents +// .map((event) => event.info.relatedEvent) // Extract relatedEvent IDs +// .filter((id) => id !== null && id !== undefined && id !== "null") // Filter out null, undefined, and 'null' +// .filter((id, index, self) => self.indexOf(id) === index); // Remove duplicates + +// // console.log("Related Event IDs", relatedEventIds); + +// let isRegisteredInRelatedEvents = false; +// if (registeredEventIds.length > 0 && relatedEventIds.length > 0) { +// isRegisteredInRelatedEvents = relatedEventIds.some((relatedEventId) => +// registeredEventIds.includes(relatedEventId) +// ); +// } + +// if (isRegisteredInRelatedEvents) { +// setIsRegisteredInRelatedEvents(true); +// } +// }, [ongoingEvents, authCtx.user.regForm]); + +// return ( +//
    +//
    + +// - - -
    - - - - - - - +// +// +//
    +// +// +// + +// +// +// - - - -
    - -
    -
    - ); -} - -export default Omega; +// > +// +// +// +//
    +// +//
    +//
    +// ); +// } + +// export default Omega; diff --git a/src/pages/LiveEvents/Omega/styles/Omega.module.scss b/src/pages/LiveEvents/Omega/styles/Omega.module.scss index df8625d1..71a0fa66 100644 --- a/src/pages/LiveEvents/Omega/styles/Omega.module.scss +++ b/src/pages/LiveEvents/Omega/styles/Omega.module.scss @@ -2,25 +2,25 @@ -.imageContainer { - height: 100%; - background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); - background-size: cover; - background-position: center; - background-repeat: no-repeat; -} +// .imageContainer { +// height: 100%; +// background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); +// background-size: cover; +// background-position: center; +// background-repeat: no-repeat; +// } - @media (max-width: 480px){ +// @media (max-width: 480px){ -.imageContainer { - height: 100%; +// .imageContainer { +// height: 100%; - background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); +// background-image: url('https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/6894c43e74ee408d8b7f56db_Group%201171275099%20(1).png'); - background-position: 13% 20%; - background-repeat: no-repeat; -} +// background-position: 13% 20%; +// background-repeat: no-repeat; +// } - } \ No newline at end of file +// } \ No newline at end of file From 3e300df71abb2be49fab89d444c95d41fea5f838 Mon Sep 17 00:00:00 2001 From: FED-Tech <128247576+fed-tech@users.noreply.github.com> Date: Thu, 21 Aug 2025 10:00:24 +0530 Subject: [PATCH 33/44] Update Event.jsx --- src/pages/Event/Event.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pages/Event/Event.jsx b/src/pages/Event/Event.jsx index fdd7cb6e..6c1accbf 100644 --- a/src/pages/Event/Event.jsx +++ b/src/pages/Event/Event.jsx @@ -190,7 +190,7 @@ const Event = () => { return ( <> -

    Register Yourself for OMEGA 5.0 to Unlock All Three Events Under OMEGA

    + {isOpen && ( )} From 746f66a58e42d78dd1724ce7a3aedca6a54926b5 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 21 Aug 2025 12:12:09 +0530 Subject: [PATCH 34/44] Attendance Sidebar --- src/App.jsx | 15 +++++---------- src/layouts/Profile/Sidebar/Sidebar.jsx | 24 +++++++++++++++++++++++- 2 files changed, 28 insertions(+), 11 deletions(-) diff --git a/src/App.jsx b/src/App.jsx index 4684d98b..ff062477 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -123,11 +123,11 @@ function App() { {authCtx.user.access === "ADMIN" ? ( } /> ) : ( - <> - } /> - } /> - + } /> )} + + } /> + } /> {authCtx.user.access === "ADMIN" && ( @@ -140,11 +140,6 @@ function App() { authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && ( } /> )} - {/* Certificates Route */} - - {authCtx.user.access === "ADMIN" && ( - } /> - )} {authCtx.user.access === "ADMIN" && ( ]} /> )} - } /> + } /> )} {
  • ); + const renderCertificateMenu = () => ( +
    handleChange("Certificates")} + style={{ + background: activepage === "Certificates" ? "var(--primary)" : "transparent", + WebkitBackgroundClip: activepage === "Certificates" ? "text" : "initial", + backgroundClip: activepage === "Certificates" ? "text" : "initial", + color: activepage === "Certificates" ? "transparent" : "inherit", + }} + > + {" "} + Certificates +
    + ); + return ( <>
    @@ -304,6 +325,7 @@ const Sidebar = ({ activepage, handleChange }) => {
    )} + {renderCertificateMenu()} )} From bfe103d4043b28ba83730f403e40d444b85a2272 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 21 Aug 2025 12:14:51 +0530 Subject: [PATCH 35/44] attendance fix --- src/App.jsx | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/src/App.jsx b/src/App.jsx index ff062477..4684d98b 100644 --- a/src/App.jsx +++ b/src/App.jsx @@ -123,11 +123,11 @@ function App() { {authCtx.user.access === "ADMIN" ? ( } /> ) : ( - } /> + <> + } /> + } /> + )} - - } /> - } /> {authCtx.user.access === "ADMIN" && ( @@ -140,6 +140,11 @@ function App() { authCtx.user.access === "SENIOR_EXECUTIVE_CREATIVE") && ( } /> )} + {/* Certificates Route */} + + {authCtx.user.access === "ADMIN" && ( + } /> + )} {authCtx.user.access === "ADMIN" && ( ]} /> )} - } /> + } /> )} Date: Thu, 21 Aug 2025 12:16:55 +0530 Subject: [PATCH 36/44] attendancefix --- src/pages/AttendancePage/AttendancePage.jsx | 69 +++++++-------------- 1 file changed, 22 insertions(+), 47 deletions(-) diff --git a/src/pages/AttendancePage/AttendancePage.jsx b/src/pages/AttendancePage/AttendancePage.jsx index 6e66df03..06486c43 100644 --- a/src/pages/AttendancePage/AttendancePage.jsx +++ b/src/pages/AttendancePage/AttendancePage.jsx @@ -22,7 +22,6 @@ const AttendancePage = () => { const [attendedUser, setAttendedUser] = useState(null); const [hasShownAlert, setHasShownAlert] = useState(false); const [isSuccess, setIsSuccess] = useState(false); - const [alertShown, setAlertShown] = useState(false); const authCtx = useContext(AuthContext); useEffect(() => { @@ -83,24 +82,19 @@ const AttendancePage = () => { setScanner(qrScanner); } catch (error) { console.error("Error initializing scanner:", error); - if (!alertShown) { + if (!hasShownAlert) { Alert({ type: "error", message: "Failed to initialize QR scanner", position: "top-right", }); - setAlertShown(true); + setHasShownAlert(true); } setShowScanner(false); } }; const onScanSuccess = async (decodedText) => { - // Prevent multiple scans if already processing or alert shown - if (isScanning || alertShown) { - return; - } - setIsScanning(true); console.log("QR Code scanned successfully:", decodedText); console.log("Selected Event ID:", selectedEventId); @@ -124,28 +118,18 @@ const AttendancePage = () => { // store user details setAttendedUser(response.data.user || response.data); setIsSuccess(true); - - // Stop scanner and clear it if (scanner) { - try { - scanner.clear(); - } catch (error) { - console.error("Error clearing scanner:", error); - } + scanner.clear(); } - setShowSuccessModal(true); setIsScanning(false); - // show success alert only if no alert has been shown - if (!alertShown) { - Alert({ - type: "success", - message: "Attendance marked successfully!", - position: "top-right", - }); - setAlertShown(true); - } + // show success alert + Alert({ + type: "success", + message: "Attendance marked successfully!", + position: "top-right", + }); return; // exit early } @@ -165,23 +149,14 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - // show error alert only if no alert has been shown - if (!alertShown) { + // show error alert + if (!hasShownAlert) { Alert({ type: "error", message: errorMessage, position: "top-right", }); - setAlertShown(true); - } - - // Stop scanner after error to prevent multiple scans - if (scanner) { - try { - scanner.clear(); - } catch (error) { - console.error("Error clearing scanner:", error); - } + setHasShownAlert(true); } } finally { setIsScanning(false); @@ -195,7 +170,7 @@ const AttendancePage = () => { const handleScanQR = (eventId) => { setSelectedEventId(eventId); setShowScanner(true); - setAlertShown(false); // reset alert state + setHasShownAlert(false); // reset alert state setIsSuccess(false); // reset success state }; @@ -205,7 +180,7 @@ const AttendancePage = () => { // auto open scanner for next scan setTimeout(() => { setShowScanner(true); - setAlertShown(false); // reset alert state + setHasShownAlert(false); // reset alert state setIsSuccess(false); // reset success state }, 100); }; @@ -214,15 +189,15 @@ const AttendancePage = () => { const handleDownloadAttendance = async (eventId) => { try { - const response = await api.get(`/api/form/download/${eventId}`, { + const response = await api.get(`/api/form/export-attendance/${eventId}?format=xlsx`, { headers: { Authorization: `Bearer ${authCtx.token}` }, responseType: "blob", }); - const blob = new Blob([response.data], { type: "text/csv" }); + const blob = new Blob([response.data], { type: "text/xlsx" }); const url = window.URL.createObjectURL(blob); const link = document.createElement("a"); link.href = url; - link.setAttribute("download", `attendance_${eventId}.csv`); + link.setAttribute("download", `attendance_${eventId}.xlsx`); document.body.appendChild(link); link.click(); link.remove(); @@ -244,14 +219,14 @@ const AttendancePage = () => { errorMessage = error.response.data.message; } - // show error alert only if no alert has been shown - if (!alertShown) { + // show error alert + if (!isSuccess && !hasShownAlert) { Alert({ type: "error", message: errorMessage, position: "top-right", }); - setAlertShown(true); + setHasShownAlert(true); } console.error("Download error:", error); } @@ -288,6 +263,7 @@ const AttendancePage = () => { style={{ padding: "8px 16px", backgroundColor: "rgba(255, 138, 0, 0.9)" }} > + Attendance
    ); @@ -346,7 +322,6 @@ const AttendancePage = () => { } setShowScanner(false); setScanner(null); - setAlertShown(false); // reset alert state when closing scanner }} > @@ -451,4 +426,4 @@ const AttendancePage = () => { ); }; -export default AttendancePage; +export default AttendancePage; \ No newline at end of file From 6e3a570df4b518a93eea8f076444be8db2fd0598 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Wed, 27 Aug 2025 00:18:06 +0530 Subject: [PATCH 37/44] Certificate issue and hero image --- src/data/Carousel.json | 11 ++++++----- .../Admin/Form/CertificatesForm/CertificatesForm.jsx | 6 +++++- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/src/data/Carousel.json b/src/data/Carousel.json index a6da4b36..91a93109 100644 --- a/src/data/Carousel.json +++ b/src/data/Carousel.json @@ -1,17 +1,18 @@ [ { - "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723491234/WebImages/pdamxjoydih8u126tcin.jpg" + "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/68ad5c933de15739388e7d58_IMG-20250821-WA0042.jpg" + }, { - "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723474147/WebImages/gkj4lcjlclqtal2ywsgy.jpg" + "image": "https://cdn.prod.website-files.com/6891df87cfba687a7fd80202/68ad5c923a6883f39fa0f16f_IMG-20250821-WA0048.jpg" }, { - "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723474144/WebImages/g702ehalm27csrqq84pa.jpg" + "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723491234/WebImages/pdamxjoydih8u126tcin.jpg" }, { - "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723474145/WebImages/q9hc1sidzihgh43wtrw5.jpg" + "image": "https://res.cloudinary.com/ddx6avza4/image/upload/v1756233848/filename_xim4ah.jpg" }, { - "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723490913/WebImages/ijleazx6xkrsb8nsnu54.jpg" + "image": "https://res.cloudinary.com/ddx6avza4/image/upload/v1756233685/IMG_4985_hq0qfv.jpg" } ] diff --git a/src/sections/Profile/Admin/Form/CertificatesForm/CertificatesForm.jsx b/src/sections/Profile/Admin/Form/CertificatesForm/CertificatesForm.jsx index be18fa09..3f36f08f 100644 --- a/src/sections/Profile/Admin/Form/CertificatesForm/CertificatesForm.jsx +++ b/src/sections/Profile/Admin/Form/CertificatesForm/CertificatesForm.jsx @@ -203,7 +203,11 @@ const CertificatesForm = () => { const response = await api.post( "/api/certificate/addCertificateTemplate", - formData + + formData, + { + headers: { Authorization: `Bearer ${authCtx.token}` }, + } ); if (response.status !== 200) { From eb7e4a56b79e7b2c6a5383a3ca0cc98bb4bbd379 Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Thu, 28 Aug 2025 02:34:53 +0530 Subject: [PATCH 38/44] certificate css --- .../styles/VerifyCertificate.module.scss | 38 ++++++++++++++++--- .../CertificatesView/CertificatesView.jsx | 1 + .../styles/CertificatesView.module.scss | 2 +- 3 files changed, 34 insertions(+), 7 deletions(-) diff --git a/src/sections/Profile/Admin/View/VerifyCertificate/styles/VerifyCertificate.module.scss b/src/sections/Profile/Admin/View/VerifyCertificate/styles/VerifyCertificate.module.scss index 7354ccc2..4d730096 100644 --- a/src/sections/Profile/Admin/View/VerifyCertificate/styles/VerifyCertificate.module.scss +++ b/src/sections/Profile/Admin/View/VerifyCertificate/styles/VerifyCertificate.module.scss @@ -50,7 +50,7 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); align-items: center; img { - max-width: 100%; + max-width: 95%; border-radius: $border-radius; box-shadow: $shadow; border: 2px solid $accent-color; @@ -59,6 +59,13 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); &:hover { transform: scale(1.02); } + @media(max-width: 390px) { + padding: 0.1rem; + width: 85%; + + + } + } } @@ -69,17 +76,31 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); padding: 2rem; border-radius: $border-radius; box-shadow: $shadow; - display: flex; + display:inline-flexbox; + width:100%; flex-direction: column; justify-content: space-between; + + @media(max-width: 480px) { + padding: 1.0rem; + margin-top: 2rem; + + } + @media(max-width: 390px) { + padding: 0rem; + width:95%; + margin-left: 9px; + margin-top: 2rem; + + } } .detailsTable { width: 100%; - // margin-bottom: 2rem; + margin-bottom: 2rem; th, td { - padding: 0.75rem; + padding: 0.95rem; text-align: left; } @@ -108,6 +129,10 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); font-weight: 600; font-size: 1rem; + @media(max-width: 390px) { + padding: 0.1rem; + margin-left: 2px; + } svg { font-size: 1.25rem; } @@ -116,7 +141,7 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); .downloadBtn { background-color: $accent-color; color: white; - padding: 0.7rem 1.3rem; + padding: 0.5rem 1.2rem; font-size: 1rem; font-weight: 600; border: none; @@ -132,9 +157,10 @@ $shadow: 0 8px 24px rgba(0, 0, 0, 0.2); @media (max-width: 480px) { flex-direction: column; - align-items: flex-start; + align-items:center; gap: 1rem; } + } .loadingContainer, .errorContainer { diff --git a/src/sections/Profile/General/CertificatesView/CertificatesView.jsx b/src/sections/Profile/General/CertificatesView/CertificatesView.jsx index 6ff3c47c..27c706c4 100644 --- a/src/sections/Profile/General/CertificatesView/CertificatesView.jsx +++ b/src/sections/Profile/General/CertificatesView/CertificatesView.jsx @@ -16,6 +16,7 @@ const Events = () => { const analyticsPath = "/profile/events/Analytics"; const createCertificatesPath = "/profile/events/createCertificates"; const viewCertificatesPath = "/profile/events/viewCertificates"; + const analyticsAccessRoles = [ "PRESIDENT", diff --git a/src/sections/Profile/General/CertificatesView/styles/CertificatesView.module.scss b/src/sections/Profile/General/CertificatesView/styles/CertificatesView.module.scss index a6e25039..ee19232a 100644 --- a/src/sections/Profile/General/CertificatesView/styles/CertificatesView.module.scss +++ b/src/sections/Profile/General/CertificatesView/styles/CertificatesView.module.scss @@ -1,5 +1,5 @@ .participatedEvents { - color: #ffffff; + color: #e2e2e2; font-family: rubik; font-weight: 300; display: flex; From 1b3605ae1f69c363426b191f4c9aed3580ca411d Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Thu, 28 Aug 2025 02:45:41 +0530 Subject: [PATCH 39/44] certificate css --- .../Admin/View/VerifyCertificate/VerifyCertificate.jsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/sections/Profile/Admin/View/VerifyCertificate/VerifyCertificate.jsx b/src/sections/Profile/Admin/View/VerifyCertificate/VerifyCertificate.jsx index 8f054c7f..4107f771 100644 --- a/src/sections/Profile/Admin/View/VerifyCertificate/VerifyCertificate.jsx +++ b/src/sections/Profile/Admin/View/VerifyCertificate/VerifyCertificate.jsx @@ -129,7 +129,7 @@ const VerifyCertificate = () => { Email: {certificateData.email} - + {/* Event Date: {new Date(certificateData.date).toLocaleDateString("en-US", { @@ -138,7 +138,7 @@ const VerifyCertificate = () => { day: "numeric", })} - + */} From b2d23ac3f6fac8841ecc0723c777a8eca4d7a251 Mon Sep 17 00:00:00 2001 From: Hardik Gupta Date: Thu, 28 Aug 2025 14:07:15 +0530 Subject: [PATCH 40/44] certificate tab --- src/layouts/Profile/Sidebar/Sidebar.jsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/layouts/Profile/Sidebar/Sidebar.jsx b/src/layouts/Profile/Sidebar/Sidebar.jsx index 7b177f94..9e896715 100644 --- a/src/layouts/Profile/Sidebar/Sidebar.jsx +++ b/src/layouts/Profile/Sidebar/Sidebar.jsx @@ -325,7 +325,7 @@ const Sidebar = ({ activepage, handleChange }) => {
    )} - {renderCertificateMenu()} + {authCtx.user.access !== "USER" && renderCertificateMenu()} )} From b73bc9c3272a8a4c4bd61c106365d9e4a7ca7a0d Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Fri, 29 Aug 2025 19:46:28 +0530 Subject: [PATCH 41/44] sponsers add --- src/data/Sponser.json | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/src/data/Sponser.json b/src/data/Sponser.json index 0afce6fd..9de63e67 100644 --- a/src/data/Sponser.json +++ b/src/data/Sponser.json @@ -1,4 +1,25 @@ [ + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/68b1b1e566f93e724d817493_eef89a14894ab60c2de4591433117cb8_347615ad16304501c571bf1208b83615bc2eb3b7.jpg" + }, + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/68b1b277c3dff77928f42d07_42506cd40d9f845726c5b38fa6135dab_1737828471512.jpeg" + }, + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898aa1700b8583e9b0cea09_9a90e8c4f7933718410931fff16e1d67d0b1a728%20(1)-modified.png" + }, + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/68b1b4a473e0c91daf83aee0_SR%20burger%20point%202.png" + }, + + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/6898a9a97a1a9e6121d28cfb_988e7f74979dc9924fdc07590a81526d0d19ddc4.png" + }, + + { + "image": "https://cdn.prod.website-files.com/6898a84f39288fa31fb19eb3/68b1b4713f09aa52852051a1_Adda%20Cafe%20-%20Logo%202.png" + }, + { "image": "https://res.cloudinary.com/dm6jd6bhk/image/upload/v1723474142/WebImages/idm0kbdoybdmiklcgvkv.png" }, From e6f8733047352a863e5a18e113ef0466c63f4dfe Mon Sep 17 00:00:00 2001 From: Sanniiii07 <241551073@kiit.ac.in> Date: Sun, 7 Dec 2025 00:24:32 +0530 Subject: [PATCH 42/44] FIC section added --- package-lock.json | 21 +++- src/pages/Team/Team.jsx | 34 +++++++ src/pages/Team/styles/Team.module.scss | 133 +++++++++++++++++++++++++ 3 files changed, 186 insertions(+), 2 deletions(-) diff --git a/package-lock.json b/package-lock.json index c5098011..7e2b0e72 100644 --- a/package-lock.json +++ b/package-lock.json @@ -119,6 +119,7 @@ "version": "7.24.6", "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.24.6.tgz", "integrity": "sha512-qAHSfAdVyFmIvl0VHELib8xar7ONuSHrE2hLnsaWkYNTI68dmi1x8GYDhJjMI/e7XWal9QBlZkwbOnkcw7Z8gQ==", + "peer": true, "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.24.6", @@ -675,6 +676,7 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.2.tgz", "integrity": "sha512-uNsoYd37AFmaCdXlg6EYD1KaPOaRWRByMCYzbKUX4+hhMfrxdVSelShywL4JVaAeM/eHUOSprYBQls+/neX3pw==", + "peer": true, "dependencies": { "@emotion/memoize": "^0.8.1" } @@ -688,6 +690,7 @@ "version": "11.11.4", "resolved": "https://registry.npmjs.org/@emotion/react/-/react-11.11.4.tgz", "integrity": "sha512-t8AjMlF0gHpvvxk5mAtCqR4vmxiGHCeJBaQO6gncUSdklELOgtwjerNY2yuJNfwnc6vi16U/+uMF+afIawJ9iw==", + "peer": true, "dependencies": { "@babel/runtime": "^7.18.3", "@emotion/babel-plugin": "^11.11.0", @@ -728,6 +731,7 @@ "version": "11.11.5", "resolved": "https://registry.npmjs.org/@emotion/styled/-/styled-11.11.5.tgz", "integrity": "sha512-/ZjjnaNKvuMPxcIiUkf/9SHoG4Q196DRl1w82hQ3WCsjo1IUR8uaGWrC6a87CrYAW0Kb/pK7hk8BnLgLRi9KoQ==", + "peer": true, "dependencies": { "@babel/runtime": "^7.18.3", "@emotion/babel-plugin": "^11.11.0", @@ -1270,6 +1274,7 @@ "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-svg-core/-/fontawesome-svg-core-6.5.2.tgz", "integrity": "sha512-5CdaCBGl8Rh9ohNdxeeTMxIj8oc3KNBgIeLMvJosBMdslK/UnEB8rzyDRrbKdL1kDweqBPo4GT9wvnakHWucZw==", "hasInstallScript": true, + "peer": true, "dependencies": { "@fortawesome/fontawesome-common-types": "6.5.2" }, @@ -2113,6 +2118,7 @@ "version": "5.15.20", "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.15.20.tgz", "integrity": "sha512-tVq3l4qoXx/NxUgIx/x3lZiPn/5xDbdTE8VrLczNpfblLYZzlrbxA7kb9mI8NoBF6+w9WE9IrxWnKK5KlPI2bg==", + "peer": true, "dependencies": { "@babel/runtime": "^7.23.9", "@mui/base": "5.0.0-beta.40", @@ -3138,6 +3144,7 @@ "version": "18.3.3", "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz", "integrity": "sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw==", + "peer": true, "dependencies": { "@types/prop-types": "*", "csstype": "^3.0.2" @@ -3312,6 +3319,7 @@ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz", "integrity": "sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==", "dev": true, + "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -3914,7 +3922,8 @@ "node_modules/blurhash": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/blurhash/-/blurhash-2.0.5.tgz", - "integrity": "sha512-cRygWd7kGBQO3VEhPiTgq4Wc43ctsM+o46urrmPOiuAe+07fzlSB9OJVdpgDL0jPqXUVQ9ht7aq7kxOeJHRK+w==" + "integrity": "sha512-cRygWd7kGBQO3VEhPiTgq4Wc43ctsM+o46urrmPOiuAe+07fzlSB9OJVdpgDL0jPqXUVQ9ht7aq7kxOeJHRK+w==", + "peer": true }, "node_modules/boxen": { "version": "7.1.1", @@ -4055,6 +4064,7 @@ "url": "https://github.com/sponsors/ai" } ], + "peer": true, "dependencies": { "caniuse-lite": "^1.0.30001587", "electron-to-chromium": "^1.4.668", @@ -4704,7 +4714,8 @@ "node_modules/csstype": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", - "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==" + "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", + "peer": true }, "node_modules/data-view-buffer": { "version": "1.0.1", @@ -5300,6 +5311,7 @@ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.0.tgz", "integrity": "sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==", "dev": true, + "peer": true, "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.6.1", @@ -10958,6 +10970,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", + "peer": true, "dependencies": { "loose-envify": "^1.1.0" }, @@ -11059,6 +11072,7 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", + "peer": true, "dependencies": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" @@ -11279,6 +11293,7 @@ "version": "6.23.1", "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.23.1.tgz", "integrity": "sha512-utP+K+aSTtEdbWpC+4gxhdlPFwuEfDKq8ZrPFU65bbRJY+l706qjR7yaidBpo3MSeA/fzwbXWbKBI6ftOnP3OQ==", + "peer": true, "dependencies": { "@remix-run/router": "1.16.1", "react-router": "6.23.1" @@ -11913,6 +11928,7 @@ "version": "1.77.2", "resolved": "https://registry.npmjs.org/sass/-/sass-1.77.2.tgz", "integrity": "sha512-eb4GZt1C3avsX3heBNlrc7I09nyT00IUuo4eFhAbeXWU2fvA7oXI53SxODVAA+zgZCk9aunAZgO+losjR3fAwA==", + "peer": true, "dependencies": { "chokidar": ">=3.0.0 <4.0.0", "immutable": "^4.0.0", @@ -13027,6 +13043,7 @@ "integrity": "sha512-qO3aKv3HoQC8QKiNSTuUM1l9o/XX3+c+VTgLHbJWHZGeTPVAg2XwazI9UWzoxjIJCGCV2zU60uqMzjeLZuULqA==", "dev": true, "license": "MIT", + "peer": true, "dependencies": { "esbuild": "^0.21.3", "postcss": "^8.4.43", diff --git a/src/pages/Team/Team.jsx b/src/pages/Team/Team.jsx index ce4e195c..c8eb0ff7 100644 --- a/src/pages/Team/Team.jsx +++ b/src/pages/Team/Team.jsx @@ -275,6 +275,40 @@ const Team = () => { Creative group, the Technical group, and the Operations group.

    +
    + +
    +
    + picture of FIC +
    +
    +

    DR. VISHAL PRADHAN

    +

    FACULTY IN CHARGE

    + + {/*
    +

    + Dr. Vishal Pradhan is an exceptional academician and researcher at KIIT, + known for his clarity of thought, deep subject expertise, and commitment + to student success. His ability to connect advanced concepts with real-world + applications makes him a truly inspiring educator. +

    +
    */} + +
    +

    + "As FIC of FED, my vision is to ignite curiosity, nurture confidence, + and inspire students to rise beyond limits—so they walk into KIIT as + learners and grow into innovators who shape the world." --- Dr. Vishal Pradhan +

    +
    + +
    +
    +
    +
    {/*
    */} diff --git a/src/pages/Team/styles/Team.module.scss b/src/pages/Team/styles/Team.module.scss index e20c3e79..2989482d 100644 --- a/src/pages/Team/styles/Team.module.scss +++ b/src/pages/Team/styles/Team.module.scss @@ -145,6 +145,139 @@ strong { left: 0; } +//* Outer dark box */ +.FICwrapper { + background: #0d0d0d; /* same as TEAM page background */ + padding: 50px; + border-radius: 20px; + max-width: 1150px; + min-height: 220px; + margin: 30px auto; + box-shadow: 0 0 40px rgba(0, 0, 0, 0.4); + +} + +/* Grid layout */ +.FICsection { + display: grid; + grid-template-columns: 300px 1fr; + gap: 50px; + align-items: center; +} + +/* Left Image */ + .image img { + display: flex; + justify-content: center; /* centers horizontally */ + align-items: center; + width: 180px; + height: 180px; + border-radius: 0%; + object-fit: cover; + box-shadow: 0 10px 40px rgba(255, 138, 0, 0.2); + border: 3px solid rgba(255, 138, 0, 0.4); + transition: transform 0.3s ease, box-shadow 0.3s ease; +} + +.FICsection .image img:hover { + transform: scale(1.05); + box-shadow: 0 15px 60px rgba(255, 138, 0, 0.4); +} + +/* Text Block */ +.textBlock { + text-align: left; /* ensures all text aligns left */ +} + +/* Name */ +.name { + font-size: 32px; + font-weight: 800; + color: #FF8A00; + margin: 0; +} + +/* Role title */ +.role { + font-size: 14px; + font-weight: 600; + letter-spacing: 2px; + color: #FF8A00; + margin-top: 8px; + text-transform: uppercase; +} + +/* Intro & Vision */ +.intro, +.vision { + margin-top: 25px; + font-style: italic +} + +.intro p, +.vision p { + font-size: 16px; + line-height: 1.8; + color: #e0e0e0; + margin: 0; +} + +/* Responsive */ +@media (max-width: 768px) { + .FICsection { + grid-template-columns: 1fr; + text-align: left; + } + + .FICsection .image { + margin-bottom: 20px; + } + + .FICsection .image img { + width: 220px; + height: 220px; + } + + .name { + font-size: 26px; + } +} + +@media (max-width: 480px) { + .FICwrapper { + max-width: 350px; + } + + .FICsection { + grid-template-columns: 1fr; + } + + .FICsection .image { + margin-bottom: 20px; + margin:0 auto; + } + + .FICsection .image img { + width: 150px; + height: 150px; + text-align: center; + } + + .vision { + font-size: 18px; + text-align: center; + } + + .name { + font-size: 22px; + text-align: center; + } + + .role{ + text-align: center; + align-items: center; + } +} /* Responsive styles */ From 72753c46ee17966a6fbcdfe52b0633a3b296d46d Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Fri, 12 Dec 2025 23:15:58 +0530 Subject: [PATCH 43/44] team page update --- package-lock.json | 21 +--- src/pages/Team/Team.jsx | 248 ++++++++++++++++------------------------ 2 files changed, 103 insertions(+), 166 deletions(-) diff --git a/package-lock.json b/package-lock.json index 7e2b0e72..c5098011 100644 --- a/package-lock.json +++ b/package-lock.json @@ -119,7 +119,6 @@ "version": "7.24.6", "resolved": "https://registry.npmjs.org/@babel/core/-/core-7.24.6.tgz", "integrity": "sha512-qAHSfAdVyFmIvl0VHELib8xar7ONuSHrE2hLnsaWkYNTI68dmi1x8GYDhJjMI/e7XWal9QBlZkwbOnkcw7Z8gQ==", - "peer": true, "dependencies": { "@ampproject/remapping": "^2.2.0", "@babel/code-frame": "^7.24.6", @@ -676,7 +675,6 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/@emotion/is-prop-valid/-/is-prop-valid-1.2.2.tgz", "integrity": "sha512-uNsoYd37AFmaCdXlg6EYD1KaPOaRWRByMCYzbKUX4+hhMfrxdVSelShywL4JVaAeM/eHUOSprYBQls+/neX3pw==", - "peer": true, "dependencies": { "@emotion/memoize": "^0.8.1" } @@ -690,7 +688,6 @@ "version": "11.11.4", "resolved": "https://registry.npmjs.org/@emotion/react/-/react-11.11.4.tgz", "integrity": "sha512-t8AjMlF0gHpvvxk5mAtCqR4vmxiGHCeJBaQO6gncUSdklELOgtwjerNY2yuJNfwnc6vi16U/+uMF+afIawJ9iw==", - "peer": true, "dependencies": { "@babel/runtime": "^7.18.3", "@emotion/babel-plugin": "^11.11.0", @@ -731,7 +728,6 @@ "version": "11.11.5", "resolved": "https://registry.npmjs.org/@emotion/styled/-/styled-11.11.5.tgz", "integrity": "sha512-/ZjjnaNKvuMPxcIiUkf/9SHoG4Q196DRl1w82hQ3WCsjo1IUR8uaGWrC6a87CrYAW0Kb/pK7hk8BnLgLRi9KoQ==", - "peer": true, "dependencies": { "@babel/runtime": "^7.18.3", "@emotion/babel-plugin": "^11.11.0", @@ -1274,7 +1270,6 @@ "resolved": "https://registry.npmjs.org/@fortawesome/fontawesome-svg-core/-/fontawesome-svg-core-6.5.2.tgz", "integrity": "sha512-5CdaCBGl8Rh9ohNdxeeTMxIj8oc3KNBgIeLMvJosBMdslK/UnEB8rzyDRrbKdL1kDweqBPo4GT9wvnakHWucZw==", "hasInstallScript": true, - "peer": true, "dependencies": { "@fortawesome/fontawesome-common-types": "6.5.2" }, @@ -2118,7 +2113,6 @@ "version": "5.15.20", "resolved": "https://registry.npmjs.org/@mui/material/-/material-5.15.20.tgz", "integrity": "sha512-tVq3l4qoXx/NxUgIx/x3lZiPn/5xDbdTE8VrLczNpfblLYZzlrbxA7kb9mI8NoBF6+w9WE9IrxWnKK5KlPI2bg==", - "peer": true, "dependencies": { "@babel/runtime": "^7.23.9", "@mui/base": "5.0.0-beta.40", @@ -3144,7 +3138,6 @@ "version": "18.3.3", "resolved": "https://registry.npmjs.org/@types/react/-/react-18.3.3.tgz", "integrity": "sha512-hti/R0pS0q1/xx+TsI73XIqk26eBsISZ2R0wUijXIngRK9R/e7Xw/cXVxQK7R5JjW+SV4zGcn5hXjudkN/pLIw==", - "peer": true, "dependencies": { "@types/prop-types": "*", "csstype": "^3.0.2" @@ -3319,7 +3312,6 @@ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz", "integrity": "sha512-Y9rRfJG5jcKOE0CLisYbojUjIrIEE7AGMzA/Sm4BslANhbS+cDMpgBdcPT91oJ7OuJ9hYJBx59RjbhxVnrF8Xg==", "dev": true, - "peer": true, "bin": { "acorn": "bin/acorn" }, @@ -3922,8 +3914,7 @@ "node_modules/blurhash": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/blurhash/-/blurhash-2.0.5.tgz", - "integrity": "sha512-cRygWd7kGBQO3VEhPiTgq4Wc43ctsM+o46urrmPOiuAe+07fzlSB9OJVdpgDL0jPqXUVQ9ht7aq7kxOeJHRK+w==", - "peer": true + "integrity": "sha512-cRygWd7kGBQO3VEhPiTgq4Wc43ctsM+o46urrmPOiuAe+07fzlSB9OJVdpgDL0jPqXUVQ9ht7aq7kxOeJHRK+w==" }, "node_modules/boxen": { "version": "7.1.1", @@ -4064,7 +4055,6 @@ "url": "https://github.com/sponsors/ai" } ], - "peer": true, "dependencies": { "caniuse-lite": "^1.0.30001587", "electron-to-chromium": "^1.4.668", @@ -4714,8 +4704,7 @@ "node_modules/csstype": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/csstype/-/csstype-3.1.3.tgz", - "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==", - "peer": true + "integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw==" }, "node_modules/data-view-buffer": { "version": "1.0.1", @@ -5311,7 +5300,6 @@ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.57.0.tgz", "integrity": "sha512-dZ6+mexnaTIbSBZWgou51U6OmzIhYM2VcNdtiTtI7qPNZm35Akpr0f6vtw3w1Kmn5PYo+tZVfh13WrhpS6oLqQ==", "dev": true, - "peer": true, "dependencies": { "@eslint-community/eslint-utils": "^4.2.0", "@eslint-community/regexpp": "^4.6.1", @@ -10970,7 +10958,6 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react/-/react-18.3.1.tgz", "integrity": "sha512-wS+hAgJShR0KhEvPJArfuPVN1+Hz1t0Y6n5jLrGQbkb4urgPE/0Rve+1kMB1v/oWgHgm4WIcV+i7F2pTVj+2iQ==", - "peer": true, "dependencies": { "loose-envify": "^1.1.0" }, @@ -11072,7 +11059,6 @@ "version": "18.3.1", "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.3.1.tgz", "integrity": "sha512-5m4nQKp+rZRb09LNH59GM4BxTh9251/ylbKIbpe7TpGxfJ+9kv6BLkLBXIjjspbgbnIBNqlI23tRnTWT0snUIw==", - "peer": true, "dependencies": { "loose-envify": "^1.1.0", "scheduler": "^0.23.2" @@ -11293,7 +11279,6 @@ "version": "6.23.1", "resolved": "https://registry.npmjs.org/react-router-dom/-/react-router-dom-6.23.1.tgz", "integrity": "sha512-utP+K+aSTtEdbWpC+4gxhdlPFwuEfDKq8ZrPFU65bbRJY+l706qjR7yaidBpo3MSeA/fzwbXWbKBI6ftOnP3OQ==", - "peer": true, "dependencies": { "@remix-run/router": "1.16.1", "react-router": "6.23.1" @@ -11928,7 +11913,6 @@ "version": "1.77.2", "resolved": "https://registry.npmjs.org/sass/-/sass-1.77.2.tgz", "integrity": "sha512-eb4GZt1C3avsX3heBNlrc7I09nyT00IUuo4eFhAbeXWU2fvA7oXI53SxODVAA+zgZCk9aunAZgO+losjR3fAwA==", - "peer": true, "dependencies": { "chokidar": ">=3.0.0 <4.0.0", "immutable": "^4.0.0", @@ -13043,7 +13027,6 @@ "integrity": "sha512-qO3aKv3HoQC8QKiNSTuUM1l9o/XX3+c+VTgLHbJWHZGeTPVAg2XwazI9UWzoxjIJCGCV2zU60uqMzjeLZuULqA==", "dev": true, "license": "MIT", - "peer": true, "dependencies": { "esbuild": "^0.21.3", "postcss": "^8.4.43", diff --git a/src/pages/Team/Team.jsx b/src/pages/Team/Team.jsx index c8eb0ff7..a1e7636e 100644 --- a/src/pages/Team/Team.jsx +++ b/src/pages/Team/Team.jsx @@ -5,12 +5,9 @@ import styles from "./styles/Team.module.scss"; import { TeamCard } from "../../components"; import { FaRegArrowAltCircleRight } from "react-icons/fa"; import useWindowWidth from "../../utils/hooks/useWindowWidth"; -import MemberData from "../../data/Team.json"; -import AccessTypes from "../../data/Access.json"; import { ComponentLoading } from "../../microInteraction"; import { ChatBot } from "../../features"; - const Team = () => { useEffect(() => { window.scrollTo(0, 0); @@ -31,33 +28,24 @@ const Team = () => { const validMembers = response.data.data.filter( (member) => member.name !== null ); + const sortedMembers = validMembers.sort((a, b) => { - if (b.year !== a.year) { - return b.year - a.year; - } + if (b.year !== a.year) return b.year - a.year; return a.name.localeCompare(b.name); }); + setTeamMembers(sortedMembers); } else { - console.error("Error fetching team members:", response.data.message); setError({ message: "Sorry for the inconvenience, we are having issues fetching our Team Members", }); } } catch (error) { - console.error("Error fetching team members:", error); setError({ message: "Sorry for the inconvenience, we are having issues fetching our Team Members", }); - // const testMembers = MemberData.sort((a, b) => { - // if (b.year !== a.year) { - // return b.year - a.year; - // } - // return a.name.localeCompare(b.name); - // }); - // setTeamMembers(testMembers); } finally { setIsLoading(false); } @@ -78,24 +66,12 @@ const Team = () => { message: "Sorry for the inconvenience, we are having issues fetching our Team Members", }); - console.error("Error fetching Access Types:", response.data.message); - // const testAccess = AccessTypes.data; - // const filteredAccess = testAccess.filter( - // (accessType) => !["ADMIN", "USER", "ALUMNI"].includes(accessType) - // ); - // setAccess(filteredAccess); } } catch (error) { setError({ message: "Sorry for the inconvenience, we are having issues fetching our Team Members", }); - console.error("Error fetching Access Types:", error); - // const testAccess = AccessTypes.data; - // const filteredAccess = testAccess.filter( - // (accessType) => !["ADMIN", "USER", "ALUMNI"].includes(accessType) - // ); - // setAccess(filteredAccess); } }; @@ -103,7 +79,7 @@ const Team = () => { fetchTeamMembers(); }, []); - // Define the director access codes in the desired order + const boardAccessCodes = [ "PRESIDENT", "VICEPRESIDENT", @@ -121,7 +97,6 @@ const Team = () => { "DEPUTY_DIRECTOR_HUMAN_RESOURCE", ]; - // Function to extract team name from SENIOR_EXECUTIVE access codes const extractTeamFromAccess = (access) => { if (access.startsWith("SENIOR_EXECUTIVE_")) { return access.replace("SENIOR_EXECUTIVE_", ""); @@ -129,7 +104,6 @@ const Team = () => { return access; }; - // Function to get display role name const getDisplayRole = (access) => { const teamCode = extractTeamFromAccess(access); let role = teamCode @@ -138,8 +112,7 @@ const Team = () => { (word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase() ) .join(" "); - - // Ensure consistent capitalization for role names + switch (role.toLowerCase()) { case "pr and finance": role = "PR And Finance"; @@ -147,33 +120,26 @@ const Team = () => { case "human resource": role = "Human Resource"; break; - // Add other cases if needed for consistent capitalization } return role; }; - // Separate directors from other members const directorsAndAbove = teamMembers .filter((member) => boardAccessCodes.includes(member.access)) - .sort((a, b) => { - const aIndex = boardAccessCodes.indexOf(a.access); - const bIndex = boardAccessCodes.indexOf(b.access); - - return aIndex - bIndex; // Sort by access code order - - // return a.name.localeCompare(b.name); // Sort alphabetically within the same role - }); + .sort( + (a, b) => + boardAccessCodes.indexOf(a.access) - boardAccessCodes.indexOf(b.access) + ); const otherMembers = teamMembers.filter( (member) => !boardAccessCodes.includes(member.access) ); - // Create a role map for non-director roles const roleMap = access.reduce((map, code) => { if (!boardAccessCodes.includes(code)) { const displayRole = getDisplayRole(code); const teamCode = extractTeamFromAccess(code); - + if (!map[displayRole]) { map[displayRole] = []; } @@ -184,26 +150,20 @@ const Team = () => { const teamByRole = Object.keys(roleMap) .map((role) => { - const members = otherMembers.filter((member) => + const members = otherMembers.filter((member) => roleMap[role].includes(member.access) ); - // Sort members: Senior Executives first, then others - const seniorExecutives = members.filter((member) => - member.access.startsWith("SENIOR_EXECUTIVE_") || - member.extra?.designation === "Senior Executive" + const seniorExecutives = members.filter((member) => + member.access.startsWith("SENIOR_EXECUTIVE_") ); - const otherMembersWithoutSenior = members.filter((member) => - !member.access.startsWith("SENIOR_EXECUTIVE_") && - member.extra?.designation !== "Senior Executive" + const others = members.filter( + (member) => !member.access.startsWith("SENIOR_EXECUTIVE_") ); - return { - role, - members: [...seniorExecutives, ...otherMembersWithoutSenior], - }; + return { role, members: [...seniorExecutives, ...others] }; }) - .filter((roleGroup) => roleGroup.members.length > 0) + .filter((group) => group.members.length > 0) .sort((a, b) => { const order = [ "Technical", @@ -216,35 +176,27 @@ const Team = () => { return order.indexOf(a.role) - order.indexOf(b.role); }); - const TeamSection = ({ title, members, isDirector }) => { + const TeamSection = ({ title, members }) => { const membersPerRow = windowWidth < 500 ? 2 : 4; - const remainderMembersCount = members.length % membersPerRow; - const lastRowMembers = - remainderMembersCount > 0 ? members.slice(-remainderMembersCount) : []; - const otherMembers = - remainderMembersCount > 0 - ? members.slice(0, -remainderMembersCount) - : members; + const remainder = members.length % membersPerRow; + + const lastRow = remainder ? members.slice(-remainder) : []; + const mainRows = remainder ? members.slice(0, -remainder) : members; + return ( -
    +
    {title &&

    {title}

    } -
    - {otherMembers.map((member, idx) => ( - + +
    + {mainRows.map((m, idx) => ( + ))}
    - {lastRowMembers.length > 0 && ( + + {lastRow.length > 0 && (
    - {lastRowMembers.map((member, idx) => ( - + {lastRow.map((m, idx) => ( + ))}
    )} @@ -254,7 +206,8 @@ const Team = () => { return (
    - + +

    Meet Our{" "} { Team

    +

    We are a tight-knit community of passionate people devoted to bringing - about vibrant and awe-inspiring changes in the field of - Entrepreneurship. The pillars of our crew are the Marketing group, the - Creative group, the Technical group, and the Operations group. -

    -
    -
    - -
    -
    - picture of FIC -
    -
    -

    DR. VISHAL PRADHAN

    -

    FACULTY IN CHARGE

    - - {/*
    -

    - Dr. Vishal Pradhan is an exceptional academician and researcher at KIIT, - known for his clarity of thought, deep subject expertise, and commitment - to student success. His ability to connect advanced concepts with real-world - applications makes him a truly inspiring educator. -

    -
    */} - -
    -

    - "As FIC of FED, my vision is to ignite curiosity, nurture confidence, - and inspire students to rise beyond limits—so they walk into KIIT as - learners and grow into innovators who shape the world." --- Dr. Vishal Pradhan + vibrant and awe-inspiring changes in the field of Entrepreneurship.

    -
    -
    -
    -
    - {/*
    */} {isLoading ? ( ) : ( <> + +
    +
    +
    + FIC +
    + +
    +

    DR. VISHAL PRADHAN

    +

    FACULTY IN CHARGE

    + +
    +

    + "As FIC of FED, my vision is to ignite curiosity, nurture + confidence, and inspire students to rise beyond limits—so + they walk into KIIT as learners and grow into innovators who + shape the world." +

    +
    +
    +
    +
    + {error &&
    {error.message}
    } - + + Team + + BOD + + + } + members={directorsAndAbove} +/>
    @@ -338,34 +295,31 @@ const Team = () => {
    - {teamByRole.map( - (section, index) => - section.members.length > 0 && ( - - Team - - {section.role} - - - } - members={section.members} - isDirector={false} - /> - ) - )} + + {teamByRole.map((group, i) => ( + + Team + + {group.role} + + + } + members={group.members} + /> + ))} )}
    ); }; -export default Team; \ No newline at end of file +export default Team; From f09e0d88ab5879bf2c5d4a794f43dfc382f79ddc Mon Sep 17 00:00:00 2001 From: Rajatava Das Date: Sat, 13 Dec 2025 20:23:10 +0530 Subject: [PATCH 44/44] BOD update --- src/pages/Team/Team.jsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/pages/Team/Team.jsx b/src/pages/Team/Team.jsx index a1e7636e..796677d8 100644 --- a/src/pages/Team/Team.jsx +++ b/src/pages/Team/Team.jsx @@ -272,7 +272,7 @@ const Team = () => { - Team + Board Of { color: "transparent", }} > - BOD + Directors }