Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"cSpell.words": ["projectdetail"]
}
2 changes: 1 addition & 1 deletion app/components/footer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ export function Footer() {
<p className="text-sm">Thormøhlens gate 55, 5006 Bergen</p>
</div>

<div className="mt-6 text-center flex flex-col items-center">
<div className="mt-6 mr-15 text-center flex flex-col items-center">
<a
href="https://echo.uib.no/"
target="_blank"
Expand Down
8 changes: 4 additions & 4 deletions app/components/nav.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,12 @@ export function Nav() {
<Link to="/tjenester" className="nav-link">
Tjenester
</Link>
{/* <Link to="/prosjekter" className="nav-link">
<Link to="/prosjekter" className="nav-link">
Prosjekter
</Link> */}
<Link to="/om-oss" className="nav-link">
Om oss
</Link>
{/* <Link to="/om-oss" className="nav-link">
Om oss
</Link> */}
</div>
</nav>
);
Expand Down
84 changes: 84 additions & 0 deletions app/components/projectCard.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
import { useState } from "react";
import { ArrowRight, Eye } from "lucide-react";

type ProjectCardProps = {
imgUrl: string;
title: string;
description: string;
previewUrl: string;
prosjektSide: string;
};

const ProjectCard = ({
imgUrl,
title,
description,
previewUrl,
prosjektSide,
}: ProjectCardProps) => {
const [isHovered, setIsHovered] = useState(false);

return (
<div className="rounded-xl overflow-hidden shadow-lg flex flex-col h-full bg-[#010F1B]">
<div
className="h-52 md:h-60 rounded-t-xl relative group py-3"
style={{
background: `url(${imgUrl}) no-repeat center center `,
backgroundSize: "contain",
backgroundPosition: "center",
backgroundOrigin: "content-box",
}}
>
<div className="overlay flex items-center justify-center absolute inset-0 bg-[#011627] opacity-0 group-hover:opacity-80 transition-all duration-250 rounded-t-xl">
<a
href={previewUrl}
className="h-14 w-14 border-2 relative rounded-full border-[#ADB7BE] hover:border-white flex items-center justify-center"
>
<Eye className="h-10 w-10 text-[#ADB7BE] hover:text-white" />
</a>
</div>
</div>
<a
href={prosjektSide}
className="text-white rounded-b-xl bg-[#011627] py-6 px-4 flex flex-col justify-between flex-grow cursor-pointer"
style={{ textDecoration: "none" }}
onMouseEnter={() => setIsHovered(true)}
onMouseLeave={() => setIsHovered(false)}
>
<h5 className="font-xl font-semibold mb-2">{title}</h5>
<p style={{ whiteSpace: "pre-line" }} className="text-[#ADB7BE] mb-4">
{description}
</p>

<span
className={`flex items-center gap-2 font-medium tracking-wider transition-colors duration-300 ${
isHovered ? "text-blue-400" : "text-white"
}`}
>
<span className="relative">
Les mer her
<span
className={`absolute left-0 -bottom-0.5 h-[2px] bg-blue-400 transition-all duration-300 ${
isHovered ? "w-full" : "w-0"
}`}
/>
</span>

<span
className="inline-flex transition-transform duration-300"
style={{
transform: isHovered ? "translateX(6px)" : "translateX(0)",
}}
>
<ArrowRight
size={20}
className={isHovered ? "text-blue-400" : "text-white"}
/>
</span>
</span>
</a>
</div>
);
};

export default ProjectCard;
69 changes: 69 additions & 0 deletions app/components/projectDetail.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
import { ArrowRight } from "lucide-react";
import { useState } from "react";

type ProjectDetailProps = {
slug: string;
title: string;
desc: string;
small_img: string;
large_img: string;
link: string;
};

export default function ProjectDetail({
title,
desc,
large_img,
link,
}: ProjectDetailProps) {
const [isHovered, setHoveredCard] = useState(false);
return (
<div>
<h1 className="text-4xl font-bold mb-6 text-center">{title}</h1>
<img
src={large_img}
alt={title}
className="w-full max-w-2xl mx-auto mb-6 rounded shadow-lg"
/>
<p className="text-lg leading-relaxed">{desc}</p>
{link != "" ? (
<a
href={link}
target="_blank"
rel="noopener noreferrer"
className="flex justify-center items-center gap-2 font-medium tracking-wider mt-2 group"
onMouseEnter={() => setHoveredCard(true)}
onMouseLeave={() => setHoveredCard(false)}
>
<span className="relative mt-5">
<span
className={`transition-colors duration-300 ${
isHovered ? "text-blue-400" : "text-white"
}`}
>
Link til siden
</span>
<span
className={`absolute left-0 -bottom-0.5 h-[2px] bg-blue-400 transition-all duration-300 ${
isHovered ? "w-full" : "w-0"
}`}
/>
</span>
<span
className="inline-flex transition-transform duration-300 mt-5"
style={{
transform: isHovered ? "translateX(6px)" : "translateX(0)",
}}
>
<ArrowRight
size={24}
className={isHovered ? "text-blue-400" : "text-white"}
/>
</span>
</a>
) : (
<></>
)}
</div>
);
}
69 changes: 0 additions & 69 deletions app/components/projects.tsx

This file was deleted.

54 changes: 54 additions & 0 deletions app/components/projectsSection.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import ProjectCard from "./projectCard";

// Dette skal hentes fra Sanity etterhvert
export const projectData = [
{
slug: "lffh",
title: "LFFH-nettsiden",
desc: "Funksjonell nettside for Linjeforeningen for Fiskehelse og Havbruk, med mulighet for blant annet innlogging, arrangementopprettelse og påmelding til arrangementer",
small_img: "/ProjectImages/lffh_logo_small.png",
large_img: "/ProjectImages/lffh_rectangle.png",
link: "https://www.lffh.no/",
},
{
slug: "integrerbar",
title: "Integrerbar-nettsiden (under utvikling)",
desc: "En nettside utviklet for Integrerbar, studentbaren tilknyttet Fakultet for naturvitenskap og teknologi ved Universitetet, med base i Realfagbygget.",
small_img: "/ProjectImages/integrerbar_logo_small.png",
large_img: "/ProjectImages/integrerbar_rectangle.jpeg",
link: "",
},
{
slug: "nti",
title: "NTidrett-nettsiden (under utvikling)",
desc: "En nettside utviklet for NT Idrett, idrettsorganisasjonen tilknyttet Fakultet for naturvitenskap og teknologi ved universitetet.",
small_img: "/ProjectImages/nti_logo_small.png",
large_img: "/ProjectImages/nti_logo_white.jpeg",
link: "",
},
];

export default function ProjectsSection() {
return (
<>
<h2 className="text-center text-4xl font-bold text-white mt-4 mb-8 md:mb-12">
Prosjekter
</h2>

{/* Prosjekter */}
<div className="flex flex-wrap gap-8 items-stretch justify-center">
{projectData.map((project) => (
<div key={project.slug} className="w-full sm:w-[48%] lg:w-[31%] flex">
<ProjectCard
imgUrl={project.small_img}
title={project.title}
description={project.desc}
previewUrl={project.link}
prosjektSide={`prosjekter/${project.slug}`}
/>
</div>
))}
</div>
</>
);
}
5 changes: 3 additions & 2 deletions app/routes.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import { type RouteConfig, route, index } from "@react-router/dev/routes";
import { type RouteConfig, index, route } from "@react-router/dev/routes";

export default [
index("routes/home.tsx"),
route("/tjenester", "routes/tjenester.tsx"),
route("/om-oss", "routes/om-oss.tsx"),
route("/prosjekter", "routes/projectOverview.tsx"),
route("/prosjekter/:slug", "routes/projectPage.tsx"),
] satisfies RouteConfig;
12 changes: 9 additions & 3 deletions app/routes/home.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { Hero } from "~/components/hero";
import ProjectsSection from "../components/projectsSection";
import { Container } from "@mantine/core";

export function meta() {
Expand All @@ -13,8 +14,13 @@ export function meta() {

export default function Home() {
return (
<Container className="relative z-10 pt-48">
<Hero />
</Container>
<div className="relative min-h-screen">
<Container className="relative z-10 pt-48">
<Hero />
</Container>
<Container className="mt-25 mb-25">
<ProjectsSection />
</Container>
</div>
);
}
Loading