Python 51.6%
TypeScript 46.7%
CSS 1.7%
1import Image from "next/image";2import { OTHERS, party, partyVar, partyLabel, partyName } from "@/lib/parties";3import { cls } from "@/lib/format";45/** Logo officiel du parti, jamais déformé ni recoloré. Le PCQ (logo blanc) est posé sur sa pastille marine officielle. */6export function PartyLogo({ id, height = 20, className, white = false }: { id: string | null | undefined; height?: number; className?: string; white?: boolean }) {7 const p = party(id);8 if (!p) return <PartyBadge id={id} className={className} />;9 const width = Math.round(height * p.logoRatio);10 const src = white && p.logoWhite ? p.logoWhite : p.logo;11 // thème sombre : variante blanche officielle quand elle existe (le marine du PQ disparaît sur fond noir)12 const img = p.logoWhite && !white ? (13 <>14 <Image src={p.logo} alt={`Logo officiel — ${p.officialName}`} width={width} height={height} className="object-contain dark:hidden" style={{ height, width: "auto", maxWidth: width }} unoptimized />15 <Image src={p.logoWhite} alt="" aria-hidden width={width} height={height} className="object-contain hidden dark:inline" style={{ height, width: "auto", maxWidth: width }} unoptimized />16 </>17 ) : (18 <Image src={src} alt={`Logo officiel — ${p.officialName}`} width={width} height={height} className="object-contain" style={{ height, width: "auto", maxWidth: width }} unoptimized />19 );20 if (p.logoBackdrop && !white) {21 return (22 <span className={cls("inline-flex items-center rounded-[6px] px-2 py-1", className)} style={{ background: p.logoBackdrop }} title={p.officialName}>23 {img}24 </span>25 );26 }27 return <span className={cls("inline-flex items-center", className)} title={p.officialName}>{img}</span>;28}2930/** Pastille sigle + couleur (accessibilité : texte toujours présent). */31export function PartyBadge({ id, className, size = "md" }: { id: string | null | undefined; className?: string; size?: "sm" | "md" | "lg" }) {32 const color = partyVar(id);33 const label = partyLabel(id);34 const sz = size === "sm" ? "text-[10px] px-1.5 py-[2px]" : size === "lg" ? "text-sm px-2.5 py-1" : "text-[11px] px-2 py-[3px]";35 return (36 <span className={cls("inline-flex items-center gap-1.5 rounded-[6px] font-semibold tracking-wide text-white num", sz, className)} style={{ background: color }} title={partyName(id)} aria-label={partyName(id)}>37 {label}38 </span>39 );40}4142export function PartyDot({ id, size = 8, className }: { id: string | null | undefined; size?: number; className?: string }) {43 return <span aria-hidden className={cls("inline-block rounded-full shrink-0", className)} style={{ width: size, height: size, background: partyVar(id) }} />;44}4546export function PartyText({ id, full = false, className }: { id: string | null | undefined; full?: boolean; className?: string }) {47 return (48 <span className={cls("inline-flex items-center gap-1.5", className)}>49 <PartyDot id={id} />50 <span className="font-semibold">{full ? partyName(id) : partyLabel(id)}</span>51 </span>52 );53}5455export { OTHERS };56