a78726303a
This commit updates the page metadata (title and description) from the default Next.js placeholders to be descriptive of the Opp lens application, improving SEO. Additionally, it refactors the HTML structure for better semantics and accessibility: - Replaced generic `div` and fragment tags with appropriate semantic elements like `main`, `article`, `li`, and `small`. - Corrected the heading hierarchy for better document structure. - Fixed image source paths by making them absolute to prevent broken images.
173 lines
4.6 KiB
TypeScript
173 lines
4.6 KiB
TypeScript
import type { Metadata } from "next";
|
|
import { Geist, Geist_Mono } from "next/font/google";
|
|
import Image from "next/image";
|
|
import Link from "next/link";
|
|
import { ToastContainer, Zoom } from "react-toastify";
|
|
import NavigationBar from "../_components/NavigationBar";
|
|
import "../globals.css";
|
|
const geistSans = Geist({
|
|
variable: "--font-geist-sans",
|
|
subsets: ["latin"],
|
|
});
|
|
|
|
const geistMono = Geist_Mono({
|
|
variable: "--font-geist-mono",
|
|
subsets: ["latin"],
|
|
});
|
|
|
|
export const metadata: Metadata = {
|
|
title: "Opp lens - AI-Powered Tender Management",
|
|
description: "Democratizing Tender Access for SMEs with AI-Powered Tender Management.",
|
|
icons: {
|
|
icon: "/fav-icon.svg",
|
|
},
|
|
};
|
|
|
|
function ContactInfo({
|
|
icon,
|
|
contact,
|
|
href,
|
|
ariaLabel,
|
|
contactIconSrc,
|
|
}: {
|
|
icon: string;
|
|
contact: string;
|
|
href?: string;
|
|
ariaLabel: string;
|
|
contactIconSrc?: string;
|
|
}) {
|
|
return (
|
|
<div className="flex gap-3 my-3 text-white">
|
|
<Image
|
|
src={icon}
|
|
width={24}
|
|
height={24}
|
|
alt=""
|
|
aria-hidden="true"
|
|
/>
|
|
{href ? (
|
|
<a
|
|
href={href}
|
|
className="cursor-pointer min-w-fit"
|
|
aria-label={ariaLabel}>
|
|
{contact}
|
|
</a>
|
|
) : (
|
|
<p className="flex gap-3">
|
|
{!!contactIconSrc && (
|
|
<Image
|
|
src={contactIconSrc}
|
|
width={20}
|
|
height={20}
|
|
alt="flag"
|
|
/>
|
|
)}
|
|
{contact}
|
|
</p>
|
|
)}
|
|
</div>
|
|
);
|
|
}
|
|
|
|
export default async function RootLayout({
|
|
children,
|
|
}: Readonly<{
|
|
children: React.ReactNode;
|
|
}>) {
|
|
const contactInfo = [
|
|
{
|
|
icon: "/Message.svg",
|
|
contact: "info@opplens.com",
|
|
href: "mailto:info@opplens.com",
|
|
ariaLabel: "Email us at info@opplens.com",
|
|
},
|
|
{
|
|
icon: "/Phone.svg",
|
|
contact: "(+46) - 761581526",
|
|
href: "tel:+46761581526",
|
|
ariaLabel: "Call us at +46 761581526",
|
|
},
|
|
{
|
|
icon: "/Location.svg",
|
|
contact: "Stockholm, Sweden",
|
|
ariaLabel: "Our location in Stockholm, Sweden",
|
|
contactIconSrc: "/sweden.svg",
|
|
},
|
|
];
|
|
|
|
return (
|
|
<html lang="en">
|
|
<body
|
|
className={`${geistSans.variable} ${geistMono.variable} antialiased flex flex-col bg-[url('/header-bg.svg')] bg-top-right bg-no-repeat bg-contain md:bg-cover`}>
|
|
<header className="flex justify-center pt-8 items-center pb-4 container px-4 py-4 m-auto md:px-28 md:justify-between flex-wrap gap-5">
|
|
<section>
|
|
<Link
|
|
href="/"
|
|
aria-label="Opp lens home">
|
|
<Image
|
|
src="/main-logo.svg"
|
|
alt="Opp lens logo"
|
|
width={180}
|
|
height={30}
|
|
priority
|
|
/>
|
|
</Link>
|
|
</section>
|
|
|
|
<NavigationBar />
|
|
</header>
|
|
|
|
<ToastContainer
|
|
position="top-right"
|
|
autoClose={2500}
|
|
theme={"colored"}
|
|
transition={Zoom}
|
|
hideProgressBar
|
|
newestOnTop
|
|
closeOnClick
|
|
pauseOnFocusLoss
|
|
draggable
|
|
pauseOnHover
|
|
/>
|
|
|
|
<div className="container px-4 py-4 m-auto flex-grow">{children}</div>
|
|
<footer className="relative h-full bg-[url('/footer-bg.svg')] bg-cover bg-no-repeat mt-40">
|
|
<div className="relative z-10 container px-4 py-4 m-auto flex flex-col justify-center items-center mt-24 ">
|
|
<div className="flex justify-between flex-col md:flex-row gap-14 w-full md:w-1/2">
|
|
<div className="flex flex-col gap-10">
|
|
<Image
|
|
src={"/footer-logo.svg"}
|
|
alt="Opp lens logo"
|
|
width={180}
|
|
height={30}
|
|
priority
|
|
/>
|
|
<div>
|
|
<p className="text-white my-2">
|
|
Democratizing Tender Access for SMEs.
|
|
</p>
|
|
<p className="text-white my-2">
|
|
© 2025 Opplens.com by PBL Partners AB. All Rights Reserved.
|
|
</p>
|
|
</div>
|
|
</div>
|
|
<div>
|
|
{contactInfo.map((contact, index) => (
|
|
<ContactInfo
|
|
key={index}
|
|
icon={contact.icon}
|
|
contact={contact.contact}
|
|
href={contact.href}
|
|
ariaLabel={contact.ariaLabel}
|
|
contactIconSrc={contact.contactIconSrc}
|
|
/>
|
|
))}
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</footer>
|
|
</body>
|
|
</html>
|
|
);
|
|
}
|