Skip to content

Commit e686881

Browse files
authored
Feat: Implement case study page (#33)
* Create case studies page * add json * add erp-fisheries page * Create case studies detail page * change banner
1 parent 7a07ff2 commit e686881

File tree

25 files changed

+1331
-49
lines changed

25 files changed

+1331
-49
lines changed
Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
import ScrollObserver from "@/app/components/scroll-observer";
2+
import type { SupportedLanguage } from "@/locales/.generated/types";
3+
import Hero from "../components/hero";
4+
import Nav from "@/app/components/nav";
5+
import Footer from "@/app/components/footer";
6+
7+
type ServiceLangProps = {
8+
children: React.ReactNode;
9+
params: Promise<{ lang: SupportedLanguage }>;
10+
};
11+
12+
export default async function CaseStudiesLangLayout({
13+
children,
14+
params
15+
}: ServiceLangProps) {
16+
const { lang } = await params;
17+
18+
return (
19+
<div className="bg-white">
20+
<ScrollObserver />
21+
<Nav className="xxl:max-w-7xl max-w-6xl" lang={lang} />
22+
<Hero lang={lang} />
23+
{children}
24+
<Footer lang={lang} type="case-studies" />
25+
</div>
26+
);
27+
}
Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,62 @@
1+
import type { SupportedLanguage } from "@/locales/.generated/types";
2+
import {
3+
caseStudyExplore,
4+
caseStudyCategory
5+
} from "@/locales/.generated/server";
6+
import { getCaseStudies } from "../components/data";
7+
import { CaseStudyButton } from "../components/button";
8+
import { CTACaseStudies } from "../components/cta-case-studies";
9+
10+
export const generateStaticParams = async () => {
11+
return [{ lang: "en" }, { lang: "id" }];
12+
};
13+
14+
type CaseStudyProps = {
15+
params: Promise<{ lang: SupportedLanguage }>;
16+
};
17+
18+
export default async function CaseStudiesPage({ params }: CaseStudyProps) {
19+
return <Home lang={(await params).lang} />;
20+
}
21+
22+
function Home({ lang }: { lang: SupportedLanguage }) {
23+
return (
24+
<main className="xxl:max-w-7xl mx-auto flex w-full max-w-6xl flex-wrap items-center justify-center px-4 text-center md:px-20 md:py-12 xl:px-0">
25+
<h3 className="text-hyperjump-black w-72 text-[34px] font-medium md:w-full md:text-[40px]">
26+
{caseStudyExplore(lang)}
27+
</h3>
28+
<CaseStudies lang={lang} />
29+
<CTACaseStudies lang={lang} />
30+
</main>
31+
);
32+
}
33+
34+
function CaseStudies({ lang }: { lang: SupportedLanguage }) {
35+
return (
36+
<section className="bg-white py-10">
37+
<div className="mx-auto max-w-6xl">
38+
<div className="grid gap-6 md:grid-cols-2">
39+
{getCaseStudies(lang).map((study, index) => (
40+
<div
41+
key={index}
42+
className="flex h-full flex-col justify-between rounded-xl border border-gray-200 p-6 text-left shadow-sm transition duration-300 hover:shadow-md">
43+
<div>
44+
<span className="mb-4 inline-block rounded-full bg-gray-100 px-3 py-1 text-sm font-medium text-gray-800">
45+
{caseStudyCategory(lang)}
46+
</span>
47+
<h3 className="text-hyperjump-black mb-2 text-lg font-semibold md:text-[22px]">
48+
{study.title}
49+
</h3>
50+
<p className="text-hyperjump-gray mb-4 text-sm md:text-base">
51+
{study.description}
52+
</p>
53+
</div>
54+
55+
<CaseStudyButton url={study.url} lang={lang} />
56+
</div>
57+
))}
58+
</div>
59+
</div>
60+
</section>
61+
);
62+
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
"use client";
2+
3+
import { SupportedLanguage } from "@/locales/.generated/types";
4+
import { caseStudyButton } from "@/locales/.generated/server";
5+
import { Button } from "@/components/ui/button";
6+
import Link from "next/link";
7+
8+
export function CaseStudyButton({
9+
lang,
10+
url
11+
}: {
12+
lang: SupportedLanguage;
13+
url: string;
14+
}) {
15+
return (
16+
<Button
17+
asChild
18+
variant="outline"
19+
className="text-hyperjump-blue hover:bg-hyperjump-blue mt-4 w-full border-gray-300 hover:text-white">
20+
<Link href={url}>{caseStudyButton(lang)}</Link>
21+
</Button>
22+
);
23+
}
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
"use client";
2+
3+
import { SupportedLanguage } from "@/locales/.generated/types";
4+
import data from "@/data.json";
5+
import Image from "next/image";
6+
import {
7+
servicesCtaDesc,
8+
servicesCtaHeading,
9+
servicesCtaLabel
10+
} from "@/locales/.generated/server";
11+
import { Button } from "@/components/ui/button";
12+
import Link from "next/link";
13+
import { sendGAEvent } from "@next/third-parties/google";
14+
15+
export function CTACaseStudies({ lang }: { lang: SupportedLanguage }) {
16+
const { gaEventName, link } = data.cta;
17+
18+
return (
19+
<section className="relative my-10 w-full max-w-6xl overflow-hidden rounded-lg">
20+
<div className="absolute inset-0 z-0">
21+
<Image
22+
src="/images/swatch.svg"
23+
alt="CTA Background"
24+
width={1440}
25+
height={308}
26+
className="pointer-events-none h-full object-cover select-none"
27+
style={{
28+
background:
29+
"linear-gradient(134.7deg, #5954DA 3.43%, #0B0B0D 48.93%)"
30+
}}
31+
/>
32+
</div>
33+
<div className="relative flex flex-col items-center justify-center px-6 py-11 text-center">
34+
<h4 className="mb-3 text-3xl font-medium text-white md:text-4xl">
35+
{servicesCtaHeading(lang)}
36+
</h4>
37+
<p className="mb-8 text-lg text-white">{servicesCtaDesc(lang)}</p>
38+
39+
<Button
40+
asChild
41+
size="lg"
42+
className="bg-hyperjump-blue hover:bg-hyperjump-blue/90 text-base font-semibold text-white">
43+
<Link
44+
onClick={() => {
45+
sendGAEvent({
46+
event: gaEventName,
47+
category: "engagement",
48+
label: "Case Studies CTA"
49+
});
50+
}}
51+
href={link}
52+
target="_blank"
53+
rel="noreferrer noopener">
54+
{servicesCtaLabel(lang)}
55+
</Link>
56+
</Button>
57+
</div>
58+
</section>
59+
);
60+
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import {
2+
caseStudyCtoaasMediaDesc,
3+
caseStudyCtoaasMediaTitle,
4+
caseStudyErpFisheriesDesc,
5+
caseStudyErpFisheriesTitle
6+
} from "@/locales/.generated/server";
7+
import { SupportedLanguage } from "@/locales/.generated/types";
8+
9+
export const getCaseStudies = (lang: SupportedLanguage) => {
10+
const data = [
11+
{
12+
title: caseStudyErpFisheriesTitle(lang),
13+
description: caseStudyErpFisheriesDesc(lang),
14+
url: "/case-studies/erp-fisheries"
15+
},
16+
{
17+
title: caseStudyCtoaasMediaTitle(lang),
18+
description: caseStudyCtoaasMediaDesc(lang),
19+
url: "/case-studies/ctoaas-media"
20+
}
21+
];
22+
23+
return data;
24+
};
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
import Image from "next/image";
2+
3+
export function Hero({ heading }: { heading: string }) {
4+
return (
5+
<section
6+
id="hero"
7+
className="bg-hyperjump-black relative h-[351px] overflow-hidden px-4 text-white md:px-20">
8+
<div className="absolute inset-0 z-0">
9+
<Image
10+
alt="Hero background"
11+
blurDataURL="/images/case-studies/banner.jpg"
12+
className="object-cover object-center"
13+
fill
14+
placeholder="blur"
15+
priority
16+
src="/images/case-studies/banner.jpg"
17+
/>
18+
</div>
19+
20+
<div className="relative z-10 mt-10 flex h-[351px] items-center justify-center">
21+
<div
22+
className="mb-4 max-w-3xl text-center text-2xl font-medium text-white sm:text-4xl md:text-[40px]"
23+
dangerouslySetInnerHTML={{
24+
__html: heading
25+
}}
26+
/>
27+
</div>
28+
</section>
29+
);
30+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import type { SupportedLanguage } from "@/locales/.generated/types";
2+
import {
3+
caseStudyHeroHeading,
4+
caseStudyHeroDesc
5+
} from "@/locales/.generated/server";
6+
7+
export default function Hero({ lang }: { lang: SupportedLanguage }) {
8+
return (
9+
<section
10+
id="hero"
11+
className="bg-services-hero text-hyperjump-black relative h-[415px] w-full px-4 text-center">
12+
<div className="mx-auto flex h-full max-w-3xl flex-col items-center justify-center pt-16">
13+
<div
14+
className="text-hyperjump-black mb-4 text-3xl font-medium sm:text-4xl md:text-[40px]"
15+
dangerouslySetInnerHTML={{
16+
__html: caseStudyHeroHeading(lang)
17+
}}
18+
/>
19+
<p className="text-hyperjump-gray text-base sm:text-lg">
20+
{caseStudyHeroDesc(lang)}
21+
</p>
22+
</div>
23+
</section>
24+
);
25+
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import ScrollObserver from "@/app/components/scroll-observer";
2+
import type { SupportedLanguage } from "@/locales/.generated/types";
3+
4+
import Nav from "@/app/components/nav";
5+
import Footer from "@/app/components/footer";
6+
import { Hero } from "../../components/hero-details";
7+
import { caseStudyCtoaasMediaTitle } from "@/locales/.generated/server";
8+
type ServiceLangProps = {
9+
children: React.ReactNode;
10+
params: Promise<{ lang: SupportedLanguage }>;
11+
};
12+
13+
export default async function CtoaasMediaLangLayout({
14+
children,
15+
params
16+
}: ServiceLangProps) {
17+
const { lang } = await params;
18+
19+
return (
20+
<div className="bg-white">
21+
<ScrollObserver />
22+
<Nav isTransparent className="xxl:max-w-7xl max-w-6xl" lang={lang} />
23+
<Hero heading={caseStudyCtoaasMediaTitle(lang)} />
24+
{children}
25+
<Footer lang={lang} type="ctoaas-media" />
26+
</div>
27+
);
28+
}

0 commit comments

Comments
 (0)