- Next.js 16 App Router site with the ANOUMA design system - Payload CMS (PostgreSQL) for offers, events, posts and page content - WebRTC video-call system with custom signaling server - SMTP email reminders and booking-request notifications - Customer accounts, calendar-based availability, and booking workflow
46 lines
1.7 KiB
TypeScript
46 lines
1.7 KiB
TypeScript
import Link from "next/link";
|
|
import type { ReactNode } from "react";
|
|
|
|
type Variant = "primary" | "secondary" | "ghost" | "invert" | "invertOutline";
|
|
|
|
// Text colors are chosen to meet WCAG AA (4.5:1) against every background
|
|
// tone the button appears on — see components/Section.tsx for the tones.
|
|
const variants: Record<Variant, string> = {
|
|
primary: "bg-anouma-mauve-dark text-white hover:bg-anouma-plum",
|
|
secondary:
|
|
"border border-anouma-mauve-dark/40 text-anouma-plum hover:bg-anouma-mauve-dark hover:text-white",
|
|
ghost:
|
|
"text-anouma-plum underline underline-offset-4 decoration-anouma-mauve-dark/50 hover:decoration-anouma-mauve-dark",
|
|
// For use on dark (plum/mauve-dark) section backgrounds, e.g. CTA.
|
|
invert: "bg-anouma-cream-light text-anouma-plum hover:bg-white",
|
|
invertOutline: "border border-white/50 text-white hover:bg-white hover:text-anouma-plum",
|
|
};
|
|
|
|
type ButtonProps = {
|
|
href: string;
|
|
children: ReactNode;
|
|
variant?: Variant;
|
|
className?: string;
|
|
};
|
|
|
|
export function Button({ href, children, variant = "primary", className = "" }: ButtonProps) {
|
|
const isExternal = href.startsWith("http") || href.startsWith("mailto:") || href.startsWith("tel:");
|
|
const base =
|
|
"inline-flex items-center justify-center gap-2 rounded-full px-7 py-3.5 text-sm font-medium tracking-wide transition-colors duration-300 focus-visible:outline-2 focus-visible:outline-offset-4";
|
|
const classes = `${base} ${variants[variant]} ${className}`;
|
|
|
|
if (isExternal) {
|
|
return (
|
|
<a href={href} className={classes} target="_blank" rel="noopener noreferrer">
|
|
{children}
|
|
</a>
|
|
);
|
|
}
|
|
|
|
return (
|
|
<Link href={href} className={classes}>
|
|
{children}
|
|
</Link>
|
|
);
|
|
}
|