+ return (
+
+
+
+
+ {endTime
+ ? dateTimeFormat.formatRange(new Date(startTime), new Date(endTime))
+ : dateTimeFormat.format(new Date(startTime))}
+
+
{title}
+
+ {/*
{props.title}
@@ -71,8 +71,8 @@ const EventCard = ({ image, title, startTime, endTime }: EventCard) => {
Close
*/}
-
- );
+
+ );
};
export default EventCard;
diff --git a/apps/site/src/app/events/PastEvents.module.scss b/apps/site/src/app/events/PastEvents.module.scss
index 4963e5d..fe38a81 100644
--- a/apps/site/src/app/events/PastEvents.module.scss
+++ b/apps/site/src/app/events/PastEvents.module.scss
@@ -1,11 +1,11 @@
.events {
- $card-width: 480px;
- $gap-x: 24px;
+ $card-width: 480px;
+ $gap-x: 24px;
- display: grid;
- grid-template-columns: repeat(auto-fill, $card-width);
- gap: 32px $gap-x;
- justify-content: center;
- max-width: $card-width * 3 + $gap-x * 2;
- margin: 0 auto;
+ display: grid;
+ grid-template-columns: repeat(auto-fill, $card-width);
+ gap: 32px $gap-x;
+ justify-content: center;
+ max-width: $card-width * 3 + $gap-x * 2;
+ margin: 0 auto;
}
diff --git a/apps/site/src/app/events/PastEvents.tsx b/apps/site/src/app/events/PastEvents.tsx
index e6e3599..e3190da 100644
--- a/apps/site/src/app/events/PastEvents.tsx
+++ b/apps/site/src/app/events/PastEvents.tsx
@@ -4,30 +4,30 @@ import EventCard from "./EventCard";
import styles from "./PastEvents.module.scss";
const PastEvents = async () => {
- const events = await getEventsDescending();
+ const events = await getEventsDescending();
- const now = new Date();
- const pastEvents = events.filter(({ timeRange: { start, end } }) =>
- end ? new Date(end) < now : new Date(start) < now
- );
+ const now = new Date();
+ const pastEvents = events.filter(({ timeRange: { start, end } }) =>
+ end ? new Date(end) < now : new Date(start) < now
+ );
- if (pastEvents.length === 0)
- return
No past events! ;
+ if (pastEvents.length === 0)
+ return
No past events! ;
- return (
-
- {pastEvents.map((event) => (
-
- ))}
-
- );
+ return (
+
+ {pastEvents.map((event) => (
+
+ ))}
+
+ );
};
export default PastEvents;
diff --git a/apps/site/src/app/events/UpcomingEvents.module.scss b/apps/site/src/app/events/UpcomingEvents.module.scss
index 84307e8..2453671 100644
--- a/apps/site/src/app/events/UpcomingEvents.module.scss
+++ b/apps/site/src/app/events/UpcomingEvents.module.scss
@@ -1,34 +1,34 @@
.title {
- font-size: 2.5rem;
- text-align: center;
- padding-top: 150px;
- padding-bottom: 30px;
+ font-size: 2.5rem;
+ text-align: center;
+ padding-top: 150px;
+ padding-bottom: 30px;
}
.noEvents {
- margin-top: 30px;
+ margin-top: 30px;
- .calendarIcon {
- width: 128px;
- height: 146px;
- margin-bottom: 20px;
- }
+ .calendarIcon {
+ width: 128px;
+ height: 146px;
+ margin-bottom: 20px;
+ }
- .stayTuned {
- font-weight: 400;
- margin-top: 14px;
- font-size: 20px;
- }
+ .stayTuned {
+ font-weight: 400;
+ margin-top: 14px;
+ font-size: 20px;
+ }
}
.events {
- $card-width: 480px;
- $gap-x: 24px;
+ $card-width: 480px;
+ $gap-x: 24px;
- display: grid;
- grid-template-columns: repeat(auto-fill, $card-width);
- gap: 32px $gap-x;
- justify-content: center;
- max-width: $card-width * 3 + $gap-x * 2;
- margin: 0 auto;
+ display: grid;
+ grid-template-columns: repeat(auto-fill, $card-width);
+ gap: 32px $gap-x;
+ justify-content: center;
+ max-width: $card-width * 3 + $gap-x * 2;
+ margin: 0 auto;
}
diff --git a/apps/site/src/app/events/UpcomingEvents.tsx b/apps/site/src/app/events/UpcomingEvents.tsx
index b9f5622..6906f07 100644
--- a/apps/site/src/app/events/UpcomingEvents.tsx
+++ b/apps/site/src/app/events/UpcomingEvents.tsx
@@ -5,41 +5,41 @@ import calendar from "./calendar-alt-regular.svg";
import styles from "./UpcomingEvents.module.scss";
const UpcomingEvents = async () => {
- const events = await getEventsDescending();
+ const events = await getEventsDescending();
- const now = new Date();
- const upcomingEvents = events.filter(({ timeRange: { start, end } }) =>
- end ? new Date(end) > now : new Date(start) > now
- );
+ const now = new Date();
+ const upcomingEvents = events.filter(({ timeRange: { start, end } }) =>
+ end ? new Date(end) > now : new Date(start) > now
+ );
- if (upcomingEvents.length === 0)
- return (
-
-
-
No Upcoming Events
-
- Stay tuned for upcoming events!
-
-
- );
+ if (upcomingEvents.length === 0)
+ return (
+
+
+
No Upcoming Events
+
+ Stay tuned for upcoming events!
+
+
+ );
- return (
- <>
-
Upcoming Events
-
- {upcomingEvents.reverse().map((event) => (
-
- ))}
-
- >
- );
+ return (
+ <>
+
Upcoming Events
+
+ {upcomingEvents.reverse().map((event) => (
+
+ ))}
+
+ >
+ );
};
export default UpcomingEvents;
diff --git a/apps/site/src/app/events/getEvents.ts b/apps/site/src/app/events/getEvents.ts
index 760656c..830bcae 100644
--- a/apps/site/src/app/events/getEvents.ts
+++ b/apps/site/src/app/events/getEvents.ts
@@ -6,28 +6,28 @@ import { client } from "@/lib/sanity/sanityClient";
import { SanityDocument, SanityImageReference } from "@/lib/sanity/types";
export const Cover = SanityImageReference.extend({
- alt: z.string(),
+ alt: z.string(),
});
const Events = z.array(
- SanityDocument.extend({
- _type: z.literal("event"),
- title: z.string(),
- cover: Cover,
- timeRange: z.object({
- timezone: z.string(),
- start: z.string().datetime(),
- end: z.string().datetime().optional(),
- }),
- description: z.string(),
- location: z.string().optional(),
- })
+ SanityDocument.extend({
+ _type: z.literal("event"),
+ title: z.string(),
+ cover: Cover,
+ timeRange: z.object({
+ timezone: z.string(),
+ start: z.string().datetime(),
+ end: z.string().datetime().optional(),
+ }),
+ description: z.string(),
+ location: z.string().optional(),
+ })
);
export const getEventsDescending = cache(async () => {
- return Events.parse(
- await client.fetch(
- "*[_type == 'event'] | order(timeRange.start desc, timeRange.end desc)"
- )
- );
+ return Events.parse(
+ await client.fetch(
+ "*[_type == 'event'] | order(timeRange.start desc, timeRange.end desc)"
+ )
+ );
});
diff --git a/apps/site/src/app/events/page.tsx b/apps/site/src/app/events/page.tsx
index 10183fb..0e1d725 100644
--- a/apps/site/src/app/events/page.tsx
+++ b/apps/site/src/app/events/page.tsx
@@ -12,29 +12,29 @@ const title = "Events — Hack at UCI";
// TODO: write description for events page
const description = "";
export const metadata: Metadata = {
- title,
- description,
- openGraph: {
- title,
- description,
- },
+ title,
+ description,
+ openGraph: {
+ title,
+ description,
+ },
};
export default async function Home() {
- return (
-
-
-
- {/* https://nextjs.org/docs/app/building-your-application/data-fetching/fetching#:~:text=Async%20Server%20Component%20TypeScript%20Error */}
- {/* @ts-expect-error Async Server Component */}
-
+ return (
+
+
+
+ {/* https://nextjs.org/docs/app/building-your-application/data-fetching/fetching#:~:text=Async%20Server%20Component%20TypeScript%20Error */}
+ {/* @ts-expect-error Async Server Component */}
+
-
-
Past Events
- {/* @ts-expect-error Async Server Component */}
-
-
-
-
- );
+
+
Past Events
+ {/* @ts-expect-error Async Server Component */}
+
+
+
+
+ );
}
diff --git a/apps/site/src/app/globals.scss b/apps/site/src/app/globals.scss
index 6c0646f..dcc3bad 100644
--- a/apps/site/src/app/globals.scss
+++ b/apps/site/src/app/globals.scss
@@ -1,51 +1,51 @@
@use "~@/lib/common/styles/hack-variables.scss" as variables;
html {
- scroll-behavior: smooth;
+ scroll-behavior: smooth;
}
body {
- margin: 0;
+ margin: 0;
}
body {
- text-align: center;
- background-color: variables.$white;
- color: black;
-
- h1 {
- font-size: 4.5rem;
- font-weight: 700;
- }
- h2 {
- font-size: 3rem;
- font-weight: 500;
- }
- h3 {
- font-size: 2.25rem;
- }
+ text-align: center;
+ background-color: variables.$white;
+ color: black;
+
+ h1 {
+ font-size: 4.5rem;
+ font-weight: 700;
+ }
+ h2 {
+ font-size: 3rem;
+ font-weight: 500;
+ }
+ h3 {
+ font-size: 2.25rem;
+ }
}
.bg-gray {
- background-color: variables.$light-grey;
+ background-color: variables.$light-grey;
}
.container {
- margin: auto;
- padding-bottom: 7.5rem;
- padding-top: 7.5rem;
-
- @media (min-width: 576px) {
- max-width: 540px;
- padding-bottom: 11.25rem;
- padding-top: 11.25rem;
- }
-
- @media (min-width: 768px) {
- max-width: 720px;
- }
-
- @media (min-width: 992px) {
- max-width: 960px;
- }
+ margin: auto;
+ padding-bottom: 7.5rem;
+ padding-top: 7.5rem;
+
+ @media (min-width: 576px) {
+ max-width: 540px;
+ padding-bottom: 11.25rem;
+ padding-top: 11.25rem;
+ }
+
+ @media (min-width: 768px) {
+ max-width: 720px;
+ }
+
+ @media (min-width: 992px) {
+ max-width: 960px;
+ }
}
diff --git a/apps/site/src/app/layout.tsx b/apps/site/src/app/layout.tsx
index 7c0b021..7978682 100644
--- a/apps/site/src/app/layout.tsx
+++ b/apps/site/src/app/layout.tsx
@@ -6,36 +6,36 @@ import Footer from "@/lib/common/components/Footer";
import "./globals.scss";
const poppins = Poppins({
- subsets: ["latin"],
- weight: ["300", "400", "500", "600", "700"],
+ subsets: ["latin"],
+ weight: ["300", "400", "500", "600", "700"],
});
const title = "Hack at UCI";
const description =
- "Hack at UCI is a student-run organization established to provide students with a platform to learn, grow, and develop technology of the future. Established in 2013, our mission is to promote, educate, and enhance the community around us by giving students the platform to learn and create technology.";
+ "Hack at UCI is a student-run organization established to provide students with a platform to learn, grow, and develop technology of the future. Established in 2013, our mission is to promote, educate, and enhance the community around us by giving students the platform to learn and create technology.";
export const metadata: Metadata = {
- title,
- description,
- openGraph: {
- title,
- description,
- },
+ title,
+ description,
+ openGraph: {
+ title,
+ description,
+ },
};
export default function RootLayout({
- children,
+ children,
}: {
- children: React.ReactNode;
+ children: React.ReactNode;
}) {
- return (
-
-
-
- {children}
- {/* https://nextjs.org/docs/app/building-your-application/data-fetching/fetching#:~:text=Async%20Server%20Component%20TypeScript%20Error */}
- {/* @ts-expect-error Async Server Component */}
-
-
-
- );
+ return (
+
+
+
+ {children}
+ {/* https://nextjs.org/docs/app/building-your-application/data-fetching/fetching#:~:text=Async%20Server%20Component%20TypeScript%20Error */}
+ {/* @ts-expect-error Async Server Component */}
+
+
+
+ );
}
diff --git a/apps/site/src/app/recruit/corporate/page.tsx b/apps/site/src/app/recruit/corporate/page.tsx
index 9849d77..96aaea8 100644
--- a/apps/site/src/app/recruit/corporate/page.tsx
+++ b/apps/site/src/app/recruit/corporate/page.tsx
@@ -1,60 +1,60 @@
import corporateLogo from "./corporate-logo.svg";
const Corporate = () => {
- return (
- <>
-
-
Corporate
-
- As a Corporate Outreach organizer, you will be responsible for
- contacting companies for financial sponsorship, hardware, swag, and
- mentorship. We build meaningful relationships with existing partners and
- reach out to other local companies to support Hack at UCI’s hackathons
- and club operations. Help us communicate with tech companies by using
- the following strategies: diligent emailing, scheduling phone calls,
- attending career fairs, participating at hackathons, and networking at
- professional events! Not only does this help us grow our professional
- network to have better experiences for our attendees, but this is also a
- great way for you to build lasting professional relationships with a
- wide breadth of companies and gain opportunities to get internships or
- full-time jobs.
-
-
- General corporate organizer: Gain as many sponsorships
- from companies whether it be monetary support, prizes, mentors, swag,
- etc.
-
-
- Hackathon specialist: Attend other hackathons (LA
- Hacks, SD Hacks, Cal Hacks, Hacktech, Citrus Hack, TreeHacks, etc) and
- talk to the sponsors there. Your job is to advertise Hack at UCI,
- network with companies, collect contact information, record what
- happened, and continuously follow up with the people you've met.
-
-
- Career specialist: Attend and volunteer at UCI career
- fairs (Fall Career Fair, STEM Career Fair, etc). Your job is to
- advertise Hack at UCI, network with companies, collect contact
- information, record what happened, and continuously follow up with the
- people you've met.
-
-
- Key Qualifications
-
-
- Strong written and verbal communication skills
- Proficient in managing information through spreadsheets
- Organized and responsive
- Experience with drafting professional documents
- High tolerance for rejection
- Drive to work in a fast paced environment
-
- Willing to dedicate ~5 hours per week to Hack (meeting, content
- creation, etc.)
-
-
- >
- );
+ return (
+ <>
+
+
Corporate
+
+ As a Corporate Outreach organizer, you will be responsible for
+ contacting companies for financial sponsorship, hardware, swag, and
+ mentorship. We build meaningful relationships with existing partners and
+ reach out to other local companies to support Hack at UCI’s hackathons
+ and club operations. Help us communicate with tech companies by using
+ the following strategies: diligent emailing, scheduling phone calls,
+ attending career fairs, participating at hackathons, and networking at
+ professional events! Not only does this help us grow our professional
+ network to have better experiences for our attendees, but this is also a
+ great way for you to build lasting professional relationships with a
+ wide breadth of companies and gain opportunities to get internships or
+ full-time jobs.
+
+
+ General corporate organizer: Gain as many sponsorships
+ from companies whether it be monetary support, prizes, mentors, swag,
+ etc.
+
+
+ Hackathon specialist: Attend other hackathons (LA
+ Hacks, SD Hacks, Cal Hacks, Hacktech, Citrus Hack, TreeHacks, etc) and
+ talk to the sponsors there. Your job is to advertise Hack at UCI,
+ network with companies, collect contact information, record what
+ happened, and continuously follow up with the people you've met.
+
+
+ Career specialist: Attend and volunteer at UCI career
+ fairs (Fall Career Fair, STEM Career Fair, etc). Your job is to
+ advertise Hack at UCI, network with companies, collect contact
+ information, record what happened, and continuously follow up with the
+ people you've met.
+
+
+ Key Qualifications
+
+
+ Strong written and verbal communication skills
+ Proficient in managing information through spreadsheets
+ Organized and responsive
+ Experience with drafting professional documents
+ High tolerance for rejection
+ Drive to work in a fast paced environment
+
+ Willing to dedicate ~5 hours per week to Hack (meeting, content
+ creation, etc.)
+
+
+ >
+ );
};
export default Corporate;
diff --git a/apps/site/src/app/recruit/layout.tsx b/apps/site/src/app/recruit/layout.tsx
index 2cf44fc..8693c54 100644
--- a/apps/site/src/app/recruit/layout.tsx
+++ b/apps/site/src/app/recruit/layout.tsx
@@ -9,76 +9,76 @@ import gears from "./gears.svg";
import styles from "./layout.module.scss";
const COMMITTEES = {
- Corporate: "corporate",
- Logistics: "logistics",
- Marketing: "marketing",
- Technology: "tech",
+ Corporate: "corporate",
+ Logistics: "logistics",
+ Marketing: "marketing",
+ Technology: "tech",
};
const title = "Events — Hack at UCI";
// TODO: write description for events page
const description = "";
export const metadata: Metadata = {
- title,
- description,
- openGraph: {
- title,
- description,
- },
+ title,
+ description,
+ openGraph: {
+ title,
+ description,
+ },
};
export default async function RecruitmentLayout({
- children,
+ children,
}: {
- children: React.ReactNode;
+ children: React.ReactNode;
}) {
- return (
-
-
-
-
-
-
-
Learn
-
- We host workshops and hackathons that support people as they learn
- industry-relevant skills.
-
-
-
-
-
Explore
-
- We provide professional events that help people to explore new
- technologies, ground-breaking ideas, and career paths.
-
-
-
-
-
Create
-
- We support the developer community at UCI to collaborate on
- innovative, technical products that have meaning.
-
-
-
-
-
-
-
Our Committees
-
- {Object.entries(COMMITTEES).map(([name, path], index) => (
-
- {name}
-
- ))}
-
-
{children}
-
- Look out for recruitment in the fall!
-
-
-
-
- );
+ return (
+
+
+
+
+
+
+
Learn
+
+ We host workshops and hackathons that support people as they learn
+ industry-relevant skills.
+
+
+
+
+
Explore
+
+ We provide professional events that help people to explore new
+ technologies, ground-breaking ideas, and career paths.
+
+
+
+
+
Create
+
+ We support the developer community at UCI to collaborate on
+ innovative, technical products that have meaning.
+
+
+
+
+
+
+
Our Committees
+
+ {Object.entries(COMMITTEES).map(([name, path], index) => (
+
+ {name}
+
+ ))}
+
+
{children}
+
+ Look out for recruitment in the fall!
+
+
+
+
+ );
}
diff --git a/apps/site/src/app/recruit/logistics/page.tsx b/apps/site/src/app/recruit/logistics/page.tsx
index 34893de..c10fe26 100644
--- a/apps/site/src/app/recruit/logistics/page.tsx
+++ b/apps/site/src/app/recruit/logistics/page.tsx
@@ -1,43 +1,43 @@
import logisticsLogo from "./logistics-logo.svg";
const Logistics = () => {
- return (
- <>
-
-
Logistics
-
- The logistics team organizes all hackathon operations, as well as other
- events during the year such as workshops, fundraising, and socials. We
- are a detail-oriented and impact-driven team, uniting diverse
- backgrounds and skill sets to ensure that events run smoothly and
- benefit all parties involved.
-
-
- Key Qualifications
-
-
- Excellent time management skills
- Great planning and organization skills
- Attention to detail
-
- Strong written and verbal communication skills, especially in a timely
- and efficient manner for issues
-
- Drive to work in a fast paced environment
- Work in a team based environment in order to meet goals
- Handle a large budget in order to organize events efficiently
-
- Proficient in managing information through folders (Google Drive),
- spreadsheets (Google Sheets), and documents (Google Docs)
-
-
- Willing to dedicate ~4 hours per week to Hack (meeting, content
- creation, etc.)
-
- Most importantly, willingness to adapt and learn new things
-
- >
- );
+ return (
+ <>
+
+
Logistics
+
+ The logistics team organizes all hackathon operations, as well as other
+ events during the year such as workshops, fundraising, and socials. We
+ are a detail-oriented and impact-driven team, uniting diverse
+ backgrounds and skill sets to ensure that events run smoothly and
+ benefit all parties involved.
+
+
+ Key Qualifications
+
+
+ Excellent time management skills
+ Great planning and organization skills
+ Attention to detail
+
+ Strong written and verbal communication skills, especially in a timely
+ and efficient manner for issues
+
+ Drive to work in a fast paced environment
+ Work in a team based environment in order to meet goals
+ Handle a large budget in order to organize events efficiently
+
+ Proficient in managing information through folders (Google Drive),
+ spreadsheets (Google Sheets), and documents (Google Docs)
+
+
+ Willing to dedicate ~4 hours per week to Hack (meeting, content
+ creation, etc.)
+
+ Most importantly, willingness to adapt and learn new things
+
+ >
+ );
};
export default Logistics;
diff --git a/apps/site/src/app/recruit/marketing/page.tsx b/apps/site/src/app/recruit/marketing/page.tsx
index 9e6bcd5..da9bc0a 100644
--- a/apps/site/src/app/recruit/marketing/page.tsx
+++ b/apps/site/src/app/recruit/marketing/page.tsx
@@ -1,67 +1,67 @@
import marketingLogo from "./marketing-logo.svg";
const Marketing = () => {
- return (
- <>
-
-
Marketing
-
-
- General Marketing Organizer: As a general marketing
- organizer, your responsibilities vary from sending emails via to
- making posts on social media platforms in a witty and creative manner.
- You are required to meet strict deadlines and have exceptional
- communication skills since marketing is all about reaching out to the
- public.
-
-
- Key Qualifications
-
-
- Exceptional communication and writing skills
-
- Experience with email and social media marketing campaigns
- (Instagram, Facebook, Discord, MailChimp)
-
- Creative and critical thinking abilities
- Drive to work in a fast-paced cross-functional team
- Photography and videography skills (preferred)
-
-
-
-
- Graphic Designer: As a graphic designer, you will be
- responsible for creating graphics that represent our organization and
- events for various platforms, such as Facebook or Instagram. Designers
- also shape the theme and aesthetic for ZotHacks and HackUCI. Each
- design will follow general guidelines and have to be submitted for
- review before given deadlines. You must be detail-oriented and have
- proficient knowledge in visual design, color theory, and typography.
- You will also be working closely with the web development team, so
- experience with HTML and CSS is a plus, but not required.
-
-
- Key Qualifications
-
-
- Proficiency in graphic design
-
- Experience using a raster graphics editor (ex. Adobe Photoshop, Fire
- Alpaca, etc.)
-
- Creative and critical thinking abilities
-
- Experience using a vector graphics editor (ex. Adobe Illustrator,
- Inkscape, etc.)
-
-
- Willing to dedicate ~4 hours per week to Hack (meeting, content
- creation, etc.)
-
-
-
- >
- );
+ return (
+ <>
+
+
Marketing
+
+
+ General Marketing Organizer: As a general marketing
+ organizer, your responsibilities vary from sending emails via to
+ making posts on social media platforms in a witty and creative manner.
+ You are required to meet strict deadlines and have exceptional
+ communication skills since marketing is all about reaching out to the
+ public.
+
+
+ Key Qualifications
+
+
+ Exceptional communication and writing skills
+
+ Experience with email and social media marketing campaigns
+ (Instagram, Facebook, Discord, MailChimp)
+
+ Creative and critical thinking abilities
+ Drive to work in a fast-paced cross-functional team
+ Photography and videography skills (preferred)
+
+
+
+
+ Graphic Designer: As a graphic designer, you will be
+ responsible for creating graphics that represent our organization and
+ events for various platforms, such as Facebook or Instagram. Designers
+ also shape the theme and aesthetic for ZotHacks and HackUCI. Each
+ design will follow general guidelines and have to be submitted for
+ review before given deadlines. You must be detail-oriented and have
+ proficient knowledge in visual design, color theory, and typography.
+ You will also be working closely with the web development team, so
+ experience with HTML and CSS is a plus, but not required.
+
+
+ Key Qualifications
+
+
+ Proficiency in graphic design
+
+ Experience using a raster graphics editor (ex. Adobe Photoshop, Fire
+ Alpaca, etc.)
+
+ Creative and critical thinking abilities
+
+ Experience using a vector graphics editor (ex. Adobe Illustrator,
+ Inkscape, etc.)
+
+
+ Willing to dedicate ~4 hours per week to Hack (meeting, content
+ creation, etc.)
+
+
+
+ >
+ );
};
export default Marketing;
diff --git a/apps/site/src/app/recruit/page.tsx b/apps/site/src/app/recruit/page.tsx
index 5614503..7a77725 100644
--- a/apps/site/src/app/recruit/page.tsx
+++ b/apps/site/src/app/recruit/page.tsx
@@ -1,5 +1,5 @@
import { redirect } from "next/navigation";
export default function Recruitment() {
- redirect("/recruit/corporate");
+ redirect("/recruit/corporate");
}
diff --git a/apps/site/src/app/recruit/tech/page.tsx b/apps/site/src/app/recruit/tech/page.tsx
index fd97c4a..5a7ae66 100644
--- a/apps/site/src/app/recruit/tech/page.tsx
+++ b/apps/site/src/app/recruit/tech/page.tsx
@@ -1,49 +1,49 @@
import techLogo from "./tech-logo.svg";
const Tech = () => {
- return (
- <>
-
-
Technology
-
- Every year, thousands of students across the country apply to our annual
- HackUCI event on our website. In addition, our website also receives a
- huge amount of traffic from various companies who visit our website to
- obtain sponsorship information. By joining the Technology team, you not
- only get to work on a large-scale hackathon application tracking
- platform, but you also have the opportunity to build exciting internal
- tools for our organizers so that they can work more efficiently.
-
-
- As a general developer, your primary task is to design and develop an
- eye-catching user interface that delivers a good first impression to
- both attendees and sponsors. You will be streamlining the hackathon
- registration experience and utilize the latest frontend technologies to
- implement it. On occasion, you will be tasked with building onto our
- server-side application or setting up and maintaining databases.
-
-
- Key Qualifications
-
-
- Proficiency in HTML, CSS and JavaScript
- Experience with modern JavaScript frameworks
- Ability to write clean, well-documented code
-
- Experience with front-end styling libraries (e.g. Bootstrap, Material
- UI, etc.)
-
-
-
- Preferred Qualifications
-
-
- Experience developing web applications with React
- Experience with backend web frameworks (e.g. Express, FastAPI)
- Experience using cloud databases
-
- >
- );
+ return (
+ <>
+
+
Technology
+
+ Every year, thousands of students across the country apply to our annual
+ HackUCI event on our website. In addition, our website also receives a
+ huge amount of traffic from various companies who visit our website to
+ obtain sponsorship information. By joining the Technology team, you not
+ only get to work on a large-scale hackathon application tracking
+ platform, but you also have the opportunity to build exciting internal
+ tools for our organizers so that they can work more efficiently.
+
+
+ As a general developer, your primary task is to design and develop an
+ eye-catching user interface that delivers a good first impression to
+ both attendees and sponsors. You will be streamlining the hackathon
+ registration experience and utilize the latest frontend technologies to
+ implement it. On occasion, you will be tasked with building onto our
+ server-side application or setting up and maintaining databases.
+
+
+ Key Qualifications
+
+
+ Proficiency in HTML, CSS and JavaScript
+ Experience with modern JavaScript frameworks
+ Ability to write clean, well-documented code
+
+ Experience with front-end styling libraries (e.g. Bootstrap, Material
+ UI, etc.)
+
+
+
+ Preferred Qualifications
+
+
+ Experience developing web applications with React
+ Experience with backend web frameworks (e.g. Express, FastAPI)
+ Experience using cloud databases
+
+ >
+ );
};
export default Tech;
diff --git a/apps/site/src/app/sponsors/page.module.scss b/apps/site/src/app/sponsors/page.module.scss
index 7c2ce53..6588881 100644
--- a/apps/site/src/app/sponsors/page.module.scss
+++ b/apps/site/src/app/sponsors/page.module.scss
@@ -1,182 +1,182 @@
@use "~@/lib/common/styles/hack-variables.scss" as variables;
.sponsorHackuci {
- margin: 0px 0 40px 0;
+ margin: 0px 0 40px 0;
}
.sponsorHackuci input {
- font-weight: 600;
- font-size: 20px;
- border: none;
- border-radius: 30px;
- color: white;
- padding: 15px 32px;
- text-align: center;
- background: linear-gradient(90deg, #ff928b 0%, #8494da 100%);
- transition: 300ms;
- opacity: 1;
- &:hover {
- opacity: 85%;
- }
+ font-weight: 600;
+ font-size: 20px;
+ border: none;
+ border-radius: 30px;
+ color: white;
+ padding: 15px 32px;
+ text-align: center;
+ background: linear-gradient(90deg, #ff928b 0%, #8494da 100%);
+ transition: 300ms;
+ opacity: 1;
+ &:hover {
+ opacity: 85%;
+ }
}
.sponsorHackuci a {
- position: relative;
+ position: relative;
}
.sponsorAttendees {
- display: flex;
- justify-content: center;
- align-content: center;
- & span {
- font-size: 48px;
- padding-left: 10px;
- }
+ display: flex;
+ justify-content: center;
+ align-content: center;
+ & span {
+ font-size: 48px;
+ padding-left: 10px;
+ }
}
.zothacksBtn {
- background: linear-gradient(90deg, #2f9c95 0%, #add8ab 100%) !important;
+ background: linear-gradient(90deg, #2f9c95 0%, #add8ab 100%) !important;
}
.sponsorHackGraph {
- padding-top: 30px;
+ padding-top: 30px;
}
.sponsorStatImg {
- width: 60%;
- margin: 20px;
+ width: 60%;
+ margin: 20px;
}
.sponsorStats {
- display: inline-block;
- margin: 100px 0;
+ display: inline-block;
+ margin: 100px 0;
}
.sponsorStat {
- display: inline-block;
- margin: 10px 50px;
- max-width: 140px;
- vertical-align: text-top;
+ display: inline-block;
+ margin: 10px 50px;
+ max-width: 140px;
+ vertical-align: text-top;
}
.sponsorStat p {
- font-size: 60px;
- margin: 0;
+ font-size: 60px;
+ margin: 0;
}
.sponsorStat label {
- font-size: 20px;
- margin: 0;
+ font-size: 20px;
+ margin: 0;
}
.sponsorHackuci p {
- margin: 0;
+ margin: 0;
}
.sponsorStatHackNumber {
- padding-top: 110px;
- padding-left: 10px;
- text-align: center;
- font-size: 120px;
+ padding-top: 110px;
+ padding-left: 10px;
+ text-align: center;
+ font-size: 120px;
}
.sponsorStatHackLabel {
- padding-top: 230px;
- text-align: center;
- font-size: 60px;
+ padding-top: 230px;
+ text-align: center;
+ font-size: 60px;
}
.sponsorContentAnecdote p {
- margin: 0;
+ margin: 0;
}
.sponsorContentAnecdote {
- grid-column: 3;
- border-radius: 10px;
- padding: 35px 35px 20px 35px;
- background-color: variables.$light-grey;
- margin-bottom: 30px;
- text-align: left;
- font-size: 20px;
+ grid-column: 3;
+ border-radius: 10px;
+ padding: 35px 35px 20px 35px;
+ background-color: variables.$light-grey;
+ margin-bottom: 30px;
+ text-align: left;
+ font-size: 20px;
}
#Bianca {
- min-height: 230px;
- grid-row: 3;
+ min-height: 230px;
+ grid-row: 3;
}
#Lizzie {
- min-height: 190px;
+ min-height: 190px;
}
#Cher {
- min-height: 200px;
- grid-row: 7;
+ min-height: 200px;
+ grid-row: 7;
}
.sponsorPrevious {
- margin-top: 150px;
- font-size: 36px;
+ margin-top: 150px;
+ font-size: 36px;
}
//commit update
@media screen and (max-width: 1200px) {
- .sponsorContent {
- display: block;
- }
- .sponsorContentAnecdote {
- font-size: 20px;
- }
- .sponsorContentAnecdote {
- font-size: 18px;
- }
+ .sponsorContent {
+ display: block;
+ }
+ .sponsorContentAnecdote {
+ font-size: 20px;
+ }
+ .sponsorContentAnecdote {
+ font-size: 18px;
+ }
}
@media screen and (max-width: 800px) {
- .sponsorHackuci input {
- font-size: 16px;
- border-radius: 30px;
- padding: 10px 24px;
- }
-
- .sponsorAttendees {
- display: flex;
- flex-direction: column;
- align-items: center;
- justify-content: center;
- align-content: center;
- & img {
- width: 75px;
- }
- & span {
- font-size: 20px;
- padding-left: 10px;
- }
- }
-
- .sponsorContent {
- display: block;
- }
- .sponsorHackuci a {
- margin: 0 20px;
- }
- .sponsorStats {
- display: flex;
- justify-content: center;
- align-items: center;
- flex-direction: column;
- margin: 20px 0;
- }
- .sponsorStat {
- margin: 10px 12px;
- }
- .sponsorStat p {
- font-size: 40px;
- }
- .sponsorStat label {
- font-size: 16px;
- }
- .sponsorContentAnecdote {
- font-size: 15px;
- }
+ .sponsorHackuci input {
+ font-size: 16px;
+ border-radius: 30px;
+ padding: 10px 24px;
+ }
+
+ .sponsorAttendees {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ justify-content: center;
+ align-content: center;
+ & img {
+ width: 75px;
+ }
+ & span {
+ font-size: 20px;
+ padding-left: 10px;
+ }
+ }
+
+ .sponsorContent {
+ display: block;
+ }
+ .sponsorHackuci a {
+ margin: 0 20px;
+ }
+ .sponsorStats {
+ display: flex;
+ justify-content: center;
+ align-items: center;
+ flex-direction: column;
+ margin: 20px 0;
+ }
+ .sponsorStat {
+ margin: 10px 12px;
+ }
+ .sponsorStat p {
+ font-size: 40px;
+ }
+ .sponsorStat label {
+ font-size: 16px;
+ }
+ .sponsorContentAnecdote {
+ font-size: 15px;
+ }
}
diff --git a/apps/site/src/app/sponsors/page.tsx b/apps/site/src/app/sponsors/page.tsx
index 705f4a1..9a65d65 100644
--- a/apps/site/src/app/sponsors/page.tsx
+++ b/apps/site/src/app/sponsors/page.tsx
@@ -10,142 +10,142 @@ const title = "Events — Hack at UCI";
// TODO: write description for events page
const description = "";
export const metadata: Metadata = {
- title,
- description,
- openGraph: {
- title,
- description,
- },
+ title,
+ description,
+ openGraph: {
+ title,
+ description,
+ },
};
export default async function Home() {
- return (
-
-
+ return (
+
+
-
-
HackUCI Profile
-
-
-
-
-
-
500+ Attendees
-
-
-
-
-
92%
-
Submitted a Project
-
-
-
46%
-
First Time Hackers
-
-
-
-
-
-
- "I really enjoyed the experience of working on a coding project with
- other people that wanted to achieve the same goal! Though I was
- focused on coding the whole time, the environment itself was
- actually very peaceful and friendly so I felt at ease. I really
- appreciated that there were so many events that hackers could go to
- for de-stressing, like the Bob Ross painting or smash bros
- tournament."
-
-
- - Bianca, Hacker
-
-
-
-
- {" "}
- "Honestly, this was the best hackathon I've been to in a while.
- HackUCI had a great community, was well-run, and we saw good hacks,
- as well as built some connections with students for the future. I
- felt connected to more hackers than usual even though I hadn't met
- them before."
-
-
- - Lizzie, Twilio
-
-
+
+
HackUCI Profile
+
+
+
+
+
+
500+ Attendees
+
+
+
+
+
92%
+
Submitted a Project
+
+
+
46%
+
First Time Hackers
+
+
+
+
+
+
+ "I really enjoyed the experience of working on a coding project with
+ other people that wanted to achieve the same goal! Though I was
+ focused on coding the whole time, the environment itself was
+ actually very peaceful and friendly so I felt at ease. I really
+ appreciated that there were so many events that hackers could go to
+ for de-stressing, like the Bob Ross painting or smash bros
+ tournament."
+
+
+ - Bianca, Hacker
+
+
+
+
+ {" "}
+ "Honestly, this was the best hackathon I've been to in a while.
+ HackUCI had a great community, was well-run, and we saw good hacks,
+ as well as built some connections with students for the future. I
+ felt connected to more hackers than usual even though I hadn't met
+ them before."
+
+
+ - Lizzie, Twilio
+
+
-
-
ZotHacks Profile
-
-
-
-
-
-
60+ Attendees
-
-
-
-
-
90%
-
Submitted a Project
-
-
-
92%
-
Would Attend Another Hackathon
-
-
-
78%
-
First-Time Hackers
-
-
-
-
-
- {" "}
- "ZotHacks was my very first hackathon, and I really liked how the
- event leaned towards beginners. I loved how helpful and
- enthusiastic my mentor was in guiding our group and the
- collaborative and encouraging environment the other hackers and
- mentors helped create."
-
-
- - Cher, Hacker
-
-
-
-
-
- Our Past Sponsors
- {/* */}
-
-
- );
+
+
ZotHacks Profile
+
+
+
+
+
+
60+ Attendees
+
+
+
+
+
90%
+
Submitted a Project
+
+
+
92%
+
Would Attend Another Hackathon
+
+
+
78%
+
First-Time Hackers
+
+
+
+
+
+ {" "}
+ "ZotHacks was my very first hackathon, and I really liked how the
+ event leaned towards beginners. I loved how helpful and
+ enthusiastic my mentor was in guiding our group and the
+ collaborative and encouraging environment the other hackers and
+ mentors helped create."
+
+
+ - Cher, Hacker
+
+
+
+
+
+ Our Past Sponsors
+ {/* */}
+
+
+ );
}
diff --git a/apps/site/src/lib/common/components/Footer/Footer.module.scss b/apps/site/src/lib/common/components/Footer/Footer.module.scss
index 424a69e..866ce3d 100644
--- a/apps/site/src/lib/common/components/Footer/Footer.module.scss
+++ b/apps/site/src/lib/common/components/Footer/Footer.module.scss
@@ -1,24 +1,24 @@
@use "~@/lib/common/styles/hack-variables.scss" as variables;
.footer {
- width: 100%;
- padding: 16px 0;
- background: variables.$blue-gradient;
- display: flex;
- justify-content: space-evenly;
- align-items: center;
+ width: 100%;
+ padding: 16px 0;
+ background: variables.$blue-gradient;
+ display: flex;
+ justify-content: space-evenly;
+ align-items: center;
- a {
- width: 25px;
+ a {
+ width: 25px;
- img {
- width: 100%;
- }
- }
+ img {
+ width: 100%;
+ }
+ }
- @media screen and (min-width: 768px) {
- a {
- width: 36px;
- }
- }
+ @media screen and (min-width: 768px) {
+ a {
+ width: 36px;
+ }
+ }
}
diff --git a/apps/site/src/lib/common/components/Footer/Footer.tsx b/apps/site/src/lib/common/components/Footer/Footer.tsx
index 1ede620..8610812 100644
--- a/apps/site/src/lib/common/components/Footer/Footer.tsx
+++ b/apps/site/src/lib/common/components/Footer/Footer.tsx
@@ -8,25 +8,25 @@ import styles from "./Footer.module.scss";
import HackIcon from "../../assets/logo.svg";
interface FooterProps {
- style?: CSSProperties;
+ style?: CSSProperties;
}
const Footer = async ({ style }: FooterProps) => {
- const socials = await getSocials();
+ const socials = await getSocials();
- if (!socials) throw new Error();
+ if (!socials) throw new Error();
- return (
-
-
-
-
- {socials.map(({ _key, icon, link }) => (
-
-
-
- ))}
-
- );
+ return (
+
+
+
+
+ {socials.map(({ _key, icon, link }) => (
+
+
+
+ ))}
+
+ );
};
export default Footer;
diff --git a/apps/site/src/lib/common/components/Header/Header.module.scss b/apps/site/src/lib/common/components/Header/Header.module.scss
index 058d8ee..9b45876 100644
--- a/apps/site/src/lib/common/components/Header/Header.module.scss
+++ b/apps/site/src/lib/common/components/Header/Header.module.scss
@@ -1,30 +1,30 @@
@use "~@/lib/common/styles/hack-variables.scss" as variables;
.globalHeader {
- background: variables.$blue-gradient;
- color: white;
- height: 20rem;
+ background: variables.$blue-gradient;
+ color: white;
+ height: 20rem;
}
.headerImage {
- height: 100%;
- background-image: url("./hackshapes_header.png");
- background-repeat: no-repeat;
- background-size: 1920px auto;
- // keep laptop near center of header
- background-position: calc(50% - 400px + min(400px, 25vw)) 100%;
+ height: 100%;
+ background-image: url("./hackshapes_header.png");
+ background-repeat: no-repeat;
+ background-size: 1920px auto;
+ // keep laptop near center of header
+ background-position: calc(50% - 400px + min(400px, 25vw)) 100%;
}
.headerOverlay {
- height: 90%;
- display: flex;
- flex-direction: column;
- align-items: center;
- justify-content: center;
+ height: 90%;
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ justify-content: center;
- @media (orientation: portrait) {
- h1 {
- font-size: 3rem !important;
- }
- }
+ @media (orientation: portrait) {
+ h1 {
+ font-size: 3rem !important;
+ }
+ }
}
diff --git a/apps/site/src/lib/common/components/Header/Header.tsx b/apps/site/src/lib/common/components/Header/Header.tsx
index 3e6e370..b09645e 100644
--- a/apps/site/src/lib/common/components/Header/Header.tsx
+++ b/apps/site/src/lib/common/components/Header/Header.tsx
@@ -3,20 +3,20 @@ import type { ReactNode } from "react";
import styles from "./Header.module.scss";
interface HeaderProps {
- title: string;
- children?: ReactNode;
+ title: string;
+ children?: ReactNode;
}
const Header = ({ title, children }: HeaderProps) => {
- return (
-
-
-
-
{title}
- {children}
-
-
-
- );
+ return (
+
+
+
+
{title}
+ {children}
+
+
+
+ );
};
export default Header;
diff --git a/apps/site/src/lib/common/components/Icon/Icon.tsx b/apps/site/src/lib/common/components/Icon/Icon.tsx
index 1328eb4..4420841 100644
--- a/apps/site/src/lib/common/components/Icon/Icon.tsx
+++ b/apps/site/src/lib/common/components/Icon/Icon.tsx
@@ -10,39 +10,39 @@ import imageUrlBuilder from "@sanity/image-url";
const builder = imageUrlBuilder(client);
interface IconProps {
- icon: z.infer
;
- size?: string | number;
- color?: string;
+ icon: z.infer;
+ size?: string | number;
+ color?: string;
}
const Icon = ({
- icon: { logo, icon, customIcon },
- size = 24,
- color = "currentColor",
+ icon: { logo, icon, customIcon },
+ size = 24,
+ color = "currentColor",
}: IconProps) => {
- if (logo) {
- return (
-
-
-
- );
- }
- if (icon) {
- const Icon = lucideIcons[icon];
- return ;
- }
- if (customIcon) {
- ;
- }
- return <>>;
+ if (logo) {
+ return (
+
+
+
+ );
+ }
+ if (icon) {
+ const Icon = lucideIcons[icon];
+ return ;
+ }
+ if (customIcon) {
+ ;
+ }
+ return <>>;
};
export default Icon;
diff --git a/apps/site/src/lib/common/components/Nav/Nav.module.scss b/apps/site/src/lib/common/components/Nav/Nav.module.scss
index 9b31947..6d40c50 100644
--- a/apps/site/src/lib/common/components/Nav/Nav.module.scss
+++ b/apps/site/src/lib/common/components/Nav/Nav.module.scss
@@ -2,327 +2,327 @@
/* reset */
.header {
- button,
- p {
- all: unset;
- }
-
- padding: 16px;
- background: variables.$blue-gradient;
- display: flex;
- justify-content: space-between;
+ button,
+ p {
+ all: unset;
+ }
+
+ padding: 16px;
+ background: variables.$blue-gradient;
+ display: flex;
+ justify-content: space-between;
}
.root {
- position: relative;
- display: flex;
- justify-content: center;
- width: 100%;
- z-index: 1;
+ position: relative;
+ display: flex;
+ justify-content: center;
+ width: 100%;
+ z-index: 1;
}
.list {
- display: flex;
- justify-content: center;
- padding: 4px;
- border-radius: 6px;
- list-style: none;
- box-shadow: 0 2px 10px var(--blackA7);
- margin: 0;
+ display: flex;
+ justify-content: center;
+ padding: 4px;
+ border-radius: 6px;
+ list-style: none;
+ box-shadow: 0 2px 10px var(--blackA7);
+ margin: 0;
}
.trigger,
.link {
- outline: none;
- user-select: none;
- padding: 8px 32px;
- color: #fff;
- opacity: 0.8;
- transition: opacity 100ms ease-in-out;
-
- &:focus {
- opacity: 1;
- }
-
- &:hover {
- opacity: 1;
- }
+ outline: none;
+ user-select: none;
+ padding: 8px 32px;
+ color: #fff;
+ opacity: 0.8;
+ transition: opacity 100ms ease-in-out;
+
+ &:focus {
+ opacity: 1;
+ }
+
+ &:hover {
+ opacity: 1;
+ }
}
.trigger {
- display: flex;
- align-items: center;
- justify-content: space-between;
- gap: 2px;
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+ gap: 2px;
}
.link {
- display: block;
- text-decoration: none;
- font-size: 20px;
- font-weight: 400;
- line-height: 1;
+ display: block;
+ text-decoration: none;
+ font-size: 20px;
+ font-weight: 400;
+ line-height: 1;
}
.content {
- position: absolute;
- top: 0;
- left: 0;
- width: 100%;
- animation-duration: 250ms;
- animation-timing-function: ease;
-
- @media only screen and (min-width: 600px) {
- width: auto;
- }
-
- &[data-motion="from-start"] {
- animation-name: enterFromLeft;
- }
-
- &[data-motion="from-end"] {
- animation-name: enterFromRight;
- }
-
- &[data-motion="to-start"] {
- animation-name: exitToLeft;
- }
-
- &[data-motion="to-end"] {
- animation-name: exitToRight;
- }
+ position: absolute;
+ top: 0;
+ left: 0;
+ width: 100%;
+ animation-duration: 250ms;
+ animation-timing-function: ease;
+
+ @media only screen and (min-width: 600px) {
+ width: auto;
+ }
+
+ &[data-motion="from-start"] {
+ animation-name: enterFromLeft;
+ }
+
+ &[data-motion="from-end"] {
+ animation-name: enterFromRight;
+ }
+
+ &[data-motion="to-start"] {
+ animation-name: exitToLeft;
+ }
+
+ &[data-motion="to-end"] {
+ animation-name: exitToRight;
+ }
}
.indicator {
- display: flex;
- align-items: flex-end;
- justify-content: center;
- height: 10px;
- top: 100%;
- overflow: hidden;
- z-index: 1;
- transition: width, transform 250ms ease;
-
- &[data-state="visible"] {
- animation: fadeIn 200ms ease;
- }
-
- &[data-state="hidden"] {
- animation: fadeOut 200ms ease;
- }
+ display: flex;
+ align-items: flex-end;
+ justify-content: center;
+ height: 10px;
+ top: 100%;
+ overflow: hidden;
+ z-index: 1;
+ transition: width, transform 250ms ease;
+
+ &[data-state="visible"] {
+ animation: fadeIn 200ms ease;
+ }
+
+ &[data-state="hidden"] {
+ animation: fadeOut 200ms ease;
+ }
}
.viewport {
- position: relative;
- transform-origin: top center;
- margin-top: 10px;
- width: 100%;
- background-color: white;
- border-radius: 6px;
- overflow: hidden;
- box-shadow: hsl(206 22% 7% / 35%) 0px 10px 38px -10px,
- hsl(206 22% 7% / 20%) 0px 10px 20px -15px;
- height: var(--radix-navigation-menu-viewport-height);
- transition: width, height, 300ms ease;
-
- &[data-state="open"] {
- animation: scaleIn 200ms ease;
- }
-
- &[data-state="closed"] {
- animation: scaleOut 200ms ease;
- }
-
- @media only screen and (min-width: 600px) {
- width: var(--radix-navigation-menu-viewport-width);
- }
+ position: relative;
+ transform-origin: top center;
+ margin-top: 10px;
+ width: 100%;
+ background-color: white;
+ border-radius: 6px;
+ overflow: hidden;
+ box-shadow: hsl(206 22% 7% / 35%) 0px 10px 38px -10px,
+ hsl(206 22% 7% / 20%) 0px 10px 20px -15px;
+ height: var(--radix-navigation-menu-viewport-height);
+ transition: width, height, 300ms ease;
+
+ &[data-state="open"] {
+ animation: scaleIn 200ms ease;
+ }
+
+ &[data-state="closed"] {
+ animation: scaleOut 200ms ease;
+ }
+
+ @media only screen and (min-width: 600px) {
+ width: var(--radix-navigation-menu-viewport-width);
+ }
}
.items {
- display: grid;
- padding: 22px;
- margin: 0;
- column-gap: 10px;
- list-style: none;
-
- @media only screen and (min-width: 600px) {
- &.one {
- width: 500px;
- grid-template-columns: 0.75fr 1fr;
- }
- &.two {
- width: 600px;
- grid-auto-flow: column;
- grid-template-rows: repeat(3, 1fr);
- }
- }
+ display: grid;
+ padding: 22px;
+ margin: 0;
+ column-gap: 10px;
+ list-style: none;
+
+ @media only screen and (min-width: 600px) {
+ &.one {
+ width: 500px;
+ grid-template-columns: 0.75fr 1fr;
+ }
+ &.two {
+ width: 600px;
+ grid-auto-flow: column;
+ grid-template-rows: repeat(3, 1fr);
+ }
+ }
}
.listItemLink {
- display: block;
- outline: none;
- text-decoration: none;
- user-select: none;
- padding: 12px;
- border-radius: 6px;
- font-size: 15px;
- line-height: 1;
-
- &:focus {
- box-shadow: 0 0 0 2px var(--violet7);
- }
-
- &:hover {
- background-color: var(--mauve3);
- }
+ display: block;
+ outline: none;
+ text-decoration: none;
+ user-select: none;
+ padding: 12px;
+ border-radius: 6px;
+ font-size: 15px;
+ line-height: 1;
+
+ &:focus {
+ box-shadow: 0 0 0 2px var(--violet7);
+ }
+
+ &:hover {
+ background-color: var(--mauve3);
+ }
}
.listItemHeading {
- font-weight: 500;
- line-height: 1.2;
- margin-bottom: 5px;
- color: var(--violet12);
+ font-weight: 500;
+ line-height: 1.2;
+ margin-bottom: 5px;
+ color: var(--violet12);
}
.listItemText {
- color: var(--mauve11);
- line-height: 1.4;
- font-weight: initial;
+ color: var(--mauve11);
+ line-height: 1.4;
+ font-weight: initial;
}
.callout {
- display: flex;
- justify-content: flex-end;
- flex-direction: column;
- width: 100%;
- height: 100%;
- background: linear-gradient(135deg, var(--purple9) 0%, var(--indigo9) 100%);
- border-radius: 6px;
- padding: 25px;
- text-decoration: none;
- outline: none;
- user-select: none;
-
- &:focus {
- box-shadow: 0 0 0 2px var(--violet7);
- }
+ display: flex;
+ justify-content: flex-end;
+ flex-direction: column;
+ width: 100%;
+ height: 100%;
+ background: linear-gradient(135deg, var(--purple9) 0%, var(--indigo9) 100%);
+ border-radius: 6px;
+ padding: 25px;
+ text-decoration: none;
+ outline: none;
+ user-select: none;
+
+ &:focus {
+ box-shadow: 0 0 0 2px var(--violet7);
+ }
}
.calloutHeading {
- color: white;
- font-size: 18px;
- font-weight: 500;
- line-height: 1.2;
- margin-top: 16px;
- margin-bottom: 7px;
+ color: white;
+ font-size: 18px;
+ font-weight: 500;
+ line-height: 1.2;
+ margin-top: 16px;
+ margin-bottom: 7px;
}
.calloutText {
- color: var(--mauve4);
- font-size: 14px;
- line-height: 1.3;
+ color: var(--mauve4);
+ font-size: 14px;
+ line-height: 1.3;
}
.viewportPosition {
- position: absolute;
- display: flex;
- justify-content: center;
- width: 100%;
- top: 100%;
- left: 0;
- perspective: 2000px;
+ position: absolute;
+ display: flex;
+ justify-content: center;
+ width: 100%;
+ top: 100%;
+ left: 0;
+ perspective: 2000px;
}
.arrow {
- position: relative;
- top: 70%;
- background-color: white;
- width: 10px;
- height: 10px;
- transform: rotate(45deg);
- border-top-left-radius: 2px;
+ position: relative;
+ top: 70%;
+ background-color: white;
+ width: 10px;
+ height: 10px;
+ transform: rotate(45deg);
+ border-top-left-radius: 2px;
}
@keyframes enterFromRight {
- from {
- opacity: 0;
- transform: translateX(200px);
- }
- to {
- opacity: 1;
- transform: translateX(0);
- }
+ from {
+ opacity: 0;
+ transform: translateX(200px);
+ }
+ to {
+ opacity: 1;
+ transform: translateX(0);
+ }
}
@keyframes enterFromLeft {
- from {
- opacity: 0;
- transform: translateX(-200px);
- }
- to {
- opacity: 1;
- transform: translateX(0);
- }
+ from {
+ opacity: 0;
+ transform: translateX(-200px);
+ }
+ to {
+ opacity: 1;
+ transform: translateX(0);
+ }
}
@keyframes exitToRight {
- from {
- opacity: 1;
- transform: translateX(0);
- }
- to {
- opacity: 0;
- transform: translateX(200px);
- }
+ from {
+ opacity: 1;
+ transform: translateX(0);
+ }
+ to {
+ opacity: 0;
+ transform: translateX(200px);
+ }
}
@keyframes exitToLeft {
- from {
- opacity: 1;
- transform: translateX(0);
- }
- to {
- opacity: 0;
- transform: translateX(-200px);
- }
+ from {
+ opacity: 1;
+ transform: translateX(0);
+ }
+ to {
+ opacity: 0;
+ transform: translateX(-200px);
+ }
}
@keyframes scaleIn {
- from {
- opacity: 0;
- transform: rotateX(-30deg) scale(0.9);
- }
- to {
- opacity: 1;
- transform: rotateX(0deg) scale(1);
- }
+ from {
+ opacity: 0;
+ transform: rotateX(-30deg) scale(0.9);
+ }
+ to {
+ opacity: 1;
+ transform: rotateX(0deg) scale(1);
+ }
}
@keyframes scaleOut {
- from {
- opacity: 1;
- transform: rotateX(0deg) scale(1);
- }
- to {
- opacity: 0;
- transform: rotateX(-10deg) scale(0.95);
- }
+ from {
+ opacity: 1;
+ transform: rotateX(0deg) scale(1);
+ }
+ to {
+ opacity: 0;
+ transform: rotateX(-10deg) scale(0.95);
+ }
}
@keyframes fadeIn {
- from {
- opacity: 0;
- }
- to {
- opacity: 1;
- }
+ from {
+ opacity: 0;
+ }
+ to {
+ opacity: 1;
+ }
}
@keyframes fadeOut {
- from {
- opacity: 1;
- }
- to {
- opacity: 0;
- }
+ from {
+ opacity: 1;
+ }
+ to {
+ opacity: 0;
+ }
}
diff --git a/apps/site/src/lib/common/components/Nav/Nav.tsx b/apps/site/src/lib/common/components/Nav/Nav.tsx
index 405d5a6..4cb8965 100644
--- a/apps/site/src/lib/common/components/Nav/Nav.tsx
+++ b/apps/site/src/lib/common/components/Nav/Nav.tsx
@@ -12,115 +12,115 @@ import styles from "./Nav.module.scss";
import Logo from "../../assets/logo.svg";
const ListItem = forwardRef, ComponentPropsWithoutRef<"a">>(
- ({ className, children, title, ...props }, forwardedRef) => (
-
-
-
- {title}
- {children}
-
-
-
- )
+ ({ className, children, title, ...props }, forwardedRef) => (
+
+
+
+ {title}
+ {children}
+
+
+
+ )
);
ListItem.displayName = NavigationMenu.Link.displayName;
function AppNavbar() {
- return (
-
-
-
-
-
-
-
-
- About
-
-
+ return (
+
+
+
+
+
+
+
+
+ About
+
+
-
-
-
- Events
-
-
-
-
-
- Build high-quality, accessible design systems and web apps.
-
-
- A quick tutorial to get you up and running with Radix
- Primitives.
-
-
- Unstyled and compatible with any styling solution.
-
-
- Use CSS keyframes or any animation library of your choice.
-
-
- Tested in a range of browsers and assistive technologies.
-
-
- Radix Primitives releases and their changelogs.
-
-
-
-
+
+
+
+ Events
+
+
+
+
+
+ Build high-quality, accessible design systems and web apps.
+
+
+ A quick tutorial to get you up and running with Radix
+ Primitives.
+
+
+ Unstyled and compatible with any styling solution.
+
+
+ Use CSS keyframes or any animation library of your choice.
+
+
+ Tested in a range of browsers and assistive technologies.
+
+
+ Radix Primitives releases and their changelogs.
+
+
+
+
-
-
- Sponsors
-
-
+
+
+ Sponsors
+
+
-
-
- Recruitment
-
-
+
+
+ Recruitment
+
+
-
-
- Contact
-
-
+
+
+ Contact
+
+
-
-
-
-
+
+
+
+
-
-
-
-
-
- );
+
+
+
+
+
+ );
}
export default AppNavbar;
diff --git a/apps/site/src/lib/queries/getSocials.ts b/apps/site/src/lib/queries/getSocials.ts
index 29c32a9..3d91cf5 100644
--- a/apps/site/src/lib/queries/getSocials.ts
+++ b/apps/site/src/lib/queries/getSocials.ts
@@ -4,19 +4,19 @@ import { client } from "@/lib/sanity/sanityClient";
import { Icon } from "@/lib/sanity/types";
export const Socials = z
- .array(
- z.object({
- _key: z.string(),
- icon: Icon,
- platform: z.string(),
- label: z.string().optional(),
- link: z.string(),
- })
- )
- .nullable();
+ .array(
+ z.object({
+ _key: z.string(),
+ icon: Icon,
+ platform: z.string(),
+ label: z.string().optional(),
+ link: z.string(),
+ })
+ )
+ .nullable();
export const getSocials = cache(async () => {
- return await client
- .fetch("*[_id == 'socials'][0].socials")
- .then((result) => Socials.parse(result));
+ return await client
+ .fetch("*[_id == 'socials'][0].socials")
+ .then((result) => Socials.parse(result));
});
diff --git a/apps/site/src/lib/sanity/sanityClient.ts b/apps/site/src/lib/sanity/sanityClient.ts
index f7c752f..f628513 100644
--- a/apps/site/src/lib/sanity/sanityClient.ts
+++ b/apps/site/src/lib/sanity/sanityClient.ts
@@ -3,17 +3,17 @@ import { createClient } from "@sanity/client";
const NEXT_PUBLIC_SANITY_PROJECT_ID = process.env.NEXT_PUBLIC_SANITY_PROJECT_ID;
const NEXT_PUBLIC_SANITY_DATASET = process.env.NEXT_PUBLIC_SANITY_DATASET;
if (!NEXT_PUBLIC_SANITY_PROJECT_ID)
- throw new Error(
- "`NEXT_PUBLIC_SANITY_PROJECT_ID` is a required env variable."
- );
+ throw new Error(
+ "`NEXT_PUBLIC_SANITY_PROJECT_ID` is a required env variable."
+ );
if (!NEXT_PUBLIC_SANITY_DATASET)
- throw new Error("`NEXT_PUBLIC_SANITY_DATASET` is a required env variable.");
+ throw new Error("`NEXT_PUBLIC_SANITY_DATASET` is a required env variable.");
const client = createClient({
- projectId: NEXT_PUBLIC_SANITY_PROJECT_ID,
- dataset: NEXT_PUBLIC_SANITY_DATASET,
- apiVersion: "2023-06-06",
- useCdn: process.env.NODE_ENV === "production",
+ projectId: NEXT_PUBLIC_SANITY_PROJECT_ID,
+ dataset: NEXT_PUBLIC_SANITY_DATASET,
+ apiVersion: "2023-06-06",
+ useCdn: process.env.NODE_ENV === "production",
});
export { client };
diff --git a/apps/site/src/lib/sanity/sanityServer.ts b/apps/site/src/lib/sanity/sanityServer.ts
index fe0d66e..f197afe 100644
--- a/apps/site/src/lib/sanity/sanityServer.ts
+++ b/apps/site/src/lib/sanity/sanityServer.ts
@@ -6,20 +6,20 @@ const NEXT_PUBLIC_SANITY_PROJECT_ID = process.env.NEXT_PUBLIC_SANITY_PROJECT_ID;
const NEXT_PUBLIC_SANITY_DATASET = process.env.NEXT_PUBLIC_SANITY_DATASET;
const SANITY_TOKEN = process.env.SANITY_TOKEN;
if (!NEXT_PUBLIC_SANITY_PROJECT_ID)
- throw new Error(
- "`NEXT_PUBLIC_SANITY_PROJECT_ID` is a required env variable."
- );
+ throw new Error(
+ "`NEXT_PUBLIC_SANITY_PROJECT_ID` is a required env variable."
+ );
if (!NEXT_PUBLIC_SANITY_DATASET)
- throw new Error("`NEXT_PUBLIC_SANITY_DATASET` is a required env variable.");
+ throw new Error("`NEXT_PUBLIC_SANITY_DATASET` is a required env variable.");
if (!SANITY_TOKEN)
- throw new Error("`SANITY_TOKEN` is a required env variable.");
+ throw new Error("`SANITY_TOKEN` is a required env variable.");
const client = createClient({
- projectId: NEXT_PUBLIC_SANITY_PROJECT_ID,
- dataset: NEXT_PUBLIC_SANITY_DATASET,
- apiVersion: "2023-06-06",
- token: SANITY_TOKEN,
- useCdn: process.env.NODE_ENV === "production",
+ projectId: NEXT_PUBLIC_SANITY_PROJECT_ID,
+ dataset: NEXT_PUBLIC_SANITY_DATASET,
+ apiVersion: "2023-06-06",
+ token: SANITY_TOKEN,
+ useCdn: process.env.NODE_ENV === "production",
});
export { client };
diff --git a/apps/site/src/lib/sanity/types.ts b/apps/site/src/lib/sanity/types.ts
index e3d3541..6d9a8ee 100644
--- a/apps/site/src/lib/sanity/types.ts
+++ b/apps/site/src/lib/sanity/types.ts
@@ -1,40 +1,40 @@
import { z } from "zod";
export const SanityDocument = z.object({
- _id: z.string(),
- _createdAt: z.string().datetime(),
- _updatedAt: z.string().datetime(),
- _rev: z.string(),
+ _id: z.string(),
+ _createdAt: z.string().datetime(),
+ _updatedAt: z.string().datetime(),
+ _rev: z.string(),
});
export const SanityReference = z.object({
- _type: z.literal("reference"),
- _ref: z.string(),
+ _type: z.literal("reference"),
+ _ref: z.string(),
});
export const SanityImageReference = z.object({
- _type: z.literal("image"),
- asset: SanityReference,
+ _type: z.literal("image"),
+ asset: SanityReference,
});
import * as simpleIcons from "simple-icons";
import { icons as lucideIcons } from "lucide";
const SimpleIconKeys = z.custom(
- (val) => typeof val === "string" && Object.keys(simpleIcons).includes(val)
+ (val) => typeof val === "string" && Object.keys(simpleIcons).includes(val)
);
const LucideIconKeys = z.custom(
- (val) => typeof val === "string" && Object.keys(lucideIcons).includes(val)
+ (val) => typeof val === "string" && Object.keys(lucideIcons).includes(val)
);
export const Icon = z
- .object({
- _type: z.literal("icon"),
- logo: SimpleIconKeys.optional(),
- icon: LucideIconKeys.optional(),
- customIcon: SanityImageReference.optional(),
- })
- .refine(
- ({ logo, icon }) => !(logo && icon),
- "logo and icon fields are mutually exclusive."
- );
+ .object({
+ _type: z.literal("icon"),
+ logo: SimpleIconKeys.optional(),
+ icon: LucideIconKeys.optional(),
+ customIcon: SanityImageReference.optional(),
+ })
+ .refine(
+ ({ logo, icon }) => !(logo && icon),
+ "logo and icon fields are mutually exclusive."
+ );
diff --git a/apps/site/tsconfig.json b/apps/site/tsconfig.json
index 0c7555f..e32e100 100644
--- a/apps/site/tsconfig.json
+++ b/apps/site/tsconfig.json
@@ -1,28 +1,28 @@
{
- "compilerOptions": {
- "target": "es5",
- "lib": ["dom", "dom.iterable", "esnext"],
- "allowJs": true,
- "skipLibCheck": true,
- "strict": true,
- "forceConsistentCasingInFileNames": true,
- "noEmit": true,
- "esModuleInterop": true,
- "module": "esnext",
- "moduleResolution": "node",
- "resolveJsonModule": true,
- "isolatedModules": true,
- "jsx": "preserve",
- "incremental": true,
- "plugins": [
- {
- "name": "next"
- }
- ],
- "paths": {
- "@/*": ["./src/*"]
- }
- },
- "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
- "exclude": ["node_modules"]
+ "compilerOptions": {
+ "target": "es5",
+ "lib": ["dom", "dom.iterable", "esnext"],
+ "allowJs": true,
+ "skipLibCheck": true,
+ "strict": true,
+ "forceConsistentCasingInFileNames": true,
+ "noEmit": true,
+ "esModuleInterop": true,
+ "module": "esnext",
+ "moduleResolution": "node",
+ "resolveJsonModule": true,
+ "isolatedModules": true,
+ "jsx": "preserve",
+ "incremental": true,
+ "plugins": [
+ {
+ "name": "next"
+ }
+ ],
+ "paths": {
+ "@/*": ["./src/*"]
+ }
+ },
+ "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
+ "exclude": ["node_modules"]
}
diff --git a/apps/site/turbo.json b/apps/site/turbo.json
index abe10ad..4aa5028 100644
--- a/apps/site/turbo.json
+++ b/apps/site/turbo.json
@@ -1,8 +1,8 @@
{
- "extends": ["//"],
- "pipeline": {
- "build": {
- "outputs": [".vercel/**", ".next/**", "!.next/cache/**"]
- }
- }
+ "extends": ["//"],
+ "pipeline": {
+ "build": {
+ "outputs": [".vercel/**", ".next/**", "!.next/cache/**"]
+ }
+ }
}
diff --git a/apps/studio/.eslintrc b/apps/studio/.eslintrc
index eec603e..68407f6 100644
--- a/apps/studio/.eslintrc
+++ b/apps/studio/.eslintrc
@@ -1,6 +1,6 @@
{
- "extends": [
- "@sanity/eslint-config-studio",
- "plugin:sanity-studio/recommended"
- ]
+ "extends": [
+ "@sanity/eslint-config-studio",
+ "plugin:sanity-studio/recommended"
+ ]
}
diff --git a/apps/studio/package.json b/apps/studio/package.json
index 39421ce..31530a2 100644
--- a/apps/studio/package.json
+++ b/apps/studio/package.json
@@ -1,40 +1,40 @@
{
- "name": "studio",
- "version": "1.0.0",
- "main": "package.json",
- "scripts": {
- "dev": "sanity dev",
- "start": "sanity start",
- "build": "sanity build",
- "deploy": "sanity deploy",
- "deploy-graphql": "sanity graphql deploy",
- "lint": "eslint .",
- "format:write": "prettier --write .",
- "format:check": "prettier --check ."
- },
- "keywords": [
- "sanity"
- ],
- "dependencies": {
- "@icons-pack/react-simple-icons": "^8.0.1",
- "@sanity/icons": "^2.3.1",
- "@sanity/ui": "^1.6.0",
- "@sanity/vision": "^3.11.5",
- "countries-and-timezones": "^3.4.1",
- "react": "^18.2.0",
- "react-dom": "^18.2.0",
- "react-is": "^18.2.0",
- "sanity": "^3.12.0",
- "styled-components": "^5.3.9",
- "title-case": "^3.0.3"
- },
- "devDependencies": {
- "@sanity/eslint-config-studio": "^2.0.1",
- "@types/react": "^18.0.25",
- "@types/styled-components": "^5.1.26",
- "eslint": "^8.6.0",
- "eslint-plugin-sanity-studio": "0.4.0",
- "prettier": "^2.8.8",
- "typescript": "^4.9.5"
- }
+ "name": "studio",
+ "version": "1.0.0",
+ "main": "package.json",
+ "scripts": {
+ "dev": "sanity dev",
+ "start": "sanity start",
+ "build": "sanity build",
+ "deploy": "sanity deploy",
+ "deploy-graphql": "sanity graphql deploy",
+ "lint": "eslint .",
+ "format:write": "prettier --write .",
+ "format:check": "prettier --check ."
+ },
+ "keywords": [
+ "sanity"
+ ],
+ "dependencies": {
+ "@icons-pack/react-simple-icons": "^8.0.1",
+ "@sanity/icons": "^2.3.1",
+ "@sanity/ui": "^1.6.0",
+ "@sanity/vision": "^3.11.5",
+ "countries-and-timezones": "^3.4.1",
+ "react": "^18.2.0",
+ "react-dom": "^18.2.0",
+ "react-is": "^18.2.0",
+ "sanity": "^3.12.0",
+ "styled-components": "^5.3.9",
+ "title-case": "^3.0.3"
+ },
+ "devDependencies": {
+ "@sanity/eslint-config-studio": "^2.0.1",
+ "@types/react": "^18.0.25",
+ "@types/styled-components": "^5.1.26",
+ "eslint": "^8.6.0",
+ "eslint-plugin-sanity-studio": "0.4.0",
+ "prettier": "^2.8.8",
+ "typescript": "^4.9.5"
+ }
}
diff --git a/apps/studio/sanity.cli.ts b/apps/studio/sanity.cli.ts
index d4f9c9c..5e76ad5 100644
--- a/apps/studio/sanity.cli.ts
+++ b/apps/studio/sanity.cli.ts
@@ -1,8 +1,8 @@
import { defineCliConfig } from "sanity/cli";
export default defineCliConfig({
- api: {
- projectId: "ue554f0d",
- dataset: "production",
- },
+ api: {
+ projectId: "ue554f0d",
+ dataset: "production",
+ },
});
diff --git a/apps/studio/sanity.config.ts b/apps/studio/sanity.config.ts
index 956244a..c8ba097 100644
--- a/apps/studio/sanity.config.ts
+++ b/apps/studio/sanity.config.ts
@@ -6,44 +6,44 @@ import { schemaTypes } from "./schemas";
import { CogIcon, EarthAmericasIcon } from "@sanity/icons";
export default defineConfig({
- name: "default",
- title: "hack.ics.uci.edu",
- theme,
+ name: "default",
+ title: "hack.ics.uci.edu",
+ theme,
- projectId: "ue554f0d",
- dataset: "production",
+ projectId: "ue554f0d",
+ dataset: "production",
- plugins: [
- deskTool({
- structure: (S) =>
- S.list()
- .title("Content")
- .items([
- S.listItem()
- .title("Site Settings")
- .icon(CogIcon)
- .child(
- S.list()
- .title("Site Settings")
- .items([
- S.listItem()
- .title("Socials")
- .icon(EarthAmericasIcon)
- .child(
- S.document().schemaType("socials").documentId("socials")
- ),
- ])
- ),
- S.divider(),
- ...S.documentTypeListItems().filter(
- (listItem) => !["socials"].includes(listItem.getId()!)
- ),
- ]),
- }),
- visionTool(),
- ],
+ plugins: [
+ deskTool({
+ structure: (S) =>
+ S.list()
+ .title("Content")
+ .items([
+ S.listItem()
+ .title("Site Settings")
+ .icon(CogIcon)
+ .child(
+ S.list()
+ .title("Site Settings")
+ .items([
+ S.listItem()
+ .title("Socials")
+ .icon(EarthAmericasIcon)
+ .child(
+ S.document().schemaType("socials").documentId("socials")
+ ),
+ ])
+ ),
+ S.divider(),
+ ...S.documentTypeListItems().filter(
+ (listItem) => !["socials"].includes(listItem.getId()!)
+ ),
+ ]),
+ }),
+ visionTool(),
+ ],
- schema: {
- types: schemaTypes,
- },
+ schema: {
+ types: schemaTypes,
+ },
});
diff --git a/apps/studio/schemas/boardYear.ts b/apps/studio/schemas/boardYear.ts
index 83d484c..022a4a0 100644
--- a/apps/studio/schemas/boardYear.ts
+++ b/apps/studio/schemas/boardYear.ts
@@ -2,72 +2,72 @@ import { UsersIcon } from "@sanity/icons";
import { defineField, defineType, defineArrayMember } from "sanity";
const personSearch = defineType({
- name: "personSearch",
- type: "object",
- fields: [
- defineField({
- name: "person",
- type: "reference",
- title: "Person",
- to: {
- type: "person",
- },
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "position",
- type: "string",
- title: "Position",
- validation: (Rule) => Rule.required(),
- }),
- ],
- preview: {
- select: {
- title: "person.name",
- subtitle: "position",
- media: "person.profilePic",
- },
- },
+ name: "personSearch",
+ type: "object",
+ fields: [
+ defineField({
+ name: "person",
+ type: "reference",
+ title: "Person",
+ to: {
+ type: "person",
+ },
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "position",
+ type: "string",
+ title: "Position",
+ validation: (Rule) => Rule.required(),
+ }),
+ ],
+ preview: {
+ select: {
+ title: "person.name",
+ subtitle: "position",
+ media: "person.profilePic",
+ },
+ },
});
const nameTitleAssoc: { [dept: string]: string } = {
- corporate: "Corporate Organizers",
- logistics: "Logistics Organizers",
- marketing: "Marketing Organizers",
- tech: "Tech Organizers",
+ corporate: "Corporate Organizers",
+ logistics: "Logistics Organizers",
+ marketing: "Marketing Organizers",
+ tech: "Tech Organizers",
};
export default defineType({
- name: "boardYear",
- icon: UsersIcon,
- type: "document",
- title: "Board Years",
- fields: [
- defineField({
- name: "year",
- type: "number",
- title: "Academic Year",
- validation: (Rule) => Rule.required(),
- }),
- ...Object.entries(nameTitleAssoc).map(([key, title]) =>
- defineField({
- name: key,
- type: "array",
- title: title,
- of: [defineArrayMember(personSearch)],
- validation: (Rule) => Rule.required(),
- })
- ),
- ],
- initialValue: {
- year: new Date().getFullYear(),
- },
- preview: {
- select: {
- title: "year",
- },
- prepare({ title }) {
- return { title: `${title} - ${title + 1}` };
- },
- },
+ name: "boardYear",
+ icon: UsersIcon,
+ type: "document",
+ title: "Board Years",
+ fields: [
+ defineField({
+ name: "year",
+ type: "number",
+ title: "Academic Year",
+ validation: (Rule) => Rule.required(),
+ }),
+ ...Object.entries(nameTitleAssoc).map(([key, title]) =>
+ defineField({
+ name: key,
+ type: "array",
+ title: title,
+ of: [defineArrayMember(personSearch)],
+ validation: (Rule) => Rule.required(),
+ })
+ ),
+ ],
+ initialValue: {
+ year: new Date().getFullYear(),
+ },
+ preview: {
+ select: {
+ title: "year",
+ },
+ prepare({ title }) {
+ return { title: `${title} - ${title + 1}` };
+ },
+ },
});
diff --git a/apps/studio/schemas/event.ts b/apps/studio/schemas/event.ts
index ac792c2..35a9801 100644
--- a/apps/studio/schemas/event.ts
+++ b/apps/studio/schemas/event.ts
@@ -2,93 +2,93 @@ import { defineField, defineType } from "sanity";
import { CalendarIcon } from "@sanity/icons";
export default defineType({
- name: "event",
- title: "Events",
- icon: CalendarIcon,
- type: "document",
- fields: [
- defineField({
- name: "title",
- title: "Title",
- type: "string",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "cover",
- title: "Cover",
- description:
- "Should be at least 1200 x 630, with an aspect ratio of 1.9:1.",
- type: "image",
- fields: [
- {
- name: "alt",
- title: "Alternative Text",
- description:
- 'Describe what\'s in the image, rather than it\'s purpose. For example, instead of writing, "A poster for ICS fair", write "an open red and white carnival tent that contains details about ICS fair inside".',
- type: "string",
- validation: (Rule) => Rule.required(),
- },
- ],
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "timeRange",
- title: "Time Range",
- type: "timeRange",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "description",
- title: "Description",
- type: "text",
- validation: (Rule) => [
- Rule.required(),
- Rule.regex(/\n\n/, { invert: true }).warning(
- "Double newlines should not be used for stylistic reasons. Content will be properly styled when displayed."
- ),
- ],
- }),
- defineField({
- name: "location",
- title: "Location",
- type: "string",
- }),
- defineField({
- name: "rsvp",
- title: "RSVP",
- type: "url",
- }),
- ],
- preview: {
- select: {
- title: "title",
- media: "cover",
- start: "timeRange.start",
- end: "timeRange.end",
- },
- prepare({ title, media, start, end }) {
- const dateTimeFormat = new Intl.DateTimeFormat("en", {
- timeZone: "UTC",
- dateStyle: "medium",
- timeStyle: "short",
- });
+ name: "event",
+ title: "Events",
+ icon: CalendarIcon,
+ type: "document",
+ fields: [
+ defineField({
+ name: "title",
+ title: "Title",
+ type: "string",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "cover",
+ title: "Cover",
+ description:
+ "Should be at least 1200 x 630, with an aspect ratio of 1.9:1.",
+ type: "image",
+ fields: [
+ {
+ name: "alt",
+ title: "Alternative Text",
+ description:
+ 'Describe what\'s in the image, rather than it\'s purpose. For example, instead of writing, "A poster for ICS fair", write "an open red and white carnival tent that contains details about ICS fair inside".',
+ type: "string",
+ validation: (Rule) => Rule.required(),
+ },
+ ],
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "timeRange",
+ title: "Time Range",
+ type: "timeRange",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "description",
+ title: "Description",
+ type: "text",
+ validation: (Rule) => [
+ Rule.required(),
+ Rule.regex(/\n\n/, { invert: true }).warning(
+ "Double newlines should not be used for stylistic reasons. Content will be properly styled when displayed."
+ ),
+ ],
+ }),
+ defineField({
+ name: "location",
+ title: "Location",
+ type: "string",
+ }),
+ defineField({
+ name: "rsvp",
+ title: "RSVP",
+ type: "url",
+ }),
+ ],
+ preview: {
+ select: {
+ title: "title",
+ media: "cover",
+ start: "timeRange.start",
+ end: "timeRange.end",
+ },
+ prepare({ title, media, start, end }) {
+ const dateTimeFormat = new Intl.DateTimeFormat("en", {
+ timeZone: "UTC",
+ dateStyle: "medium",
+ timeStyle: "short",
+ });
- const time = end
- ? dateTimeFormat.formatRange(new Date(start), new Date(end))
- : dateTimeFormat.format(new Date(start));
+ const time = end
+ ? dateTimeFormat.formatRange(new Date(start), new Date(end))
+ : dateTimeFormat.format(new Date(start));
- return {
- title,
- media,
- subtitle: time,
- };
- },
- },
- orderings: [
- {
- title: "Start Time, Desc",
- name: "startTimeDesc",
- by: [{ field: "timeRange.start", direction: "desc" }],
- },
- ],
+ return {
+ title,
+ media,
+ subtitle: time,
+ };
+ },
+ },
+ orderings: [
+ {
+ title: "Start Time, Desc",
+ name: "startTimeDesc",
+ by: [{ field: "timeRange.start", direction: "desc" }],
+ },
+ ],
});
diff --git a/apps/studio/schemas/icon.tsx b/apps/studio/schemas/icon.tsx
index aa01c02..f2a6e94 100644
--- a/apps/studio/schemas/icon.tsx
+++ b/apps/studio/schemas/icon.tsx
@@ -4,122 +4,122 @@ import * as simpleIcons from "simple-icons";
import { createElement, icons as lucideIcons } from "lucide";
const logos = Object.entries(simpleIcons).map(([key, { title, path }]) => ({
- title: title,
- value: key,
- svg: (
-
-
-
- ),
+ title: title,
+ value: key,
+ svg: (
+
+
+
+ ),
}));
const icons = Object.entries(lucideIcons).map(([key, icon]) => {
- // Iterating through all exports of `lucide-react` should return an object where all values are type `LucideIcon`.
- // This also throws an error with for some reason.
- // `lucide-react` exports also include aliases, which is undesirable.
+ // Iterating through all exports of `lucide-react` should return an object where all values are type `LucideIcon`.
+ // This also throws an error with for some reason.
+ // `lucide-react` exports also include aliases, which is undesirable.
- return {
- title: titleCase(key),
- value: key,
- svg: (
-
- ),
- };
+ return {
+ title: titleCase(key),
+ value: key,
+ svg: (
+
+ ),
+ };
});
const getIcon = (id: string) => {
- return icons.find(({ value }) => value === id)?.svg;
+ return icons.find(({ value }) => value === id)?.svg;
};
const getLogo = (id: string) => {
- return logos.find(({ value }) => value === id)?.svg;
+ return logos.find(({ value }) => value === id)?.svg;
};
// Resuable preview function that can be used in previews of documents that use an `icon` object.
// Refer to the list preview function in `socials.ts` for example usage.
export const previewIcon = (iconObject: {
- logo: string;
- icon: string;
- customIcon: { _type: "image"; asset: Reference };
+ logo: string;
+ icon: string;
+ customIcon: { _type: "image"; asset: Reference };
}): any => {
- const { logo, icon, customIcon } = iconObject;
- // Sanity's prepare preview function doesn't accept a Sanity image object even though it's redered correctly.
- // Forcing the return type of this function to be any to get around this for now.
- // This probably isn't an optimal solution and might be an upstream issue?
- if (customIcon) return customIcon;
- if (logo) return getLogo(logo);
- if (icon) return getIcon(icon);
- return undefined;
+ const { logo, icon, customIcon } = iconObject;
+ // Sanity's prepare preview function doesn't accept a Sanity image object even though it's redered correctly.
+ // Forcing the return type of this function to be any to get around this for now.
+ // This probably isn't an optimal solution and might be an upstream issue?
+ if (customIcon) return customIcon;
+ if (logo) return getLogo(logo);
+ if (icon) return getIcon(icon);
+ return undefined;
};
export default defineType({
- name: "icon",
- title: "Icon",
- type: "object",
- fields: [
- defineField({
- name: "logo",
- title: "Logo",
- type: "string",
- options: {
- list: logos,
- },
- }),
- defineField({
- name: "icon",
- title: "Icon",
- description: "Explore available icons at https://lucide.dev/icons.",
- type: "string",
- options: {
- list: icons,
- },
- }),
- defineField({
- name: "customIcon",
- title: "Custom Icon",
- description:
- '.svg files are preferred. This field takes precedent over the "Logo" and "Icon" fields.',
- type: "image",
- validation: (Rule) =>
- Rule.custom(async (image, context) => {
- if (
- typeof image === "undefined" ||
- typeof image.asset === "undefined"
- )
- return true;
+ name: "icon",
+ title: "Icon",
+ type: "object",
+ fields: [
+ defineField({
+ name: "logo",
+ title: "Logo",
+ type: "string",
+ options: {
+ list: logos,
+ },
+ }),
+ defineField({
+ name: "icon",
+ title: "Icon",
+ description: "Explore available icons at https://lucide.dev/icons.",
+ type: "string",
+ options: {
+ list: icons,
+ },
+ }),
+ defineField({
+ name: "customIcon",
+ title: "Custom Icon",
+ description:
+ '.svg files are preferred. This field takes precedent over the "Logo" and "Icon" fields.',
+ type: "image",
+ validation: (Rule) =>
+ Rule.custom(async (image, context) => {
+ if (
+ typeof image === "undefined" ||
+ typeof image.asset === "undefined"
+ )
+ return true;
- const client = context.getClient({ apiVersion: "2023-06-05" });
- const extension: string | undefined = (
- await client.getDocument(image.asset._ref)
- )?.extension;
+ const client = context.getClient({ apiVersion: "2023-06-05" });
+ const extension: string | undefined = (
+ await client.getDocument(image.asset._ref)
+ )?.extension;
- if (!extension) return true;
+ if (!extension) return true;
- return extension === "svg" ? true : ".svg files are preferred.";
- }).warning(),
- }),
- ],
- options: {
- collapsible: true,
- collapsed: true,
- },
- validation: (Rule) => [
- // `logo` and `icon` fields are mutually exclusive.
- Rule.custom((object) => {
- if (typeof object === "undefined") return true;
+ return extension === "svg" ? true : ".svg files are preferred.";
+ }).warning(),
+ }),
+ ],
+ options: {
+ collapsible: true,
+ collapsed: true,
+ },
+ validation: (Rule) => [
+ // `logo` and `icon` fields are mutually exclusive.
+ Rule.custom((object) => {
+ if (typeof object === "undefined") return true;
- return object.logo && object.icon
- ? '"Logo" and "Icon" fields can not be selected at the same time.'
- : true;
- }).error(),
- ],
+ return object.logo && object.icon
+ ? '"Logo" and "Icon" fields can not be selected at the same time.'
+ : true;
+ }).error(),
+ ],
});
diff --git a/apps/studio/schemas/person.ts b/apps/studio/schemas/person.ts
index 4d02813..08cf80f 100644
--- a/apps/studio/schemas/person.ts
+++ b/apps/studio/schemas/person.ts
@@ -3,116 +3,116 @@ import { SiLinkedin } from "@icons-pack/react-simple-icons";
import { defineField, defineType, defineArrayMember } from "sanity";
enum Socials {
- LinkedIn = "LinkedIn",
- PersonalWebsite = "Personal Website",
- Other = "Other Platform",
+ LinkedIn = "LinkedIn",
+ PersonalWebsite = "Personal Website",
+ Other = "Other Platform",
}
export default defineType({
- name: "person",
- icon: UserIcon,
- title: "People",
- type: "document",
- fields: [
- defineField({
- name: "name",
- title: "Name",
- type: "string",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "pronouns",
- title: "Pronouns",
- type: "string",
- }),
- defineField({
- name: "email",
- title: "Email",
- type: "email",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "socials",
- title: "Socials",
- type: "array",
- of: [
- defineArrayMember({
- type: "object",
- fields: [
- defineField({
- name: "platform",
- title: "Platform",
- type: "string",
- options: {
- list: [
- { title: Socials.LinkedIn, value: "linkedin" },
- { title: Socials.PersonalWebsite, value: "site" },
- ],
- },
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "label",
- title: "Label",
- description:
- "Primary identifier of platform (i.e. Username). Include a prefix character (@, ~, etc.) if used by brand.",
- type: "string",
- }),
- defineField({
- name: "link",
- title: "Link",
- type: "url",
- validation: (Rule) => Rule.required(),
- }),
- ],
- preview: {
- select: {
- platform: "platform",
- label: "label",
- link: "link",
- },
- prepare({ platform, label, link }) {
- let icon, title;
- switch (platform) {
- case "linkedin":
- title = Socials.LinkedIn;
- icon = SiLinkedin;
- break;
- case "site":
- title = Socials.PersonalWebsite;
- icon = LinkIcon;
- break;
- default:
- title = Socials.Other;
- icon = EarthGlobeIcon;
- break;
- }
- return {
- title,
- icon,
- subtitle: label ?? link,
- };
- },
- },
- }),
- ],
- validation: (Rule) => Rule.unique(),
- }),
- defineField({
- name: "profilePic",
- title: "Profile Picture",
- description: "Images should preferably have a 1:1 aspect ratio.",
- type: "image",
- options: {
- hotspot: true,
- },
- }),
- ],
- preview: {
- select: {
- title: "name",
- subtitle: "email",
- media: "profilePic",
- },
- },
+ name: "person",
+ icon: UserIcon,
+ title: "People",
+ type: "document",
+ fields: [
+ defineField({
+ name: "name",
+ title: "Name",
+ type: "string",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "pronouns",
+ title: "Pronouns",
+ type: "string",
+ }),
+ defineField({
+ name: "email",
+ title: "Email",
+ type: "email",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "socials",
+ title: "Socials",
+ type: "array",
+ of: [
+ defineArrayMember({
+ type: "object",
+ fields: [
+ defineField({
+ name: "platform",
+ title: "Platform",
+ type: "string",
+ options: {
+ list: [
+ { title: Socials.LinkedIn, value: "linkedin" },
+ { title: Socials.PersonalWebsite, value: "site" },
+ ],
+ },
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "label",
+ title: "Label",
+ description:
+ "Primary identifier of platform (i.e. Username). Include a prefix character (@, ~, etc.) if used by brand.",
+ type: "string",
+ }),
+ defineField({
+ name: "link",
+ title: "Link",
+ type: "url",
+ validation: (Rule) => Rule.required(),
+ }),
+ ],
+ preview: {
+ select: {
+ platform: "platform",
+ label: "label",
+ link: "link",
+ },
+ prepare({ platform, label, link }) {
+ let icon, title;
+ switch (platform) {
+ case "linkedin":
+ title = Socials.LinkedIn;
+ icon = SiLinkedin;
+ break;
+ case "site":
+ title = Socials.PersonalWebsite;
+ icon = LinkIcon;
+ break;
+ default:
+ title = Socials.Other;
+ icon = EarthGlobeIcon;
+ break;
+ }
+ return {
+ title,
+ icon,
+ subtitle: label ?? link,
+ };
+ },
+ },
+ }),
+ ],
+ validation: (Rule) => Rule.unique(),
+ }),
+ defineField({
+ name: "profilePic",
+ title: "Profile Picture",
+ description: "Images should preferably have a 1:1 aspect ratio.",
+ type: "image",
+ options: {
+ hotspot: true,
+ },
+ }),
+ ],
+ preview: {
+ select: {
+ title: "name",
+ subtitle: "email",
+ media: "profilePic",
+ },
+ },
});
diff --git a/apps/studio/schemas/socials.ts b/apps/studio/schemas/socials.ts
index 662ab87..cb416e8 100644
--- a/apps/studio/schemas/socials.ts
+++ b/apps/studio/schemas/socials.ts
@@ -2,67 +2,67 @@ import { defineField, defineType, defineArrayMember } from "sanity";
import { previewIcon } from "./icon";
export default defineType({
- name: "socials",
- title: "Socials",
- type: "document",
- fields: [
- defineField({
- name: "socials",
- title: "Socials",
- type: "array",
- of: [
- defineArrayMember({
- type: "object",
- fields: [
- defineField({
- name: "icon",
- title: "Icon",
- type: "icon",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "platform",
- title: "Platform",
- type: "string",
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "label",
- title: "Label",
- description:
- "Primary identifier of platform (i.e. Username). Include a prefix character (@, ~, etc.) if used by brand.",
- type: "string",
- }),
- defineField({
- name: "link",
- title: "Link",
- type: "url",
- validation: (Rule) =>
- Rule.required().uri({ scheme: ["http", "https", "mailto"] }),
- }),
- ],
- preview: {
- select: {
- title: "platform",
- subtitle: "label",
- icon: "icon",
- },
- prepare({ title, subtitle, icon }) {
- return {
- title,
- subtitle,
- media: previewIcon(icon),
- };
- },
- },
- }),
- ],
- validation: (Rule) => Rule.unique(),
- }),
- ],
- preview: {
- prepare() {
- return { title: "Socials" };
- },
- },
+ name: "socials",
+ title: "Socials",
+ type: "document",
+ fields: [
+ defineField({
+ name: "socials",
+ title: "Socials",
+ type: "array",
+ of: [
+ defineArrayMember({
+ type: "object",
+ fields: [
+ defineField({
+ name: "icon",
+ title: "Icon",
+ type: "icon",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "platform",
+ title: "Platform",
+ type: "string",
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "label",
+ title: "Label",
+ description:
+ "Primary identifier of platform (i.e. Username). Include a prefix character (@, ~, etc.) if used by brand.",
+ type: "string",
+ }),
+ defineField({
+ name: "link",
+ title: "Link",
+ type: "url",
+ validation: (Rule) =>
+ Rule.required().uri({ scheme: ["http", "https", "mailto"] }),
+ }),
+ ],
+ preview: {
+ select: {
+ title: "platform",
+ subtitle: "label",
+ icon: "icon",
+ },
+ prepare({ title, subtitle, icon }) {
+ return {
+ title,
+ subtitle,
+ media: previewIcon(icon),
+ };
+ },
+ },
+ }),
+ ],
+ validation: (Rule) => Rule.unique(),
+ }),
+ ],
+ preview: {
+ prepare() {
+ return { title: "Socials" };
+ },
+ },
});
diff --git a/apps/studio/schemas/timeRange.tsx b/apps/studio/schemas/timeRange.tsx
index 4cb5131..0303992 100644
--- a/apps/studio/schemas/timeRange.tsx
+++ b/apps/studio/schemas/timeRange.tsx
@@ -6,70 +6,70 @@ import ct from "countries-and-timezones";
const timezones = ct.getAllTimezones();
const CustomDateTimeInput = ({ onChange, value }: DateTimeInputProps) => {
- return (
- {
- const value = event.currentTarget.value;
+ return (
+ {
+ const value = event.currentTarget.value;
- // YYYY-MM-DDThh:mm -> [YYYY, MM, DD, hh, mm]
- const [year, month, day, hour, minute] = value
- .split(/[-T:]/)
- .map((string) => parseInt(string));
+ // YYYY-MM-DDThh:mm -> [YYYY, MM, DD, hh, mm]
+ const [year, month, day, hour, minute] = value
+ .split(/[-T:]/)
+ .map((string) => parseInt(string));
- onChange(
- value
- ? set(
- new Date(Date.UTC(year, month, day, hour, minute)).toISOString()
- )
- : unset()
- );
- }}
- // Ensure pattern matches on browers that don't support `datetime-local`.
- pattern="[0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9]{2}:[0-9]{2}"
- value={value ? new Date(value).toISOString().slice(0, 16) : undefined}
- />
- );
+ onChange(
+ value
+ ? set(
+ new Date(Date.UTC(year, month, day, hour, minute)).toISOString()
+ )
+ : unset()
+ );
+ }}
+ // Ensure pattern matches on browers that don't support `datetime-local`.
+ pattern="[0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9]{2}:[0-9]{2}"
+ value={value ? new Date(value).toISOString().slice(0, 16) : undefined}
+ />
+ );
};
export default defineType({
- name: "timeRange",
- title: "Time Range",
- type: "object",
- fields: [
- defineField({
- name: "timezone",
- title: "Timezone",
- type: "string",
- initialValue: "America/Los_Angeles",
- options: {
- list: Object.entries(timezones).map(([key, timezone]) => ({
- title: `${timezone.name} (${timezone.utcOffsetStr})`,
- value: key,
- })),
- },
- validation: (Rule) => Rule.required(),
- }),
- // The default behavior for datetime fields is to display / set the datetime based on the user's local timezone and store in UTC. For example if I'm in NY and select 9AM it'll be stored as 13:00 (assuming we're not in daylight savings), but still displayed as 9AM. This is neither configurable nor transparent to the user.
- // I was unable to find a way to set the timezone of the datetime field, or disable the timezone conversion.
- // Since there's no way to set the timezone, we need to be able to select the datetime as it's stored, hence the custom component.
- defineField({
- name: "start",
- title: "Start",
- type: "datetime",
- components: {
- input: CustomDateTimeInput,
- },
- validation: (Rule) => Rule.required(),
- }),
- defineField({
- name: "end",
- title: "End",
- type: "datetime",
- components: {
- input: CustomDateTimeInput,
- },
- validation: (Rule) => Rule.required().min(Rule.valueOfField("start")),
- }),
- ],
+ name: "timeRange",
+ title: "Time Range",
+ type: "object",
+ fields: [
+ defineField({
+ name: "timezone",
+ title: "Timezone",
+ type: "string",
+ initialValue: "America/Los_Angeles",
+ options: {
+ list: Object.entries(timezones).map(([key, timezone]) => ({
+ title: `${timezone.name} (${timezone.utcOffsetStr})`,
+ value: key,
+ })),
+ },
+ validation: (Rule) => Rule.required(),
+ }),
+ // The default behavior for datetime fields is to display / set the datetime based on the user's local timezone and store in UTC. For example if I'm in NY and select 9AM it'll be stored as 13:00 (assuming we're not in daylight savings), but still displayed as 9AM. This is neither configurable nor transparent to the user.
+ // I was unable to find a way to set the timezone of the datetime field, or disable the timezone conversion.
+ // Since there's no way to set the timezone, we need to be able to select the datetime as it's stored, hence the custom component.
+ defineField({
+ name: "start",
+ title: "Start",
+ type: "datetime",
+ components: {
+ input: CustomDateTimeInput,
+ },
+ validation: (Rule) => Rule.required(),
+ }),
+ defineField({
+ name: "end",
+ title: "End",
+ type: "datetime",
+ components: {
+ input: CustomDateTimeInput,
+ },
+ validation: (Rule) => Rule.required().min(Rule.valueOfField("start")),
+ }),
+ ],
});
diff --git a/apps/studio/themer.d.ts b/apps/studio/themer.d.ts
index 2746f08..d32ed46 100644
--- a/apps/studio/themer.d.ts
+++ b/apps/studio/themer.d.ts
@@ -1,18 +1,18 @@
declare module "https://themer.sanity.build/api/hues?*" {
- interface Hue
- extends Omit {
- midPoint: 50 | 100 | 200 | 300 | 400 | 500 | 600 | 700 | 800 | 900 | 950;
- }
- interface Hues {
- default: Hue;
- transparent: Hue;
- primary: Hue;
- positive: Hue;
- caution: Hue;
- critical: Hue;
- }
- export const hues: Hues;
- type Theme = import("sanity").StudioTheme;
- export function createTheme(_hues: Hues): Theme;
- export const theme: Theme;
+ interface Hue
+ extends Omit {
+ midPoint: 50 | 100 | 200 | 300 | 400 | 500 | 600 | 700 | 800 | 900 | 950;
+ }
+ interface Hues {
+ default: Hue;
+ transparent: Hue;
+ primary: Hue;
+ positive: Hue;
+ caution: Hue;
+ critical: Hue;
+ }
+ export const hues: Hues;
+ type Theme = import("sanity").StudioTheme;
+ export function createTheme(_hues: Hues): Theme;
+ export const theme: Theme;
}
diff --git a/apps/studio/tsconfig.json b/apps/studio/tsconfig.json
index dee6b84..c840bc7 100644
--- a/apps/studio/tsconfig.json
+++ b/apps/studio/tsconfig.json
@@ -1,20 +1,20 @@
{
- "compilerOptions": {
- "target": "ES2017",
- "lib": ["dom", "dom.iterable", "esnext"],
- "allowJs": true,
- "skipLibCheck": true,
- "strict": true,
- "forceConsistentCasingInFileNames": true,
- "noEmit": true,
- "esModuleInterop": true,
- "module": "esnext",
- "moduleResolution": "node",
- "resolveJsonModule": true,
- "isolatedModules": true,
- "jsx": "preserve",
- "incremental": true
- },
- "include": ["**/*.ts", "**/*.tsx"],
- "exclude": ["node_modules"]
+ "compilerOptions": {
+ "target": "ES2017",
+ "lib": ["dom", "dom.iterable", "esnext"],
+ "allowJs": true,
+ "skipLibCheck": true,
+ "strict": true,
+ "forceConsistentCasingInFileNames": true,
+ "noEmit": true,
+ "esModuleInterop": true,
+ "module": "esnext",
+ "moduleResolution": "node",
+ "resolveJsonModule": true,
+ "isolatedModules": true,
+ "jsx": "preserve",
+ "incremental": true
+ },
+ "include": ["**/*.ts", "**/*.tsx"],
+ "exclude": ["node_modules"]
}
diff --git a/apps/studio/turbo.json b/apps/studio/turbo.json
index 1ca1faa..117d9d6 100644
--- a/apps/studio/turbo.json
+++ b/apps/studio/turbo.json
@@ -1,8 +1,8 @@
{
- "extends": ["//"],
- "pipeline": {
- "build": {
- "outputs": ["dist/**"]
- }
- }
+ "extends": ["//"],
+ "pipeline": {
+ "build": {
+ "outputs": ["dist/**"]
+ }
+ }
}