mirror of
https://github.com/UiO-Gaming/mustaboard.git
synced 2026-11-05 13:56:52 +01:00
add gangfest support
This commit is contained in:
1 parent
4c9dfdb1c2
commit
91491748cd
7 files changed
+203
-11
No files matched your search
Generated
+15
@@ -5749,6 +5749,21 @@
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/@next/swc-win32-ia32-msvc": {
|
||||
"version": "14.2.13",
|
||||
"resolved": "https://registry.npmjs.org/@next/swc-win32-ia32-msvc/-/swc-win32-ia32-msvc-14.2.13.tgz",
|
||||
"integrity": "sha512-V26ezyjPqQpDBV4lcWIh8B/QICQ4v+M5Bo9ykLN+sqeKKBxJVDpEc6biDVyluTXTC40f5IqCU0ttth7Es2ZuMw==",
|
||||
"cpu": [
|
||||
"ia32"
|
||||
],
|
||||
"optional": true,
|
||||
"os": [
|
||||
"win32"
|
||||
],
|
||||
"engines": {
|
||||
"node": ">= 10"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -12,7 +12,9 @@ interface SpecialEvent {
|
||||
name: string;
|
||||
date: string;
|
||||
time: string;
|
||||
end_time?: string;
|
||||
timeDiffMs?: number;
|
||||
ongoing?: boolean;
|
||||
}
|
||||
|
||||
interface Place {
|
||||
@@ -46,8 +48,7 @@ const EventCard: React.FC<EventCardProps> = ({
|
||||
specialTimeAhead,
|
||||
placeTimeAhead,
|
||||
}) => {
|
||||
const [nextSpecialEvent, setNextSpecialEvent] = useState<
|
||||
RecurringEvent | SpecialEvent | Place | null
|
||||
const [nextSpecialEvent, setNextSpecialEvent] = useState<SpecialEvent | null
|
||||
>(null);
|
||||
const [upcomingEvents, setUpcomingEvents] = useState<
|
||||
(RecurringEvent | SpecialEvent | Place)[]
|
||||
@@ -76,9 +77,24 @@ const EventCard: React.FC<EventCardProps> = ({
|
||||
// handle special events
|
||||
const specialEventsWithCountdown = specialEvents.map((event) => {
|
||||
const [day, month, year] = event.date.split(".");
|
||||
const eventTime = new Date(`${year}-${month}-${day}T${event.time}`);
|
||||
const timeDiffMs = eventTime.getTime() - now.getTime();
|
||||
return { ...event, timeDiffMs };
|
||||
|
||||
const start = new Date(`${year}-${month}-${day}T${event.time}`);
|
||||
|
||||
let end = null;
|
||||
if (event.end_time) {
|
||||
const endHour = parseInt(event.end_time.split(":")[0]);
|
||||
const endMinute = parseInt(event.end_time.split(":")[1]);
|
||||
end = new Date(start);
|
||||
if (endHour < start.getHours()) {
|
||||
end.setDate(end.getDate() + 1);
|
||||
}
|
||||
end.setHours(endHour, endMinute);
|
||||
}
|
||||
|
||||
const now = new Date();
|
||||
const ongoing = end ? now >= start && now <= end : false;
|
||||
const timeDiffMs = start.getTime() - now.getTime();
|
||||
return { ...event, timeDiffMs, ongoing };
|
||||
});
|
||||
|
||||
const filteredEvents = [
|
||||
@@ -98,10 +114,17 @@ const EventCard: React.FC<EventCardProps> = ({
|
||||
|
||||
const nextSpecialEvent = specialEventsWithCountdown.find(
|
||||
(event) =>
|
||||
event.timeDiffMs! > 0 &&
|
||||
event.timeDiffMs! <= parseInt(specialTimeAhead) * 60 * 60 * 1000 // 30 days
|
||||
(event.timeDiffMs! > 0 &&
|
||||
event.timeDiffMs! <= parseInt(specialTimeAhead) * 60 * 60 * 1000) ||
|
||||
event.ongoing
|
||||
);
|
||||
|
||||
if (specialEventsWithCountdown.some(e => e.ongoing)) {
|
||||
document.body.classList.add("swmg");
|
||||
} else {
|
||||
document.body.classList.remove("swmg");
|
||||
}
|
||||
|
||||
// sort events by time difference
|
||||
filteredEvents.sort((a, b) => a.timeDiffMs! - b.timeDiffMs!);
|
||||
|
||||
@@ -135,7 +158,7 @@ const EventCard: React.FC<EventCardProps> = ({
|
||||
</div>
|
||||
))}
|
||||
<hr className="border-2 border-primary"></hr>
|
||||
{nextSpecialEvent?.name != "" && (
|
||||
{nextSpecialEvent && (nextSpecialEvent.ongoing || nextSpecialEvent.timeDiffMs! > 0) && (
|
||||
<div className="flex flex-1 flex-row bg-gradient-to-r from-purple-500 to-overlay rounded-lg p-3 justify-between space border-2 border-primary animate-pulse">
|
||||
<div className="flex flex-row gap-3">
|
||||
<p className="parabold">Special Event</p>
|
||||
@@ -143,7 +166,9 @@ const EventCard: React.FC<EventCardProps> = ({
|
||||
</div>
|
||||
<div>
|
||||
<p className="para">
|
||||
{getTimeDifference(nextSpecialEvent?.timeDiffMs ?? 0)}
|
||||
{nextSpecialEvent?.ongoing
|
||||
? "Now"
|
||||
: getTimeDifference(nextSpecialEvent?.timeDiffMs ?? 0)}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
import React from "react";
|
||||
import menuItems from "../../public/menuItems.json";
|
||||
import MenuSection from "./MenuSection";
|
||||
import swmgSpecials from "../../public/swmgItems.json";
|
||||
import SWMGSpecials from "./SWMGSpecials";
|
||||
|
||||
function MenuCard() {
|
||||
return (
|
||||
@@ -13,9 +15,13 @@ function MenuCard() {
|
||||
{/*right-side container containing 2 boxes*/}
|
||||
<div className="flex flex-1 flex-col rounded-lg gap-3">
|
||||
{/*top box*/}
|
||||
<MenuSection title="Soda and Energy Drinks" items={menuItems.Soda}></MenuSection>
|
||||
<MenuSection
|
||||
title="Soda and Energy Drinks"
|
||||
items={menuItems.Soda}
|
||||
></MenuSection>
|
||||
|
||||
{/*bottom box*/}
|
||||
<SWMGSpecials title="Gangfest Specials" items={swmgSpecials.Specials} />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -0,0 +1,40 @@
|
||||
interface SpecialItem {
|
||||
name: string;
|
||||
description?: string;
|
||||
price: number;
|
||||
}
|
||||
|
||||
interface SpecialsProps {
|
||||
title: string;
|
||||
items: SpecialItem[];
|
||||
}
|
||||
|
||||
const SWMGSpecials: React.FC<SpecialsProps> = ({ title, items }) => {
|
||||
return (
|
||||
<div className="flex-1 specials-box bg-primary rounded-lg p-3 swmg-glow">
|
||||
<h1 className="text-headers mb-2">{title}</h1>
|
||||
<div className="flex flex-col gap-3">
|
||||
{items.map((item) => (
|
||||
<div
|
||||
key={item.name}
|
||||
className="grid grid-cols-2 justify-between items-start"
|
||||
>
|
||||
<div className="flex flex-col">
|
||||
<p className="para">{item.name}</p>
|
||||
{item.description && (
|
||||
<p className="parasmall text-p">{item.description}</p>
|
||||
)}
|
||||
</div>
|
||||
<div className="flex justify-end">
|
||||
<p className="para">kr {item.price}</p>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
|
||||
export default SWMGSpecials;
|
||||
|
||||
@@ -77,3 +77,55 @@ p {
|
||||
text-wrap: balance;
|
||||
}
|
||||
}
|
||||
|
||||
/* === swmg theme === */
|
||||
.swmg {
|
||||
--background: #050509;
|
||||
--foreground: #120c1c;
|
||||
--primary: #230b3a;
|
||||
--headers: #ffffff;
|
||||
--overlay: #1a102b;
|
||||
}
|
||||
|
||||
.swmg p,
|
||||
.swmg .para,
|
||||
.swmg .parasmall,
|
||||
.swmg .text-p,
|
||||
.swmg .time {
|
||||
color: #f5c542 !important;
|
||||
text-shadow: 0 0 8px #ffffff88;
|
||||
}
|
||||
|
||||
.swmg .text-headers {
|
||||
color: #f5c542 !important;
|
||||
text-shadow: 0 0 8px #ffffff88;
|
||||
}
|
||||
|
||||
@keyframes swmgPulse {
|
||||
0%, 100% {
|
||||
box-shadow: 0 0 10px #6f42c1aa, 0 0 20px #6f42c188;
|
||||
}
|
||||
50% {
|
||||
box-shadow: 0 0 15px #a164ffcc, 0 0 30px #6f42c1cc;
|
||||
}
|
||||
}
|
||||
|
||||
.swmg .animate-pulse,
|
||||
.swmg .swmg-glow {
|
||||
animation: swmgPulse 2.5s ease-in-out infinite;
|
||||
}
|
||||
|
||||
.swmg .bg-primary {
|
||||
animation: swmgPulse 5s ease-in-out infinite;
|
||||
}
|
||||
|
||||
.swmg .specials-box {
|
||||
background: linear-gradient(145deg, #2a1d38, #1a102b);
|
||||
border: 2px solid #f5c542aa;
|
||||
border-radius: 12px;
|
||||
box-shadow:
|
||||
0 0 8px #f5c54255,
|
||||
0 0 20px #6f42c188,
|
||||
inset 0 0 12px #2a1d38cc;
|
||||
animation: swmgPulse 3s ease-in-out infinite;
|
||||
}
|
||||
@@ -26,7 +26,8 @@
|
||||
{
|
||||
"name": "Gangfest",
|
||||
"date": "22.03.2025",
|
||||
"time": "18:00"
|
||||
"time": "18:00",
|
||||
"end_time": "03:00"
|
||||
}
|
||||
],
|
||||
|
||||
@@ -96,6 +97,39 @@
|
||||
"time": "22:00"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"name": "Valkyrien Grill",
|
||||
"closing_times" : [
|
||||
{
|
||||
"day": "Monday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Tuesday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Wednesday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Thursday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Friday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Saturday",
|
||||
"time": "04:00"
|
||||
},
|
||||
{
|
||||
"day": "Sunday",
|
||||
"time": "04:00"
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
{
|
||||
"Specials": [
|
||||
{
|
||||
"name": "Hard Cider",
|
||||
"description": "Apple, 0.4 liter, 6% vol",
|
||||
"price": 20
|
||||
},
|
||||
{
|
||||
"name": "Cup Noodle",
|
||||
"description": "Spicy Beef or Chicken",
|
||||
"price": 23
|
||||
},
|
||||
{
|
||||
"name": "Doritos",
|
||||
"description": "Sweet Chili, Nacho Cheese, Flamin' Hot",
|
||||
"price": 12
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user