Retour au catalogue
Login Split
Page de connexion en split-screen : visuel/branding a gauche, formulaire a droite.
authmedium Both Responsive a11y
elegantboldsaasagencyuniversalsplit
Theme
"use client";
import { motion } from "framer-motion";
interface AuthLoginSplitProps {
brandName?: string;
title?: string;
subtitle?: string;
tagline?: string;
showSocial?: boolean;
showRemember?: boolean;
}
const ease: [number, number, number, number] = [0.16, 1, 0.3, 1];
export default function AuthLoginSplit({
brandName = "Studio",
title = "Bon retour",
subtitle = "",
tagline = "",
showSocial = true,
showRemember = true,
}: AuthLoginSplitProps) {
return (
<section className="min-h-screen grid lg:grid-cols-2">
{/* Left - branding */}
<div
className="hidden lg:flex flex-col justify-between p-12"
style={{ background: "var(--color-accent)" }}
>
<div
className="text-lg font-bold"
style={{ color: "var(--color-background)" }}
>
{brandName}
</div>
<div>
<p
className="text-3xl lg:text-4xl font-bold leading-tight max-w-md"
style={{ color: "var(--color-background)" }}
>
{tagline}
</p>
</div>
<p
className="text-sm opacity-70"
style={{ color: "var(--color-background)" }}
>
© {new Date().getFullYear()} {brandName}
</p>
</div>
{/* Right - form */}
<div
className="flex items-center justify-center p-8"
style={{ background: "var(--color-background)" }}
>
<motion.div
initial={{ opacity: 0, y: 20 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 0.6, ease }}
className="w-full max-w-sm"
>
<h1
className="text-2xl font-bold mb-2"
style={{ color: "var(--color-foreground)" }}
>
{title}
</h1>
{subtitle && (
<p className="text-sm mb-8" style={{ color: "var(--color-foreground-muted)" }}>
{subtitle}
</p>
)}
{showSocial && (
<>
<button
className="w-full py-2.5 rounded-lg text-sm font-medium mb-3 transition-opacity hover:opacity-80"
style={{ border: "1px solid var(--color-border)", color: "var(--color-foreground)" }}
>
Continuer avec Google
</button>
<div className="flex items-center gap-3 my-6">
<div className="flex-1 h-px" style={{ background: "var(--color-border)" }} />
<span className="text-xs" style={{ color: "var(--color-foreground-light)" }}>ou</span>
<div className="flex-1 h-px" style={{ background: "var(--color-border)" }} />
</div>
</>
)}
<form onSubmit={(e) => e.preventDefault()} className="flex flex-col gap-4">
<input
type="email"
placeholder="Email"
className="w-full px-4 py-3 rounded-lg text-sm outline-none"
style={{ background: "var(--color-background-alt)", color: "var(--color-foreground)", border: "1px solid var(--color-border)" }}
/>
<input
type="password"
placeholder="Mot de passe"
className="w-full px-4 py-3 rounded-lg text-sm outline-none"
style={{ background: "var(--color-background-alt)", color: "var(--color-foreground)", border: "1px solid var(--color-border)" }}
/>
{showRemember && (
<div className="flex items-center justify-between text-sm">
<label className="flex items-center gap-2" style={{ color: "var(--color-foreground-muted)" }}>
<input type="checkbox" /> Se souvenir
</label>
<a href="#" style={{ color: "var(--color-accent)" }}>Mot de passe oublie ?</a>
</div>
)}
<button
type="submit"
className="w-full py-3 rounded-lg text-sm font-semibold transition-opacity hover:opacity-90"
style={{ background: "var(--color-accent)", color: "var(--color-background)" }}
>
Se connecter
</button>
</form>
<p className="mt-6 text-center text-sm" style={{ color: "var(--color-foreground-muted)" }}>
Pas de compte ?{" "}
<a href="#" className="font-medium" style={{ color: "var(--color-accent)" }}>S'inscrire</a>
</p>
</motion.div>
</div>
</section>
);
}