templates/application/whileresume/application/enterprises/components/header.html.twig line 1

Open in your IDE?
  1. {# =========================================================
  2.    HEADER WhileResume — thème Sociala (v2)
  3.    - Utilise les classes natives Sociala (.nav-menu, .menu-icon,
  4.      .center-menu-icon) → pas de conflit avec le JS qui toggle .active
  5.    - CTA login : pill noire bien placée (mobile + desktop)
  6.    - User connecté : avatar + nom dans une pill grise (desktop)
  7.    - Plus de doublon de bouton login (séparation propre mobile/desktop)
  8.    - Hamburger animé natif Sociala respecté
  9.    - iOS / Android : dropdown vers le bas avec liste pays + search
  10.    ========================================================= #}
  11. {# Liens stores : source unique = table cvs_app_store_links #}
  12. {% set _hdrStoreData = getAppStoreCountries() %}
  13. {% set _hdrStorePrimary = _hdrStoreData.primary|default({}) %}
  14. {% set _hdrStoreOthers = _hdrStoreData.others|default({}) %}
  15. <style>
  16.     /* ============================================================
  17.        FIX rightbar Sociala
  18.        ------------------------------------------------------------
  19.        Le CSS Sociala met `.right-chat { display: none }` par défaut.
  20.        La classe `.active-sidebar` (ajoutée par scripts.js ≥1600px,
  21.        ou par le toggle au clic) DEVRAIT débloquer l'affichage,
  22.        mais dans notre install ça ne se fait pas (override CSS).
  23.        On force ici l'affichage quand active-sidebar est présente.
  24.        ============================================================ */
  25.     .right-chat.active-sidebar {
  26.         display: block !important;
  27.     }
  28.     /* ---------- Tweaks Sociala header ---------- */
  29.     /* Le `<a>` logo a un line-height:90px et width:280px par défaut Sociala
  30.        (sert d'ancre pour la sidebar) — on garde ça mais on neutralise sur mobile */
  31.     .whr-header .whr-logo-link img {
  32.         max-width: 160px;
  33.         height: auto;
  34.         display: block;
  35.     }
  36.     @media (max-width: 991.98px) {
  37.         .whr-header .whr-logo-link img { max-width: 130px; }
  38.     }
  39.     /* CTA Connexion : pill noire propre */
  40.     .whr-cta-login {
  41.         display: inline-flex;
  42.         align-items: center;
  43.         gap: 6px;
  44.         padding: 8px 14px;
  45.         background: #111;
  46.         color: #fff !important;
  47.         font-weight: 600;
  48.         font-size: 13px;
  49.         line-height: 1;
  50.         border-radius: 999px;
  51.         text-decoration: none !important;
  52.         transition: transform .15s ease, background .2s ease;
  53.         white-space: nowrap;
  54.     }
  55.     .whr-cta-login:hover { background: #2c2c46; transform: translateY(-1px); color: #fff; }
  56.     .whr-cta-login i { font-size: 14px; }
  57.     @media (max-width: 480px) {
  58.         .whr-cta-login .whr-cta-label { display: none; }
  59.         .whr-cta-login { padding: 8px 10px; }
  60.     }
  61.     /* User pill (avatar + prénom) — desktop uniquement */
  62.     .whr-user-menu {
  63.         display: inline-flex;
  64.         align-items: center;
  65.         gap: 8px;
  66.         padding: 4px 12px 4px 4px;
  67.         background: #f5f6fa;
  68.         border-radius: 999px;
  69.         text-decoration: none !important;
  70.         transition: background .2s ease;
  71.         margin-left: 8px;
  72.     }
  73.     .whr-user-menu:hover { background: #ececf3; }
  74.     .whr-user-menu img {
  75.         width: 32px; height: 32px;
  76.         border-radius: 50%;
  77.         object-fit: cover;
  78.     }
  79.     .whr-user-menu .whr-user-name {
  80.         font-weight: 600;
  81.         font-size: 13px;
  82.         color: #2c2c46;
  83.         max-width: 140px;
  84.         overflow: hidden;
  85.         text-overflow: ellipsis;
  86.         white-space: nowrap;
  87.     }
  88.     .theme-dark .whr-user-menu { background: #2a2a3c; }
  89.     .theme-dark .whr-user-menu:hover { background: #34344a; }
  90.     .theme-dark .whr-user-menu .whr-user-name { color: #fff; }
  91.     /* Wrapper actions mobile (chat ou login) — visible <992px uniquement */
  92.     .whr-mobile-actions {
  93.         display: none;
  94.         align-items: center;
  95.         gap: 8px;
  96.         margin-left: auto;
  97.         margin-right: 12px;
  98.     }
  99.     @media (max-width: 991.98px) {
  100.         .whr-mobile-actions { display: inline-flex; }
  101.     }
  102.     /* Wrapper actions desktop — visible >=992px uniquement */
  103.     .whr-desktop-actions {
  104.         display: none;
  105.         align-items: center;
  106.         gap: 8px;
  107.         margin-left: auto;
  108.     }
  109.     @media (min-width: 992px) {
  110.         .whr-desktop-actions { display: inline-flex; }
  111.     }
  112.     /* Icône bouton ronde (chat mobile) */
  113.     .whr-icon-btn {
  114.         width: 38px; height: 38px;
  115.         border-radius: 12px;
  116.         background: #f5f6fa;
  117.         display: inline-flex;
  118.         align-items: center;
  119.         justify-content: center;
  120.         color: #2c2c46;
  121.         text-decoration: none !important;
  122.         transition: background .2s ease;
  123.     }
  124.     .whr-icon-btn:hover { background: #ececf3; }
  125.     .whr-icon-btn i { font-size: 18px; }
  126.     .theme-dark .whr-icon-btn { background: #2a2a3c; color: #fff; }
  127.     /* ============================================================
  128.        === Stores dropdowns (header) — version "icône ronde" ===
  129.        ============================================================ */
  130.     /* Wrapper du bouton store (icône) + dropdown */
  131.     .whr-hdr-store-wrap {
  132.         position: relative;
  133.         display: inline-block;
  134.     }
  135.     /* Le bouton "icône ronde" du header — version <button> stylée pour
  136.        ressembler au <a class="menu-icon center-menu-icon"> existant */
  137.     .whr-hdr-store-btn {
  138.         background: transparent;
  139.         border: none;
  140.         padding: 0.5rem;
  141.         text-align: center;
  142.         cursor: pointer;
  143.         font-family: inherit;
  144.     }
  145.     .whr-hdr-store-btn:focus { outline: none; }
  146.     .whr-hdr-store-btn:focus-visible {
  147.         outline: 2px solid var(--theme-color, #6C3AED);
  148.         outline-offset: 2px;
  149.         border-radius: 12px;
  150.     }
  151.     /* Dropdown vers le BAS (puisque le bouton est en haut) */
  152.     .whr-hdr-store-dropdown {
  153.         position: absolute;
  154.         top: calc(100% + 6px);
  155.         left: 50%;
  156.         transform: translateX(-50%);
  157.         width: 380px;
  158.         max-width: calc(100vw - 32px);
  159.         background: #fff;
  160.         border-radius: 12px;
  161.         box-shadow: 0 8px 24px rgba(0,0,0,.15), 0 2px 6px rgba(0,0,0,.08);
  162.         z-index: 1050;
  163.         display: none;
  164.         overflow: hidden;
  165.     }
  166.     .theme-dark .whr-hdr-store-dropdown {
  167.         background: #34344a;
  168.         box-shadow: 0 8px 24px rgba(0,0,0,.4), 0 2px 6px rgba(0,0,0,.2);
  169.     }
  170.     .whr-hdr-store-wrap.is-open .whr-hdr-store-dropdown {
  171.         display: flex;
  172.         flex-direction: column;
  173.         animation: whrHdrFadeInDown .15s ease;
  174.     }
  175.     @keyframes whrHdrFadeInDown {
  176.         from { opacity: 0; transform: translateX(-50%) translateY(-4px); }
  177.         to   { opacity: 1; transform: translateX(-50%) translateY(0); }
  178.     }
  179.     /* Petite flèche "tail" en haut du dropdown (pointe vers le bouton) */
  180.     .whr-hdr-store-dropdown::before {
  181.         content: '';
  182.         position: absolute;
  183.         top: -6px;
  184.         left: 50%;
  185.         transform: translateX(-50%) rotate(45deg);
  186.         width: 12px;
  187.         height: 12px;
  188.         background: #fff;
  189.         border-radius: 2px;
  190.     }
  191.     .theme-dark .whr-hdr-store-dropdown::before { background: #34344a; }
  192.     /* Zone search en haut */
  193.     .whr-hdr-store-search-wrap {
  194.         padding: 10px 10px 6px;
  195.         border-bottom: 1px solid rgba(0,0,0,.06);
  196.         flex-shrink: 0;
  197.     }
  198.     .theme-dark .whr-hdr-store-search-wrap { border-bottom-color: rgba(255,255,255,.08); }
  199.     .whr-hdr-store-search {
  200.         width: 100%;
  201.         height: 34px;
  202.         padding: 0 12px 0 32px;
  203.         border: 1px solid rgba(0,0,0,.1);
  204.         border-radius: 8px;
  205.         background: #f5f5f8 url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 24 24' fill='none' stroke='%23888' stroke-width='2' stroke-linecap='round' stroke-linejoin='round'><circle cx='11' cy='11' r='8'/><line x1='21' y1='21' x2='16.65' y2='16.65'/></svg>") no-repeat 10px center;
  206.         font-size: 13px;
  207.         color: #2c2c46;
  208.         outline: none;
  209.         transition: border-color .15s ease, background-color .15s ease;
  210.         font-family: inherit;
  211.     }
  212.     .whr-hdr-store-search:focus {
  213.         border-color: var(--theme-color, #6C3AED);
  214.         background-color: #fff;
  215.     }
  216.     .theme-dark .whr-hdr-store-search {
  217.         background-color: #2a2a3c;
  218.         border-color: rgba(255,255,255,.1);
  219.         color: #e9e9ef;
  220.     }
  221.     .theme-dark .whr-hdr-store-search:focus { background-color: #3c3c52; }
  222.     .whr-hdr-store-search::placeholder { color: #999; }
  223.     /* Featured pinné */
  224.     .whr-hdr-store-featured {
  225.         padding: 8px 8px 4px;
  226.         flex-shrink: 0;
  227.         border-bottom: 1px solid rgba(0,0,0,.06);
  228.     }
  229.     .theme-dark .whr-hdr-store-featured { border-bottom-color: rgba(255,255,255,.08); }
  230.     /* Zone "Other regions" (scrollable) */
  231.     .whr-hdr-store-others {
  232.         padding: 8px;
  233.         max-height: 280px;
  234.         overflow-y: auto;
  235.         flex: 1;
  236.     }
  237.     .whr-hdr-store-others::-webkit-scrollbar { width: 6px; }
  238.     .whr-hdr-store-others::-webkit-scrollbar-thumb { background: rgba(0,0,0,.15); border-radius: 3px; }
  239.     .theme-dark .whr-hdr-store-others::-webkit-scrollbar-thumb { background: rgba(255,255,255,.15); }
  240.     /* Header de section */
  241.     .whr-hdr-store-dropdown-header {
  242.         font-size: 10px;
  243.         font-weight: 700;
  244.         text-transform: uppercase;
  245.         letter-spacing: .5px;
  246.         opacity: .55;
  247.         padding: 4px 8px 6px;
  248.         color: #2c2c46;
  249.     }
  250.     .theme-dark .whr-hdr-store-dropdown-header { color: #e9e9ef; }
  251.     /* Grille 2 colonnes */
  252.     .whr-hdr-store-grid {
  253.         display: grid;
  254.         grid-template-columns: 1fr 1fr;
  255.         gap: 2px;
  256.     }
  257.     /* Item pays */
  258.     .whr-hdr-store-country {
  259.         display: flex;
  260.         align-items: center;
  261.         gap: 8px;
  262.         padding: 7px 9px;
  263.         border-radius: 6px;
  264.         text-decoration: none !important;
  265.         color: #2c2c46 !important;
  266.         font-size: 12.5px;
  267.         transition: background .15s ease;
  268.         min-width: 0;
  269.     }
  270.     .theme-dark .whr-hdr-store-country { color: #e9e9ef !important; }
  271.     .whr-hdr-store-country:hover {
  272.         background: rgba(108, 58, 237, .08);
  273.         color: var(--theme-color, #6C3AED) !important;
  274.     }
  275.     .theme-dark .whr-hdr-store-country:hover { background: rgba(108, 58, 237, .2); }
  276.     .whr-hdr-store-country .whr-flag {
  277.         font-size: 16px;
  278.         line-height: 1;
  279.         width: 18px;
  280.         text-align: center;
  281.         flex-shrink: 0;
  282.     }
  283.     .whr-hdr-store-country .whr-country-name {
  284.         flex: 1;
  285.         font-weight: 500;
  286.         white-space: nowrap;
  287.         overflow: hidden;
  288.         text-overflow: ellipsis;
  289.         min-width: 0;
  290.     }
  291.     /* Featured = pleine largeur, mis en avant */
  292.     .whr-hdr-store-featured .whr-hdr-store-country {
  293.         background: linear-gradient(135deg, rgba(108, 58, 237, .08), rgba(108, 58, 237, .03));
  294.         font-weight: 600;
  295.         padding: 9px 10px;
  296.     }
  297.     .theme-dark .whr-hdr-store-featured .whr-hdr-store-country {
  298.         background: linear-gradient(135deg, rgba(108, 58, 237, .25), rgba(108, 58, 237, .1));
  299.     }
  300.     /* Message "aucun résultat" */
  301.     .whr-hdr-store-empty {
  302.         text-align: center;
  303.         padding: 20px 12px;
  304.         font-size: 12px;
  305.         color: #999;
  306.         font-style: italic;
  307.     }
  308.     .theme-dark .whr-hdr-store-empty { color: #aaa; }
  309.     /* Item caché par la recherche */
  310.     .whr-hdr-store-country.is-hidden { display: none; }
  311.     /* Responsive : sur mobile, ajuster la position et la largeur */
  312.     @media (max-width: 575.98px) {
  313.         .whr-hdr-store-dropdown {
  314.             width: calc(100vw - 24px);
  315.             max-width: 360px;
  316.             /* Sur mobile, on cale à gauche pour ne pas déborder à droite */
  317.             left: 0;
  318.             transform: none;
  319.         }
  320.         .whr-hdr-store-wrap.is-open .whr-hdr-store-dropdown {
  321.             animation: whrHdrFadeInDownMobile .15s ease;
  322.         }
  323.         @keyframes whrHdrFadeInDownMobile {
  324.             from { opacity: 0; transform: translateY(-4px); }
  325.             to   { opacity: 1; transform: translateY(0); }
  326.         }
  327.         .whr-hdr-store-dropdown::before {
  328.             left: 22px;
  329.             transform: rotate(45deg);
  330.         }
  331.         .whr-hdr-store-grid { grid-template-columns: 1fr; }
  332.     }
  333. </style>
  334. <div class="nav-header bg-white shadow-xs border-0 whr-header">
  335.     {# === Bandeau supérieur (mobile : tout, desktop : juste le logo qui sert d'ancre sidebar) === #}
  336.     <div class="nav-top">
  337.         <a href="{% if app.request.locale == 'en' %}{{ path('whileresume_homepage') }}{% else %}{{ path('locale_whileresume_homepage', {'_locale': app.request.locale}) }}{% endif %}"
  338.            class="whr-logo-link"
  339.            aria-label="{{ websitename }}">
  340.             <img src="/uploads/logo.png" alt="{{ websitename }}" />
  341.         </a>
  342.         {# --- Actions visibles uniquement <992px --- #}
  343.         {% if connectUser %}
  344.             {# Structure native Sociala : mob-menu + chat-active-btn → ouvre .right-chat #}
  345.             <a href="#" class="mob-menu ms-auto me-2 chat-active-btn" aria-label="Messages">
  346.                 <i class="feather-message-circle text-grey-900 font-sm btn-round-md bg-greylight"></i>
  347.             </a>
  348.         {% else %}
  349.             <div class="whr-mobile-actions">
  350.                 <a href="{% if app.request.locale == 'en' %}{{ path('app_login') }}{% else %}{{ path('locale_app_login', {'_locale': app.request.locale}) }}{% endif %}"
  351.                    class="whr-cta-login">
  352.                     <i class="feather-log-in"></i>
  353.                     <span class="whr-cta-label">{{ 'layout.signin'|trans({}, 'whr-public') }}</span>
  354.                 </a>
  355.             </div>
  356.         {% endif %}
  357.         {# Hamburger natif Sociala : on NE TOUCHE PAS, son JS gère .active #}
  358.         <button class="nav-menu me-0 ms-2" aria-label="Menu"></button>
  359.     </div>
  360.     {# === Icônes centrales (desktop uniquement, masquées <1200px par Sociala) === #}
  361.     <a href="{% if app.request.locale == 'en' %}{{ path('whileresume_homepage') }}{% else %}{{ path('locale_whileresume_homepage', {'_locale': app.request.locale}) }}{% endif %}"
  362.        class="p-2 text-center ms-3 menu-icon center-menu-icon"
  363.        aria-label="{{ 'layout.home'|trans({}, 'whr-public')|default('Accueil') }}">
  364.         <i class="feather-home font-lg bg-greylight btn-round-lg theme-dark-bg text-grey-500"></i>
  365.     </a>
  366.     {# ============================================================
  367.        === Bouton iOS / App Store ===
  368.        - Version FR : lien direct vers le store FR (pas de dropdown)
  369.        - Version EN : bouton qui ouvre le dropdown pays
  370.        ============================================================ #}
  371.     {% set _hdrHasIos = false %}
  372.     {% for c in _hdrStorePrimary %}{% if c.ios %}{% set _hdrHasIos = true %}{% endif %}{% endfor %}
  373.     {% for c in _hdrStoreOthers %}{% if c.ios %}{% set _hdrHasIos = true %}{% endif %}{% endfor %}
  374.     {% if _hdrHasIos %}
  375.         {# === Dropdown pays (FR & EN) === #}
  376.         <div class="whr-hdr-store-wrap menu-icon center-menu-icon" data-whr-hdr-store="ios">
  377.             <button type="button" class="whr-hdr-store-btn" aria-haspopup="true" aria-expanded="false" aria-label="App Store - Choose your country">
  378.                     <span class="font-lg bg-greylight btn-round-lg theme-dark-bg d-inline-flex align-items-center justify-content-center">
  379.                         <svg fill="#adb5bc" width="22" height="22" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg" aria-hidden="true">
  380.                             <path d="M18.71 19.5C17.88 20.74 17 21.95 15.66 21.97C14.32 22 13.89 21.18 12.37 21.18C10.84 21.18 10.37 21.95 9.09997 22C7.78997 22.05 6.79997 20.68 5.95997 19.47C4.24997 17 2.93997 12.45 4.69997 9.39C5.56997 7.87 7.12997 6.91 8.81997 6.88C10.1 6.86 11.32 7.75 12.11 7.75C12.89 7.75 14.37 6.68 15.92 6.84C16.57 6.87 18.39 7.1 19.56 8.82C19.47 8.88 17.39 10.1 17.41 12.63C17.44 15.65 20.06 16.66 20.09 16.67C20.06 16.74 19.67 18.11 18.71 19.5ZM13 3.5C13.73 2.67 14.94 2.04 15.94 2C16.07 3.17 15.6 4.35 14.9 5.19C14.21 6.04 13.07 6.7 11.95 6.61C11.8 5.46 12.36 4.26 13 3.5Z"/>
  381.                         </svg>
  382.                     </span>
  383.             </button>
  384.             <div class="whr-hdr-store-dropdown" role="menu">
  385.                 {# Search bar (apparaît si > 20 pays "others") #}
  386.                 {% set _hdrIosOthersCount = 0 %}
  387.                 {% for c in _hdrStoreOthers %}{% if c.ios %}{% set _hdrIosOthersCount = _hdrIosOthersCount + 1 %}{% endif %}{% endfor %}
  388.                 {% if _hdrIosOthersCount > 20 %}
  389.                     <div class="whr-hdr-store-search-wrap">
  390.                         <input type="text"
  391.                                class="whr-hdr-store-search"
  392.                                placeholder="{{ 'layout.search_country'|trans({}, 'whr-public')|default('Search country...') }}"
  393.                                aria-label="Search country"
  394.                                autocomplete="off">
  395.                     </div>
  396.                 {% endif %}
  397.                 {# Featured pinné #}
  398.                 {% set _hdrIosPrimaryCount = 0 %}
  399.                 {% for c in _hdrStorePrimary %}{% if c.ios %}{% set _hdrIosPrimaryCount = _hdrIosPrimaryCount + 1 %}{% endif %}{% endfor %}
  400.                 {% if _hdrIosPrimaryCount > 0 %}
  401.                     <div class="whr-hdr-store-featured">
  402.                         <div class="whr-hdr-store-dropdown-header">
  403.                             {{ 'layout.featured'|trans({}, 'whr-public')|default('Featured') }}
  404.                         </div>
  405.                         {% for code, country in _hdrStorePrimary %}
  406.                             {% if country.ios %}
  407.                                 <a href="{{ country.ios }}"
  408.                                    class="whr-hdr-store-country"
  409.                                    data-search="{{ country.label|lower }} {{ code|lower }}"
  410.                                    target="_blank" rel="noopener" role="menuitem">
  411.                                     {% if country.flag %}<span class="whr-flag">{{ country.flag }}</span>{% endif %}
  412.                                     <span class="whr-country-name">{{ country.label }}</span>
  413.                                 </a>
  414.                             {% endif %}
  415.                         {% endfor %}
  416.                     </div>
  417.                 {% endif %}
  418.                 {# Other regions (grille 2 cols) #}
  419.                 {% if _hdrStoreOthers is not empty %}
  420.                     <div class="whr-hdr-store-others">
  421.                         <div class="whr-hdr-store-dropdown-header">
  422.                             {{ 'layout.other_regions'|trans({}, 'whr-public')|default('Other regions') }}
  423.                         </div>
  424.                         <div class="whr-hdr-store-grid">
  425.                             {% for code, country in _hdrStoreOthers %}
  426.                                 {% if country.ios %}
  427.                                     <a href="{{ country.ios }}"
  428.                                        class="whr-hdr-store-country"
  429.                                        data-search="{{ country.label|lower }} {{ code|lower }}"
  430.                                        target="_blank" rel="noopener" role="menuitem">
  431.                                         {% if country.flag %}<span class="whr-flag">{{ country.flag }}</span>{% endif %}
  432.                                         <span class="whr-country-name">{{ country.label }}</span>
  433.                                     </a>
  434.                                 {% endif %}
  435.                             {% endfor %}
  436.                         </div>
  437.                         <div class="whr-hdr-store-empty" style="display: none;">
  438.                             {{ 'layout.no_country_found'|trans({}, 'whr-public')|default('No country found') }}
  439.                         </div>
  440.                     </div>
  441.                 {% endif %}
  442.             </div>
  443.         </div>
  444.     {% endif %}
  445.     {# ============================================================
  446.        === Bouton Android / Google Play ===
  447.        ============================================================ #}
  448.     {% set _hdrHasAndroid = false %}
  449.     {% for c in _hdrStorePrimary %}{% if c.android %}{% set _hdrHasAndroid = true %}{% endif %}{% endfor %}
  450.     {% for c in _hdrStoreOthers %}{% if c.android %}{% set _hdrHasAndroid = true %}{% endif %}{% endfor %}
  451.     {% if _hdrHasAndroid %}
  452.         {# === Dropdown pays (FR & EN) === #}
  453.         <div class="whr-hdr-store-wrap menu-icon center-menu-icon" data-whr-hdr-store="android">
  454.             <button type="button" class="whr-hdr-store-btn" aria-haspopup="true" aria-expanded="false" aria-label="Google Play - Choose your country">
  455.                     <span class="font-lg bg-greylight btn-round-lg theme-dark-bg d-inline-flex align-items-center justify-content-center">
  456.                         <svg height="20" width="20" viewBox="0 0 512 512" aria-hidden="true">
  457.                             <path style="fill:#3A9BC8;" d="M225.656,256.052L14.016,485.451l-6.442,7.052c-4.005-5.919-6.704-12.972-7.313-20.806C0.087,470.305,0,468.91,0,467.518V44.499c0-9.488,2.873-18.02,7.574-24.987L225.656,256.052z"/>
  458.                             <path style="fill:#9BCD83;" d="M320.811,152.8l-95.155,103.253L7.574,19.512C19.936,1.405,45.183-6.342,66.6,6.02L320.811,152.8z"/>
  459.                             <path style="fill:#EEB84C;" d="M455.056,257.27c-0.348,14.453-7.748,28.904-22.113,37.174l-112.132,64.771l-95.155-103.163L320.811,152.8l70.518,40.745l41.614,24.026C448.178,226.366,455.579,241.861,455.056,257.27z"/>
  460.                             <path style="fill:#B43F70;" d="M7.591,492.492c12.368,18.116,37.599,25.838,58.976,13.496L320.775,359.22l-95.156-103.209L7.591,492.492z"/>
  461.                         </svg>
  462.                     </span>
  463.             </button>
  464.             <div class="whr-hdr-store-dropdown" role="menu">
  465.                 {# Search bar (apparaît si > 20 pays "others") #}
  466.                 {% set _hdrAndroidOthersCount = 0 %}
  467.                 {% for c in _hdrStoreOthers %}{% if c.android %}{% set _hdrAndroidOthersCount = _hdrAndroidOthersCount + 1 %}{% endif %}{% endfor %}
  468.                 {% if _hdrAndroidOthersCount > 20 %}
  469.                     <div class="whr-hdr-store-search-wrap">
  470.                         <input type="text"
  471.                                class="whr-hdr-store-search"
  472.                                placeholder="{{ 'layout.search_country'|trans({}, 'whr-public')|default('Search country...') }}"
  473.                                aria-label="Search country"
  474.                                autocomplete="off">
  475.                     </div>
  476.                 {% endif %}
  477.                 {# Featured pinné #}
  478.                 {% set _hdrAndroidPrimaryCount = 0 %}
  479.                 {% for c in _hdrStorePrimary %}{% if c.android %}{% set _hdrAndroidPrimaryCount = _hdrAndroidPrimaryCount + 1 %}{% endif %}{% endfor %}
  480.                 {% if _hdrAndroidPrimaryCount > 0 %}
  481.                     <div class="whr-hdr-store-featured">
  482.                         <div class="whr-hdr-store-dropdown-header">
  483.                             {{ 'layout.featured'|trans({}, 'whr-public')|default('Featured') }}
  484.                         </div>
  485.                         {% for code, country in _hdrStorePrimary %}
  486.                             {% if country.android %}
  487.                                 <a href="{{ country.android }}"
  488.                                    class="whr-hdr-store-country"
  489.                                    data-search="{{ country.label|lower }} {{ code|lower }}"
  490.                                    target="_blank" rel="noopener" role="menuitem">
  491.                                     {% if country.flag %}<span class="whr-flag">{{ country.flag }}</span>{% endif %}
  492.                                     <span class="whr-country-name">{{ country.label }}</span>
  493.                                 </a>
  494.                             {% endif %}
  495.                         {% endfor %}
  496.                     </div>
  497.                 {% endif %}
  498.                 {# Other regions (grille 2 cols) #}
  499.                 {% if _hdrStoreOthers is not empty %}
  500.                     <div class="whr-hdr-store-others">
  501.                         <div class="whr-hdr-store-dropdown-header">
  502.                             {{ 'layout.other_regions'|trans({}, 'whr-public')|default('Other regions') }}
  503.                         </div>
  504.                         <div class="whr-hdr-store-grid">
  505.                             {% for code, country in _hdrStoreOthers %}
  506.                                 {% if country.android %}
  507.                                     <a href="{{ country.android }}"
  508.                                        class="whr-hdr-store-country"
  509.                                        data-search="{{ country.label|lower }} {{ code|lower }}"
  510.                                        target="_blank" rel="noopener" role="menuitem">
  511.                                         {% if country.flag %}<span class="whr-flag">{{ country.flag }}</span>{% endif %}
  512.                                         <span class="whr-country-name">{{ country.label }}</span>
  513.                                     </a>
  514.                                 {% endif %}
  515.                             {% endfor %}
  516.                         </div>
  517.                         <div class="whr-hdr-store-empty" style="display: none;">
  518.                             {{ 'layout.no_country_found'|trans({}, 'whr-public')|default('No country found') }}
  519.                         </div>
  520.                     </div>
  521.                 {% endif %}
  522.             </div>
  523.         </div>
  524.     {% endif %}
  525.     {# === Action desktop (>=992px), à droite ===
  526.        Structure native Sociala : .menu-icon + .chat-active-btn + ms-auto
  527.        → le JS Sociala ouvre .right-chat (la rightbar messagerie) #}
  528.     {% if connectUser %}
  529.         <a href="#" class="p-2 text-center ms-auto menu-icon chat-active-btn" aria-label="Messages">
  530.             <i class="feather-message-square font-xl text-current"></i>
  531.         </a>
  532.     {% else %}
  533.         <div class="whr-desktop-actions">
  534.             <a href="{% if app.request.locale == "fr"  %}{{ path('locale_cv_public_entry', {'_locale': app.request.locale}) }}{% else %}{{ path('cv_public_entry') }}{% endif %}" class="whr-cta-login">
  535.                 <i class="feather-plus-circle"></i>
  536.                 {{ 'sidebar.moncv'|trans({}, 'whr-public') }}
  537.             </a>
  538.         </div>
  539.     {% endif %}
  540. </div>
  541. {# ====== JS dropdown stores HEADER (vanilla, autonome, pas de dépendance) ====== #}
  542. <script>
  543.     (function() {
  544.         'use strict';
  545.         function closeAllHdrDropdowns() {
  546.             document.querySelectorAll('.whr-hdr-store-wrap.is-open').forEach(function(w) {
  547.                 w.classList.remove('is-open');
  548.                 var b = w.querySelector('.whr-hdr-store-btn');
  549.                 if (b) b.setAttribute('aria-expanded', 'false');
  550.                 var input = w.querySelector('.whr-hdr-store-search');
  551.                 if (input) {
  552.                     input.value = '';
  553.                     applyHdrFilter(w, '');
  554.                 }
  555.             });
  556.         }
  557.         function applyHdrFilter(wrap, query) {
  558.             query = (query || '').trim().toLowerCase();
  559.             var items = wrap.querySelectorAll('.whr-hdr-store-country');
  560.             var emptyMsg = wrap.querySelector('.whr-hdr-store-empty');
  561.             var grid = wrap.querySelector('.whr-hdr-store-grid');
  562.             var visibleInOthers = 0;
  563.             items.forEach(function(item) {
  564.                 var searchData = item.dataset.search || '';
  565.                 var matches = query === '' || searchData.indexOf(query) !== -1;
  566.                 if (matches) {
  567.                     item.classList.remove('is-hidden');
  568.                     if (grid && grid.contains(item)) {
  569.                         visibleInOthers++;
  570.                     }
  571.                 } else {
  572.                     item.classList.add('is-hidden');
  573.                 }
  574.             });
  575.             if (emptyMsg && grid) {
  576.                 if (query !== '' && visibleInOthers === 0) {
  577.                     grid.style.display = 'none';
  578.                     emptyMsg.style.display = 'block';
  579.                 } else {
  580.                     grid.style.display = '';
  581.                     emptyMsg.style.display = 'none';
  582.                 }
  583.             }
  584.         }
  585.         function initWhrHdrStoreDropdowns() {
  586.             var wraps = document.querySelectorAll('.whr-hdr-store-wrap');
  587.             if (!wraps.length) return;
  588.             wraps.forEach(function(wrap) {
  589.                 var btn = wrap.querySelector('.whr-hdr-store-btn');
  590.                 if (!btn || btn.dataset.whrHdrInit === '1') return;
  591.                 btn.dataset.whrHdrInit = '1';
  592.                 // Toggle au clic sur le bouton
  593.                 btn.addEventListener('click', function(e) {
  594.                     e.preventDefault();
  595.                     e.stopPropagation();
  596.                     var isOpen = wrap.classList.contains('is-open');
  597.                     closeAllHdrDropdowns();
  598.                     if (!isOpen) {
  599.                         wrap.classList.add('is-open');
  600.                         btn.setAttribute('aria-expanded', 'true');
  601.                         // Auto-focus search à l'ouverture (desktop seulement)
  602.                         var input = wrap.querySelector('.whr-hdr-store-search');
  603.                         if (input && window.innerWidth >= 768) {
  604.                             setTimeout(function() { input.focus(); }, 50);
  605.                         }
  606.                     }
  607.                 });
  608.                 // Filtrage live
  609.                 var input = wrap.querySelector('.whr-hdr-store-search');
  610.                 if (input) {
  611.                     input.addEventListener('input', function() {
  612.                         applyHdrFilter(wrap, this.value);
  613.                     });
  614.                     input.addEventListener('click', function(e) {
  615.                         e.stopPropagation();
  616.                     });
  617.                     input.addEventListener('keydown', function(e) {
  618.                         if (e.key === 'Escape') {
  619.                             if (this.value !== '') {
  620.                                 this.value = '';
  621.                                 applyHdrFilter(wrap, '');
  622.                                 e.stopPropagation();
  623.                             }
  624.                         }
  625.                     });
  626.                 }
  627.             });
  628.             // Listeners globaux (1 seule fois pour tout le doc)
  629.             if (!document.body.dataset.whrHdrStoreOutsideInit) {
  630.                 document.body.dataset.whrHdrStoreOutsideInit = '1';
  631.                 document.addEventListener('click', function(e) {
  632.                     if (!e.target.closest('.whr-hdr-store-wrap')) {
  633.                         closeAllHdrDropdowns();
  634.                     }
  635.                 });
  636.                 document.addEventListener('keydown', function(e) {
  637.                     if (e.key === 'Escape') {
  638.                         closeAllHdrDropdowns();
  639.                     }
  640.                 });
  641.             }
  642.         }
  643.         if (document.readyState === 'loading') {
  644.             document.addEventListener('DOMContentLoaded', initWhrHdrStoreDropdowns);
  645.         } else {
  646.             initWhrHdrStoreDropdowns();
  647.         }
  648.     })();
  649. </script>