diff --git a/src/app/layout.tsx b/src/app/layout.tsx index c6156ef..c1b9db0 100644 --- a/src/app/layout.tsx +++ b/src/app/layout.tsx @@ -1,6 +1,5 @@ import { ConditionalFooter } from "@/components/conditional-footer" import { Header } from "@/components/header/header" -import { Shape } from "@/components/shapes" import { ThemeProvider } from "@/components/theme-provider" import "@/styles/globals.css" import type { Metadata } from "next" @@ -75,12 +74,7 @@ export default function RootLayout({ children }: Readonly<{ children: React.Reac // storageKey="polinetwork_darkmode_temp" // TODO: enable when dark mode design is ready disableTransitionOnChange > -
- - - - -
+ {/* */}
{children} diff --git a/src/app/page.tsx b/src/app/page.tsx index 0296908..66b8b37 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -2,13 +2,20 @@ import { AboutUs } from "@/components/home/about-us" import { Hero } from "@/components/home/hero" import { Materials } from "@/components/home/materials" import { Projects } from "@/components/home/projects" +import { HomeMaterialsShapes, HomeProjectsShapes } from "@/components/home/shapes" export default function Home() { return (
- - +
+ + +
+
+ + +
) diff --git a/src/app/projects/page.tsx b/src/app/projects/page.tsx index fbfb0d7..a431936 100644 --- a/src/app/projects/page.tsx +++ b/src/app/projects/page.tsx @@ -3,6 +3,7 @@ import { CommunityNews } from "@/components/projects/community-news" import { Deprecated } from "@/components/projects/deprecated" import { Upload } from "@/components/projects/upload" import { getAllProjects } from "@/queries/projects" +import { CollectionShapes, CommunityNewsShapes, DeprecatedShapes, UploadShapes } from "./shapes" export const metadata = { title: "Progetti", @@ -20,10 +21,22 @@ export default async function Home() { return (
- - - - +
+ + +
+
+ + +
+
+ + +
+
+ + +
) } diff --git a/src/app/projects/shapes.tsx b/src/app/projects/shapes.tsx new file mode 100644 index 0000000..35d9031 --- /dev/null +++ b/src/app/projects/shapes.tsx @@ -0,0 +1,97 @@ +import { Shape } from "@/components/shapes" + +/** + * `left` offsets below are expressed as `calc(50% + Npx)`, i.e. relative to the + * horizontal center of the section rather than its left edge. The projects + * content is itself center-anchored (not width-capped), so anchoring shapes to + * the edge would make them drift away from the content on screens wider or + * narrower than the 1728px/402px Figma reference frames. + * + * `top` is relative to the top of the section each component is mounted in + * (CommunityNews, Collection, Upload, Deprecated), not to the page. Every + * section on this page uses `min-h-screen` (fluid height, depends on the viewport) + * — each shape below is therefore scoped and `top`-anchored to the section it + * visually belongs to, rather than using cumulative page offsets. + */ + +export function CommunityNewsShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + + + + + {/* Desktop Shapes */} + + + + + +
+ ) +} + +export function CollectionShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + {/* Desktop Shapes */} + + + +
+ ) +} + +export function UploadShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + {/* Desktop Shapes */} + + + +
+ ) +} + +export function DeprecatedShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + + {/* Desktop Shapes */} + + + +
+ ) +} diff --git a/src/assets/shapes/hero-glow.svg b/src/assets/shapes/hero-glow.svg new file mode 100644 index 0000000..98a159b --- /dev/null +++ b/src/assets/shapes/hero-glow.svg @@ -0,0 +1,30 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/assets/shapes/projects-glow.svg b/src/assets/shapes/projects-glow.svg new file mode 100644 index 0000000..07df19c --- /dev/null +++ b/src/assets/shapes/projects-glow.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/src/components/conditional-global-shapes.tsx b/src/components/conditional-global-shapes.tsx new file mode 100644 index 0000000..d034b7e --- /dev/null +++ b/src/components/conditional-global-shapes.tsx @@ -0,0 +1,26 @@ +"use client" + +import { usePathname } from "next/navigation" +import { Shape } from "@/components/shapes" + +const HIDDEN_EXACT = ["/"] + +/** + * Generic top-of-page decorative shapes, reused on every page that doesn't + * define its own (e.g. the homepage, which has a Figma-accurate composition). + */ +export function ConditionalGlobalShapes() { + const pathname = usePathname() + if (HIDDEN_EXACT.includes(pathname)) return null + + return ( +
+
+ + + + +
+
+ ) +} diff --git a/src/components/footer/index.tsx b/src/components/footer/index.tsx index f403e40..7ccad65 100644 --- a/src/components/footer/index.tsx +++ b/src/components/footer/index.tsx @@ -4,11 +4,13 @@ import { FiFacebook, FiGithub, FiInstagram, FiLinkedin } from "react-icons/fi" import discord from "@/assets/icons/discord.svg" import telegram from "@/assets/icons/telegram.svg" import { CardMultipleIcons } from "../card-multiple-icons" +import { FooterShapes } from "./shapes" export function Footer() { return ( -
-

+
+ +

Keep in touch!

@@ -40,7 +42,7 @@ export function Footer() {

-
+
diff --git a/src/components/footer/shapes.tsx b/src/components/footer/shapes.tsx new file mode 100644 index 0000000..6299352 --- /dev/null +++ b/src/components/footer/shapes.tsx @@ -0,0 +1,12 @@ +import { Shape } from "@/components/shapes" + +export function FooterShapes() { + return ( +
+ {/* Desktop Shapes */} + + + +
+ ) +} diff --git a/src/components/home/hero.tsx b/src/components/home/hero.tsx index ff1152f..22bfccb 100644 --- a/src/components/home/hero.tsx +++ b/src/components/home/hero.tsx @@ -2,10 +2,13 @@ import Link from "next/link" import { FiNavigation, FiUserPlus } from "react-icons/fi" import { Button } from "../ui/button" import { GroupSearch } from "./group-search" +import { HomeHeroShapes } from "./shapes" export function Hero() { return ( -
+
+ +

Trova gruppi, risorse e supporto tra gli studenti del Polimi diff --git a/src/components/home/shapes.tsx b/src/components/home/shapes.tsx new file mode 100644 index 0000000..a1667be --- /dev/null +++ b/src/components/home/shapes.tsx @@ -0,0 +1,72 @@ +import { Shape } from "@/components/shapes" + +/** + * `left` offsets below are expressed as `calc(50% + Npx)`, i.e. relative to the + * horizontal center of the section rather than its left edge. The homepage + * content is itself center-anchored (not width-capped), so anchoring shapes to + * the edge would make them drift away from the content on screens wider or + * narrower than the 1728px/402px Figma reference frames. + * + * `top` is relative to the top of the section each component is mounted in + * (Materials or Projects), not to the page. Materials and Projects/AboutUs + * used to share one absolute layer with cumulative offsets, but AboutUs uses + * `min-h-screen` (fluid height, depends on the viewport) — if a shape ever + * needs to sit inside AboutUs, mount it scoped to that section too, the same + * way this file already splits Materials from Projects. Otherwise any + * mismatch between a fluid section's real height and Figma's fixed height + * assumption compounds into every shape positioned after it (e.g. shapes + * drifting away from their section when the browser is zoomed out — see + * src/app/projects/shapes.tsx, which had exactly this bug). + */ + +export function HomeHeroShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + + {/* Desktop Shapes */} + + +
+ ) +} + +export function HomeMaterialsShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + + + + + {/* Desktop Shapes */} + + + +
+ ) +} + +export function HomeProjectsShapes() { + return ( +
+ {/* Mobile Shapes */} + + + + + {/* Desktop Shapes */} + + +
+ ) +} diff --git a/src/components/shapes.tsx b/src/components/shapes.tsx index 19dd3e2..683100e 100644 --- a/src/components/shapes.tsx +++ b/src/components/shapes.tsx @@ -1,11 +1,13 @@ import Image from "next/image" import bigBlueSvg from "@/assets/shapes/big-blue.svg" import bigTealSvg from "@/assets/shapes/big-teal.svg" +import heroGlowSvg from "@/assets/shapes/hero-glow.svg" import looperSvg from "@/assets/shapes/looper.svg" +import projectsGlowSvg from "@/assets/shapes/projects-glow.svg" import smallBlueSvg from "@/assets/shapes/small-blue.svg" import { cn } from "@/lib/utils" -export type ShapeVariant = "big-blue" | "big-teal" | "small-blue" | "looper" +export type ShapeVariant = "big-blue" | "big-teal" | "small-blue" | "hero-glow" | "projects-glow" | "looper" export type ShapeProps = { variant: ShapeVariant @@ -21,6 +23,10 @@ export const Shape: React.FC = ({ variant, className }) => { return bigTealSvg case "small-blue": return smallBlueSvg + case "hero-glow": + return heroGlowSvg + case "projects-glow": + return projectsGlowSvg case "looper": return looperSvg default: @@ -28,5 +34,7 @@ export const Shape: React.FC = ({ variant, className }) => { } } - return + return ( + + ) }