Identité visuelle officielle Lou-Ka — palette marine #0B1330 / bleu vif #2258FF / orange #FF6A00 / gris #F2F2F2 ; logo « porte entrouverte » (Logo.tsx, favicon + icône PWA sur carré marine) ; wordmark Lou-Ka (Ka orange) ; baseline « La porte d'entrée vers votre prochain chez-vous. » ; héro « Trouvez votre prochain chez-vous. » + rangée des 4 avantages ; Inter partout (fin de Space Grotesk/JetBrains Mono) ; coins très arrondis + pill-shaped + ombres douces (styles.css réécrit, mêmes sélecteurs) ; barre de nav mobile 4 onglets (active orange) ; thème Ka Maps marine/orange + immeuble 3D orange ; PDF (pdfgen.py) et SSR SEO alignés
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
13 changed files +744 −554
modified
frontend/index.html
+3 −3
@@ -9,7 +9,7 @@ | ||
| 9 | 9 | <meta name="viewport" content="width=device-width, initial-scale=1.0, viewport-fit=cover" /> |
| 10 | 10 | <title>Lou-Ka — Logements à louer au Québec</title> |
| 11 | 11 | <meta name="description" content="Lou-Ka agrège les appartements et logements à louer publiés par les gestionnaires immobiliers partout au Québec — Montréal, Québec, Lévis, Gatineau et plus — toujours à jour." /> |
| 12 | − <meta name="theme-color" content="#f5f3ee" /> | |
| 12 | + <meta name="theme-color" content="#ffffff" /> | |
| 13 | 13 | <meta name="mobile-web-app-capable" content="yes" /> |
| 14 | 14 | <meta name="apple-mobile-web-app-capable" content="yes" /> |
| 15 | 15 | <meta name="apple-mobile-web-app-status-bar-style" content="default" /> |
@@ -17,8 +17,8 @@ | ||
| 17 | 17 | <link rel="manifest" href="/manifest.webmanifest" /> |
| 18 | 18 | <link rel="preconnect" href="https://fonts.googleapis.com" /> |
| 19 | 19 | <link rel="preconnect" href="https://fonts.gstatic.com" crossorigin /> |
| 20 | − <link href="https://fonts.googleapis.com/css2?family=Space+Grotesk:wght@400;500;600;700&family=Inter:wght@400;500;600;700&family=JetBrains+Mono:wght@400;500;700&display=swap" rel="stylesheet" /> | |
| 21 | − <link rel="icon" href="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 64 64'%3E%3Crect width='64' height='64' rx='12' fill='%23121712'/%3E%3Ctext x='32' y='45' font-family='Arial Black,sans-serif' font-size='32' font-weight='900' fill='%23d9f26b' text-anchor='middle'%3ELK%3C/text%3E%3C/svg%3E" /> | |
| 20 | + <link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap" rel="stylesheet" /> | |
| 21 | + <link rel="icon" href="data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 64 64'%3E%3Crect width='64' height='64' rx='14' fill='%230B1330'/%3E%3Crect x='19' y='9' width='26' height='46' rx='8' fill='none' stroke='%23FF6A00' stroke-width='4'/%3E%3Cpolygon points='24.5,16 36,13.5 36,49 24.5,46' fill='%23ffffff'/%3E%3Cpolygon points='24.5,46 36,49 42,52.5 24.5,52.5' fill='%23FF6A00'/%3E%3C/svg%3E" /> | |
| 22 | 22 | </head> |
| 23 | 23 | <body> |
| 24 | 24 | <div id="root"></div> |
modified
frontend/public/manifest.webmanifest
+4 −4
@@ -1,15 +1,15 @@ | ||
| 1 | 1 | { |
| 2 | 2 | "name": "Lou-Ka — Logements à louer au Québec", |
| 3 | 3 | "short_name": "Lou-Ka", |
| 4 | − "description": "Tous les logements à louer de Québec et Lévis, un seul endroit.", | |
| 4 | + "description": "La porte d'entrée vers votre prochain chez-vous. Tous les logements à louer au Québec, regroupés au même endroit.", | |
| 5 | 5 | "start_url": "/", |
| 6 | 6 | "display": "standalone", |
| 7 | − "background_color": "#f5f3ee", | |
| 8 | − "theme_color": "#f5f3ee", | |
| 7 | + "background_color": "#ffffff", | |
| 8 | + "theme_color": "#0b1330", | |
| 9 | 9 | "lang": "fr", |
| 10 | 10 | "icons": [ |
| 11 | 11 | { |
| 12 | − "src": "data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 512 512'%3E%3Crect width='512' height='512' rx='96' fill='%23121712'/%3E%3Ctext x='256' y='356' font-family='Arial Black,sans-serif' font-size='256' font-weight='900' fill='%23d9f26b' text-anchor='middle'%3ELK%3C/text%3E%3C/svg%3E", | |
| 12 | + "src": "data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 512 512'%3E%3Crect width='512' height='512' rx='112' fill='%230B1330'/%3E%3Crect x='152' y='72' width='208' height='368' rx='64' fill='none' stroke='%23FF6A00' stroke-width='32'/%3E%3Cpolygon points='196,128 288,108 288,392 196,368' fill='%23ffffff'/%3E%3Cpolygon points='196,368 288,392 336,420 196,420' fill='%23FF6A00'/%3E%3C/svg%3E", | |
| 13 | 13 | "sizes": "512x512", |
| 14 | 14 | "type": "image/svg+xml", |
| 15 | 15 | "purpose": "any" |
modified
frontend/src/App.tsx
+38 −9
@@ -12,8 +12,10 @@ import { | ||
| 12 | 12 | import { AccountProvider, useAccount } from "./account"; |
| 13 | 13 | import CookieConsent from "./components/CookieConsent"; |
| 14 | 14 | import { |
| 15 | − IcoChart, IcoCompass, IcoDoc, IcoFolder, IcoHouse, IcoLock, IcoMap, | |
| 15 | + IcoChart, IcoCompass, IcoDoc, IcoFolder, IcoHeart, IcoHouse, IcoLock, | |
| 16 | + IcoMap, IcoSearch, IcoUser, | |
| 16 | 17 | } from "./components/Icons"; |
| 18 | +import { LogoIcon } from "./components/Logo"; | |
| 17 | 19 | import Home from "./pages/Home"; |
| 18 | 20 | import ListingPage from "./pages/Listing"; |
| 19 | 21 | import BotPage from "./pages/Bot"; |
@@ -97,12 +99,11 @@ function AccountMenu() { | ||
| 97 | 99 | justifyContent: "center", |
| 98 | 100 | width: 18, |
| 99 | 101 | height: 16, |
| 100 | − borderRadius: 4, | |
| 101 | − background: "#141814", | |
| 102 | − color: "#d9f26b", | |
| 103 | − font: "700 9px/1 'Space Grotesk', system-ui, sans-serif", | |
| 102 | + borderRadius: 5, | |
| 103 | + background: "#ff6a00", | |
| 104 | + color: "#ffffff", | |
| 105 | + font: "700 9px/1 'Inter', system-ui, sans-serif", | |
| 104 | 106 | letterSpacing: "-0.02em", |
| 105 | − transform: "rotate(-2deg)", | |
| 106 | 107 | }} |
| 107 | 108 | > |
| 108 | 109 | KA |
@@ -199,8 +200,9 @@ function Header() { | ||
| 199 | 200 | <header className="header"> |
| 200 | 201 | <div className="container header-inner"> |
| 201 | 202 | <NavLink to="/" className="brand" aria-label="Lou-Ka — accueil"> |
| 202 | − Lou<span className="ka">Ka</span> | |
| 203 | − <span className="brand-tag">Québec · Lévis · Montréal — toujours à jour</span> | |
| 203 | + <LogoIcon size={30} /> | |
| 204 | + Lou-<span className="ka">Ka</span> | |
| 205 | + <span className="brand-tag">La porte d'entrée vers votre prochain chez-vous.</span> | |
| 204 | 206 | </NavLink> |
| 205 | 207 | <nav className="nav" aria-label="Navigation principale"> |
| 206 | 208 | <NavLink to="/" end className={({ isActive }) => (isActive ? "active" : "")}> |
@@ -258,7 +260,11 @@ function Footer() { | ||
| 258 | 260 | <footer className="footer"> |
| 259 | 261 | <div className="container"> |
| 260 | 262 | <div className="fbrand"> |
| 261 | − Lou<span className="ka">Ka</span> | |
| 263 | + <LogoIcon size={32} dark /> | |
| 264 | + Lou-<span className="ka">Ka</span> | |
| 265 | + </div> | |
| 266 | + <div className="fbaseline"> | |
| 267 | + La porte d'entrée vers votre prochain <span className="hl">chez-vous.</span> | |
| 262 | 268 | </div> |
| 263 | 269 | <div className="frow"> |
| 264 | 270 | <div> |
@@ -294,6 +300,28 @@ function Footer() { | ||
| 294 | 300 | ); |
| 295 | 301 | } |
| 296 | 302 | |
| 303 | +/** Barre de navigation inférieure (mobile) — icône active en orange. */ | |
| 304 | +function MobileTabBar() { | |
| 305 | + const location = useLocation(); | |
| 306 | + const isCarte = new URLSearchParams(location.search).get("view") === "carte"; | |
| 307 | + const tabs = [ | |
| 308 | + { to: "/", label: "Rechercher", icon: <IcoSearch size={20} />, on: location.pathname === "/" && !isCarte }, | |
| 309 | + { to: "/?view=carte", label: "Carte", icon: <IcoMap size={20} />, on: location.pathname === "/" && isCarte }, | |
| 310 | + { to: "/favoris", label: "Favoris", icon: <IcoHeart size={20} />, on: location.pathname.startsWith("/favoris") }, | |
| 311 | + { to: "/profil", label: "Profil", icon: <IcoUser size={20} />, on: location.pathname.startsWith("/profil") }, | |
| 312 | + ]; | |
| 313 | + return ( | |
| 314 | + <nav className="tabbar" aria-label="Navigation mobile"> | |
| 315 | + {tabs.map((t) => ( | |
| 316 | + <NavLink key={t.label} to={t.to} className={() => (t.on ? "active" : "")}> | |
| 317 | + {t.icon} | |
| 318 | + {t.label} | |
| 319 | + </NavLink> | |
| 320 | + ))} | |
| 321 | + </nav> | |
| 322 | + ); | |
| 323 | +} | |
| 324 | + | |
| 297 | 325 | export default function App() { |
| 298 | 326 | return ( |
| 299 | 327 | <AccountProvider> |
@@ -330,6 +358,7 @@ export default function App() { | ||
| 330 | 358 | </Routes> |
| 331 | 359 | </main> |
| 332 | 360 | <Footer /> |
| 361 | + <MobileTabBar /> | |
| 333 | 362 | <CookieConsent /> |
| 334 | 363 | </AccountProvider> |
| 335 | 364 | ); |
modified
frontend/src/components/Icons.tsx
+12 −5
@@ -1,9 +1,9 @@ | ||
| 1 | 1 | // ----------------------------------------------------------------------------- |
| 2 | 2 | // Lou-Ka — Agrégateur de logements à louer (province de Québec) |
| 3 | 3 | // Auteur : Simon-Pierre Boucher — contact@spboucher.ai |
| 4 | −// components/Icons.tsx : icônes SVG maison « éditorial sharp » | |
| 5 | −// Tracés au trait (stroke) 2 px, coins vifs (square/miter), currentColor — | |
| 6 | −// remplacent les emojis génériques pour coller à l'identité de l'app. | |
| 4 | +// components/Icons.tsx : icônes SVG maison — style linéaire (outline), | |
| 5 | +// trait moyen 2 px, extrémités arrondies, currentColor — conformes à | |
| 6 | +// l'identité visuelle Lou-Ka (minimaliste et chaleureuse). | |
| 7 | 7 | // ----------------------------------------------------------------------------- |
| 8 | 8 | import { SVGProps } from "react"; |
| 9 | 9 | |
@@ -13,8 +13,8 @@ function Base({ size = 16, children, ...rest }: P) { | ||
| 13 | 13 | return ( |
| 14 | 14 | <svg |
| 15 | 15 | width={size} height={size} viewBox="0 0 24 24" fill="none" |
| 16 | − stroke="currentColor" strokeWidth="2" strokeLinecap="square" | |
| 17 | − strokeLinejoin="miter" aria-hidden="true" focusable="false" {...rest} | |
| 16 | + stroke="currentColor" strokeWidth="2" strokeLinecap="round" | |
| 17 | + strokeLinejoin="round" aria-hidden="true" focusable="false" {...rest} | |
| 18 | 18 | > |
| 19 | 19 | {children} |
| 20 | 20 | </svg> |
@@ -163,6 +163,13 @@ export const IcoHeart = (p: P & { filled?: boolean }) => { | ||
| 163 | 163 | |
| 164 | 164 | // -- réseaux sociaux (tracés au trait, même langage que le reste) -------------- |
| 165 | 165 | |
| 166 | +export const IcoUser = (p: P) => ( | |
| 167 | + <Base {...p}> | |
| 168 | + <circle cx="12" cy="8" r="3.5" /> | |
| 169 | + <path d="M5 20c1.2-3.4 3.8-5 7-5s5.8 1.6 7 5" /> | |
| 170 | + </Base> | |
| 171 | +); | |
| 172 | + | |
| 166 | 173 | export const IcoInstagram = (p: P) => ( |
| 167 | 174 | <Base {...p}> |
| 168 | 175 | <rect x="4" y="4" width="16" height="16" rx="4.5" /> |
modified
frontend/src/components/ListingMap3D.tsx
+2 −2
@@ -17,7 +17,7 @@ import { louKaMapTheme } from "../kamaps/theme"; | ||
| 17 | 17 | import { MAPBOX_TOKEN } from "../kamaps/config"; |
| 18 | 18 | |
| 19 | 19 | /** Rouge signal de la fiche — même langage que les badges d'alerte. */ |
| 20 | −export const BUILDING_RED = "#e03131"; | |
| 20 | +export const BUILDING_RED = "#ff6a00"; // orange officiel Lou-Ka | |
| 21 | 21 | |
| 22 | 22 | export default function ListingMap3D({ l }: { l: Listing }) { |
| 23 | 23 | const property = useMemo<MapProperty | null>(() => { |
@@ -41,7 +41,7 @@ export default function ListingMap3D({ l }: { l: Listing }) { | ||
| 41 | 41 | |
| 42 | 42 | return ( |
| 43 | 43 | <div className="lmap3d" role="img" |
| 44 | − aria-label={`Carte 3D — ${l.address || l.title}, bâtiment de l'annonce en rouge`}> | |
| 44 | + aria-label={`Carte 3D — ${l.address || l.title}, bâtiment de l'annonce en orange`}> | |
| 45 | 45 | <KaSpotlightMap |
| 46 | 46 | theme={louKaMapTheme} |
| 47 | 47 | mapboxToken={MAPBOX_TOKEN} |
added
frontend/src/components/Logo.tsx
+62 −0
@@ -0,0 +1,62 @@ | ||
| 1 | +// ----------------------------------------------------------------------------- | |
| 2 | +// Lou-Ka — Agrégateur de logements à louer (province de Québec) | |
| 3 | +// Auteur : Simon-Pierre Boucher — contact@spboucher.ai | |
| 4 | +// components/Logo.tsx : icône officielle Lou-Ka — la porte d'entrée. | |
| 5 | +// Cadre orange #FF6A00 aux coins très arrondis ; porte entrouverte bleu | |
| 6 | +// marine #0B1330 en perspective (ouverture vers la droite) ; tapis de | |
| 7 | +// lumière orange projeté au sol. Effet « liquid glass » subtil. | |
| 8 | +// Baseline : « La porte d'entrée vers votre prochain chez-vous. » | |
| 9 | +// ----------------------------------------------------------------------------- | |
| 10 | + | |
| 11 | +/** Icône seule (fond transparent — pour fonds clairs). */ | |
| 12 | +export function LogoIcon({ size = 30, dark = false }: { size?: number; dark?: boolean }) { | |
| 13 | + // dark = version pour fond bleu marine : la porte devient blanche | |
| 14 | + const door = dark ? "#ffffff" : "#0b1330"; | |
| 15 | + const doorTop = dark ? "#ffffff" : "#16204a"; | |
| 16 | + const uid = dark ? "lk-dark" : "lk-light-bg"; | |
| 17 | + return ( | |
| 18 | + <svg | |
| 19 | + className="logo-ico" | |
| 20 | + width={size} | |
| 21 | + height={size} | |
| 22 | + viewBox="0 0 64 64" | |
| 23 | + fill="none" | |
| 24 | + aria-hidden="true" | |
| 25 | + > | |
| 26 | + <defs> | |
| 27 | + <linearGradient id={`${uid}-door`} x1="0" y1="0" x2="0" y2="1"> | |
| 28 | + <stop offset="0" stopColor={doorTop} /> | |
| 29 | + <stop offset="1" stopColor={door} /> | |
| 30 | + </linearGradient> | |
| 31 | + <linearGradient id={`${uid}-light`} x1="0" y1="0" x2="1" y2="0"> | |
| 32 | + <stop offset="0" stopColor="#ff6a00" /> | |
| 33 | + <stop offset="1" stopColor="#ff6a00" stopOpacity="0.72" /> | |
| 34 | + </linearGradient> | |
| 35 | + <linearGradient id={`${uid}-frame`} x1="0" y1="0" x2="0" y2="1"> | |
| 36 | + <stop offset="0" stopColor="#ff7d1f" /> | |
| 37 | + <stop offset="1" stopColor="#ff6a00" /> | |
| 38 | + </linearGradient> | |
| 39 | + </defs> | |
| 40 | + {/* cadre : rectangle vertical, coins très arrondis, contour orange épais */} | |
| 41 | + <rect x="15" y="5" width="34" height="54" rx="10" stroke={`url(#${uid}-frame)`} strokeWidth="4.5" /> | |
| 42 | + {/* porte entrouverte : parallélogramme en perspective, bord droit plus proche */} | |
| 43 | + <polygon points="22,13.5 37,10.5 37,52 22,48.5" fill={`url(#${uid}-door)`} /> | |
| 44 | + {/* reflet « liquid glass » sur la porte */} | |
| 45 | + <polygon points="24,13.2 28,12.4 28,49 24,48.2" fill="#ffffff" opacity="0.08" /> | |
| 46 | + {/* lumière projetée au sol — tapis d'accueil */} | |
| 47 | + <polygon points="22,48.5 37,52 44.5,55.8 22,55.8" fill={`url(#${uid}-light)`} /> | |
| 48 | + </svg> | |
| 49 | + ); | |
| 50 | +} | |
| 51 | + | |
| 52 | +/** Wordmark complet : icône + « Lou-Ka » (Lou- marine, Ka orange). */ | |
| 53 | +export default function Logo({ size = 30 }: { size?: number }) { | |
| 54 | + return ( | |
| 55 | + <span style={{ display: "inline-flex", alignItems: "center" }}> | |
| 56 | + <LogoIcon size={size} /> | |
| 57 | + <span style={{ color: "#0b1330", fontWeight: 700 }}> | |
| 58 | + Lou-<span style={{ color: "#ff6a00" }}>Ka</span> | |
| 59 | + </span> | |
| 60 | + </span> | |
| 61 | + ); | |
| 62 | +} | |
modified
frontend/src/kamaps/theme.ts
+43 −43
@@ -2,75 +2,75 @@ | ||
| 2 | 2 | // Author: Simon-Pierre Boucher |
| 3 | 3 | // Contact: contact@spboucher.ai |
| 4 | 4 | // Project: Groupe Ka / Ka Maps (Lou-Ka integration) |
| 5 | −// kamaps/theme.ts : thème Lou-Ka Maps — les jetons du design system | |
| 6 | −// (encre/lime/vert « éditorial sharp ») appliqués au framework Ka Maps. | |
| 5 | +// kamaps/theme.ts : thème Lou-Ka Maps — identité officielle Lou-Ka | |
| 6 | +// (marine #0B1330 / bleu vif #2258FF / orange #FF6A00) appliquée à Ka Maps. | |
| 7 | 7 | // ----------------------------------------------------------------------------- |
| 8 | 8 | import type { KaMapTheme } from "@groupe-ka/ka-maps"; |
| 9 | 9 | |
| 10 | −const INK = "#141814"; | |
| 11 | −const PAPER = "#f5f3ee"; | |
| 12 | −const GREEN = "#1c5c41"; | |
| 13 | −const LIME = "#d9f26b"; | |
| 10 | +const NAVY = "#0b1330"; | |
| 11 | +const BLUE = "#2258ff"; | |
| 12 | +const ORANGE = "#ff6a00"; | |
| 13 | +const WHITE = "#ffffff"; | |
| 14 | 14 | |
| 15 | 15 | export const louKaMapTheme: KaMapTheme = { |
| 16 | 16 | id: "lou-ka", |
| 17 | 17 | productName: "Lou-Ka Maps", |
| 18 | − accent: GREEN, | |
| 19 | − onAccent: LIME, | |
| 18 | + accent: BLUE, | |
| 19 | + onAccent: WHITE, | |
| 20 | 20 | fontFamily: |
| 21 | 21 | '"Inter", system-ui, -apple-system, "Segoe UI", sans-serif', |
| 22 | 22 | markers: { |
| 23 | − // Prix : pastille encre, texte BLANC — contraste maximal sur fond clair. | |
| 24 | − // Le lime n'apparaît qu'à la sélection (le moment de marque). | |
| 23 | + // Prix : pastille bleu marine, texte BLANC — contraste maximal sur fond clair. | |
| 24 | + // L'orange n'apparaît qu'à la sélection (le moment de marque). | |
| 25 | 25 | sale: { |
| 26 | − background: INK, | |
| 27 | − text: "#ffffff", | |
| 26 | + background: NAVY, | |
| 27 | + text: WHITE, | |
| 28 | 28 | halo: "rgba(255,255,255,0.45)", |
| 29 | − selectedBackground: LIME, | |
| 30 | − selectedText: INK, | |
| 29 | + selectedBackground: ORANGE, | |
| 30 | + selectedText: WHITE, | |
| 31 | 31 | }, |
| 32 | 32 | rent: { |
| 33 | − background: INK, | |
| 34 | − text: "#ffffff", | |
| 33 | + background: NAVY, | |
| 34 | + text: WHITE, | |
| 35 | 35 | halo: "rgba(255,255,255,0.45)", |
| 36 | − selectedBackground: LIME, | |
| 37 | − selectedText: INK, | |
| 36 | + selectedBackground: ORANGE, | |
| 37 | + selectedText: WHITE, | |
| 38 | 38 | }, |
| 39 | 39 | highlight: { |
| 40 | − background: GREEN, | |
| 41 | − text: "#ffffff", | |
| 40 | + background: BLUE, | |
| 41 | + text: WHITE, | |
| 42 | 42 | halo: "rgba(255,255,255,0.45)", |
| 43 | − selectedBackground: LIME, | |
| 44 | − selectedText: INK, | |
| 43 | + selectedBackground: ORANGE, | |
| 44 | + selectedText: WHITE, | |
| 45 | 45 | }, |
| 46 | 46 | }, |
| 47 | 47 | cluster: { |
| 48 | − background: INK, | |
| 49 | − text: "#ffffff", | |
| 50 | − border: LIME, | |
| 48 | + background: NAVY, | |
| 49 | + text: WHITE, | |
| 50 | + border: ORANGE, | |
| 51 | 51 | }, |
| 52 | − // Cartographie Lou-Ka : fond neutre et raffiné — papier chaud discret, | |
| 53 | − // eau bleu-gris désaturé, parcs verts subtils, bâtiments bien définis. | |
| 52 | + // Cartographie Lou-Ka : fond neutre et raffiné — gris très pâle, | |
| 53 | + // eau bleu désaturé, parcs verts subtils, bâtiments bien définis. | |
| 54 | 54 | // Les prix restent l'élément dominant de la carte. |
| 55 | 55 | basemapOverrides: { |
| 56 | 56 | light: { |
| 57 | − background: "#f6f5f1", | |
| 58 | − residential: "#efeee8", | |
| 59 | − water: "#c3d6df", | |
| 60 | − waterway: "#b8cdd8", | |
| 61 | − park: "#dde8d1", | |
| 62 | − wood: "#d2e0c4", | |
| 63 | − building: "#e7e4db", | |
| 64 | − buildingOutline: "#d2cec1", | |
| 57 | + background: "#f7f8fa", | |
| 58 | + residential: "#f0f1f4", | |
| 59 | + water: "#c9d8ef", | |
| 60 | + waterway: "#bfd0ea", | |
| 61 | + park: "#dce8d8", | |
| 62 | + wood: "#d0e0ca", | |
| 63 | + building: "#e6e8ee", | |
| 64 | + buildingOutline: "#d0d3dd", | |
| 65 | 65 | road: "#ffffff", |
| 66 | − roadCasing: "#dcd8cc", | |
| 67 | − motorway: "#f0e9d0", | |
| 68 | − boundary: "#b0a998", | |
| 69 | − label: "#474b45", | |
| 70 | − labelHalo: "rgba(246,245,241,0.92)", | |
| 71 | − cityLabel: "#1f231e", | |
| 72 | − roadLabel: "#8b8d82", | |
| 73 | − waterLabel: "#5c7c8c", | |
| 66 | + roadCasing: "#dcdee6", | |
| 67 | + motorway: "#f4ede2", | |
| 68 | + boundary: "#a9adbd", | |
| 69 | + label: "#3e4560", | |
| 70 | + labelHalo: "rgba(247,248,250,0.92)", | |
| 71 | + cityLabel: "#0b1330", | |
| 72 | + roadLabel: "#8a90a5", | |
| 73 | + waterLabel: "#5c74a8", | |
| 74 | 74 | }, |
| 75 | 75 | }, |
| 76 | 76 | supportsDark: false, |
modified
frontend/src/pages/Home.tsx
+25 −8
@@ -15,7 +15,8 @@ import { | ||
| 15 | 15 | import ListingCard from "../components/ListingCard"; |
| 16 | 16 | import Pager from "../components/Pager"; |
| 17 | 17 | import { |
| 18 | − IcoAlert, IcoBolt, IcoList, IcoMap, IcoPaw, IcoSearch, IcoSliders, IcoSofa, | |
| 18 | + IcoAlert, IcoBolt, IcoHeart, IcoHouse, IcoList, IcoMap, IcoPaw, IcoPin, | |
| 19 | + IcoSearch, IcoSliders, IcoSofa, | |
| 19 | 20 | } from "../components/Icons"; |
| 20 | 21 | |
| 21 | 22 | // La carte (MapLibre, ~220 ko) n'est chargée que si l'utilisateur l'ouvre |
@@ -196,16 +197,32 @@ export default function Home() { | ||
| 196 | 197 | return ( |
| 197 | 198 | <div className="container"> |
| 198 | 199 | <section className="hero"> |
| 199 | − <span className="kicker">Agrégateur — Québec · Lévis · Montréal</span> | |
| 200 | + <span className="kicker">La porte d'entrée vers votre prochain chez-vous.</span> | |
| 200 | 201 | <h1> |
| 201 | − Tous les logements <span className="outline">à louer</span>,<br /> | |
| 202 | − <span className="hl">un seul</span> endroit. | |
| 202 | + Trouvez votre prochain <span className="hl">chez-vous.</span> | |
| 203 | 203 | </h1> |
| 204 | 204 | <p className="lede"> |
| 205 | − Lou-Ka rassemble les appartements affichés par les gestionnaires immobiliers du | |
| 206 | − Québec — Québec, Lévis et le Grand Montréal — mis à jour automatiquement, avec | |
| 207 | − toutes les photos et un lien direct vers l'annonce originale. | |
| 205 | + Tous les logements à louer au Québec, regroupés au même endroit — mis à jour | |
| 206 | + automatiquement, avec toutes les photos et un lien direct vers l'annonce originale. | |
| 208 | 207 | </p> |
| 208 | + <div className="benefits" aria-label="Avantages"> | |
| 209 | + <div className="benefit"> | |
| 210 | + <span className="benefit-ico"><IcoHouse size={20} /></span> | |
| 211 | + <span className="benefit-label">Nouveaux logements</span> | |
| 212 | + </div> | |
| 213 | + <div className="benefit"> | |
| 214 | + <span className="benefit-ico"><IcoSearch size={20} /></span> | |
| 215 | + <span className="benefit-label">Recherche facile</span> | |
| 216 | + </div> | |
| 217 | + <div className="benefit"> | |
| 218 | + <span className="benefit-ico"><IcoHeart size={20} /></span> | |
| 219 | + <span className="benefit-label">Favoris et alertes</span> | |
| 220 | + </div> | |
| 221 | + <div className="benefit"> | |
| 222 | + <span className="benefit-ico blue"><IcoPin size={20} /></span> | |
| 223 | + <span className="benefit-label">Partout au Québec</span> | |
| 224 | + </div> | |
| 225 | + </div> | |
| 209 | 226 | <div className="stat-row"> |
| 210 | 227 | <span className="stat-chip"><span className="pulse" /> Données synchronisées en continu</span> |
| 211 | 228 | {stats && ( |
@@ -245,7 +262,7 @@ export default function Home() { | ||
| 245 | 262 | <div className="f-search"> |
| 246 | 263 | <IcoSearch size={15} strokeWidth={2.4} /> |
| 247 | 264 | <input |
| 248 | − id="f-q" placeholder="Adresse, quartier, rue…" value={q} | |
| 265 | + id="f-q" placeholder="Ville, quartier ou code postal" value={q} | |
| 249 | 266 | onChange={(e) => setQ(e.target.value)} |
| 250 | 267 | aria-label="Recherche" |
| 251 | 268 | /> |
modified
frontend/src/pages/Listing.tsx
+1 −1
@@ -342,7 +342,7 @@ export default function ListingPage() { | ||
| 342 | 342 | <ListingMap3D l={l} /> |
| 343 | 343 | </Suspense> |
| 344 | 344 | <p className="fine"> |
| 345 | − Vue 3D du secteur — l'immeuble de l'annonce est surligné en rouge. | |
| 345 | + Vue 3D du secteur — l'immeuble de l'annonce est surligné en orange. | |
| 346 | 346 | Position selon l'adresse géocodée (Adresses Québec). |
| 347 | 347 | </p> |
| 348 | 348 | </section> |
modified
frontend/src/styles.css
+537 −462
Large diff (1,790 lines) is not loaded by default to keep the page fast.Load diff
modified
frontend/tsconfig.tsbuildinfo
+1 −1
Large diff (4 lines) is not loaded by default to keep the page fast.Load diff
modified
louka/pdfgen.py
+15 −15
Large diff (47 lines) is not loaded by default to keep the page fast.Load diff
modified
louka/seo.py
+1 −1
Large diff (9 lines) is not loaded by default to keep the page fast.Load diff