/* ============================================================
   Ebokoli Messenger — refonte visuelle "premium / futuriste"
   ------------------------------------------------------------
   Fichier ADDITIF : chargé après style.css, ne modifie aucune
   règle existante ailleurs sur le site. Tout est scopé sous
   .panel-messages / .chat-widget (messagerie + widget flottant)
   pour ne jamais toucher aux commentaires, posts, etc. qui
   réutilisent des classes proches (.conversation, .text...).
   Aucune logique métier ici : uniquement du visuel + de petites
   micro-interactions CSS. Le JS qui l'accompagne (chat-modern.js)
   ne fait que lire/relayer les mêmes événements et données que
   le code existant (aucune fonction backend modifiée).
   ============================================================ */

.panel-messages,
.chat-widget {
  --msg-accent: #4f7cff;
  --msg-accent-2: #7c5cff;
  --msg-accent-glow: rgba(79, 124, 255, 0.45);
  --msg-surface: #ffffff;
  --msg-surface-alt: #f3f5fb;
  --msg-bubble-in: #eef1fb;
  --msg-bubble-in-text: #1a1f36;
  --msg-border: #e6e9f5;
  --msg-muted: #8a90a6;
  --msg-status-sent: #ff5d6c;
  --msg-status-delivered: #ffb648;
  --msg-status-seen: #37d67a;
}

body.night-mode .panel-messages,
body.night-mode .chat-widget {
  --msg-surface: #10141f;
  --msg-surface-alt: #161b29;
  --msg-bubble-in: #1c2233;
  --msg-bubble-in-text: #e7ebff;
  --msg-border: #232a3d;
  --msg-muted: #7982a3;
}

/* ---------- structure générale de la fenêtre de conversation ---------- */
.panel-messages {
  border: 1px solid var(--msg-border);
  border-radius: 22px;
  overflow: hidden;
  background: var(--msg-surface);
}

.panel-messages .card-header {
  background: var(--msg-surface);
  border-bottom: 1px solid var(--msg-border);
}

.panel-messages .card-body {
  background: var(--msg-surface-alt);
}

/* ---------- bulles de message ---------- */
.panel-messages .conversation,
.chat-widget .conversation {
  padding-top: 6px;
  margin-bottom: 16px;
}

.panel-messages .conversation-user,
.chat-widget .conversation-user {
  width: 34px;
  height: 34px;
  box-shadow: 0 0 0 2px var(--msg-surface-alt), 0 0 0 3px var(--msg-accent-glow);
}

.panel-messages .conversation-user img,
.chat-widget .conversation-user img {
  width: 34px;
  height: 34px;
}

.panel-messages .conversation-body .text,
.chat-widget .conversation-body .text {
  background: var(--msg-bubble-in);
  color: var(--msg-bubble-in-text);
  padding: 10px 14px;
  border-radius: 18px;
  border-bottom-left-radius: 6px;
  box-shadow: 0 2px 10px rgba(20, 25, 45, 0.06);
  transition: transform 0.15s ease;
}

.panel-messages .conversation.right .conversation-body .text,
.chat-widget .conversation.right .conversation-body .text {
  background: linear-gradient(135deg, var(--msg-accent), var(--msg-accent-2));
  color: #fff;
  border-radius: 18px;
  border-bottom-right-radius: 6px;
  box-shadow: 0 4px 16px var(--msg-accent-glow);
}

.panel-messages .conversation-body .text:hover,
.chat-widget .conversation-body .text:hover {
  transform: translateY(-1px);
}

.panel-messages .conversation-body .time,
.chat-widget .conversation-body .time {
  color: var(--msg-muted);
  font-size: 10.5px;
}

/* ---------- statut de message (losanges géométriques) ----------
   Deux états réellement disponibles côté données : envoyé (sent)
   et vu (seen, dérivé de last_seen_message_id). Il n'existe pas
   aujourd'hui de statut "reçu" distinct côté backend (pas de
   colonne "delivered_at") : ce 3e état demanderait un changement
   de logique serveur, volontairement hors périmètre ici. */
.msg-status {
  display: inline-block;
  width: 7px;
  height: 7px;
  margin-left: 6px;
  margin-bottom: 1px;
  transform: rotate(45deg);
  vertical-align: middle;
  border-radius: 1.5px;
  background: transparent;
  border: 1.5px solid var(--msg-status-delivered);
  transition: background 0.2s ease, border-color 0.2s ease;
}

.msg-status.is-seen {
  background: var(--msg-status-seen);
  border-color: var(--msg-status-seen);
  box-shadow: 0 0 6px rgba(55, 214, 122, 0.6);
}

/* ---------- zone de saisie ---------- */
.panel-messages .chat-form,
.chat-widget .chat-form {
  background: var(--msg-surface);
  border-top: 1px solid var(--msg-border);
}

.panel-messages .chat-form-message,
.chat-widget .chat-form-message {
  background: var(--msg-surface-alt);
  border-radius: 20px;
  border: 1px solid transparent;
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}

.panel-messages .chat-form-message:focus-within,
.chat-widget .chat-form-message:focus-within {
  border-color: var(--msg-accent);
  box-shadow: 0 0 0 3px var(--msg-accent-glow);
}

.panel-messages .x-form-tools-post,
.chat-widget .x-form-tools-post {
  color: var(--msg-accent);
}

/* ============================================================
   Bouton microphone — états idle / recording / pause
   ============================================================ */
.voice-recording-wrapper {
  display: flex;
  align-items: center;
  gap: 10px;
}

.btn-voice-start,
.btn-voice-stop {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  cursor: pointer;
  user-select: none;
  padding: 8px 16px;
  border-radius: 999px;
  font-size: 13px;
  font-weight: 500;
}

/* idle (avant le clic) : anneau lumineux discret */
.btn-voice-start {
  background: var(--msg-surface-alt);
  color: var(--msg-accent);
  border: 1.5px solid var(--msg-accent);
  box-shadow: 0 0 0 0 var(--msg-accent-glow);
  animation: msg-mic-idle-pulse 2.6s ease-in-out infinite;
}

.btn-voice-start i {
  color: var(--msg-accent);
}

@keyframes msg-mic-idle-pulse {
  0%, 100% { box-shadow: 0 0 0 0 var(--msg-accent-glow); }
  50% { box-shadow: 0 0 0 6px rgba(79, 124, 255, 0); }
}

/* recording : anneau rouge pulsant, plus assertif */
.btn-voice-stop {
  background: rgba(255, 93, 108, 0.1);
  color: var(--msg-status-sent);
  border: 1.5px solid var(--msg-status-sent);
  animation: msg-mic-rec-pulse 1.4s ease-in-out infinite;
}

.btn-voice-stop i {
  color: var(--msg-status-sent);
}

@keyframes msg-mic-rec-pulse {
  0%, 100% { box-shadow: 0 0 0 0 rgba(255, 93, 108, 0.45); }
  50% { box-shadow: 0 0 0 8px rgba(255, 93, 108, 0); }
}

.js_voice-timer {
  font-variant-numeric: tabular-nums;
  font-weight: 600;
}

/* petit bouton micro rond dans la barre de saisie (x-form-tools-voice),
   même logique d'anneau lumineux quand le parent est en enregistrement */
.x-form-tools-voice {
  position: relative;
  transition: color 0.15s ease;
}

.x-form-tools-voice.is-recording {
  color: var(--msg-status-sent);
}

.x-form-tools-voice.is-recording::after {
  content: "";
  position: absolute;
  inset: -6px;
  border-radius: 50%;
  border: 1.5px solid var(--msg-status-sent);
  animation: msg-mic-rec-pulse 1.4s ease-in-out infinite;
}

/* ---------- message de traitement / succès (prévisualisation) ---------- */
.js_voice-processing-message,
.js_voice-success-message {
  border-radius: 16px;
  padding: 10px 14px;
  background: var(--msg-surface-alt);
  border: 1px solid var(--msg-border);
}

.js_voice-success-message {
  display: flex;
  align-items: center;
  gap: 10px;
  color: var(--msg-status-seen);
}

/* .float-end (Bootstrap) n'a aucun effet en display:flex : on restaure
   explicitement le comportement "poussé à droite" du bouton de suppression
   pour ne pas régresser par rapport à l'affichage d'origine. */
.js_voice-success-message > .float-end {
  margin-left: auto;
  float: none;
}

/* conteneur de prévisualisation waveform injecté par chat-modern.js
   (mêmes données que le succès existant : le fichier vient déjà
   d'être uploadé par le code existant, on ne fait qu'afficher un
   lecteur au lieu du texte brut) */
.voice-preview-player {
  display: flex;
  align-items: center;
  gap: 10px;
  flex: 1;
  min-width: 0;
}

.voice-preview-player .voice-play-btn {
  flex: 0 0 auto;
  width: 28px;
  height: 28px;
  min-width: 28px;
  background: linear-gradient(135deg, var(--msg-accent), var(--msg-accent-2));
  color: #fff;
  box-shadow: 0 2px 8px var(--msg-accent-glow);
}

.voice-preview-player .voice-play-btn svg {
  width: 11px;
  height: 11px;
}

/* ============================================================
   Lecteur audio personnalisé (remplace <audio controls> natif)
   ------------------------------------------------------------
   Le <audio class="js_audio"> d'origine reste présent et
   fonctionnel dans le DOM (juste masqué visuellement) : c'est
   TOUJOURS lui qui joue le son, chat-modern.js ne fait que
   piloter .play()/.pause() dessus et refléter son état. Le
   binding existant "pause les autres audios au play" continue
   donc de fonctionner sans aucune modification.
   ============================================================ */
.voice-player {
  display: flex;
  align-items: center;
  gap: 10px;
  min-width: 200px;
  padding: 6px 10px 6px 6px;
  border-radius: 999px;
  background: rgba(255, 255, 255, 0.12);
}

.conversation-body .text .voice-player {
  background: rgba(255, 255, 255, 0.16);
}

.conversation-body .text:not(.js_chat-color-me) .voice-player,
.panel-messages .conversation:not(.right) .voice-player {
  background: rgba(79, 124, 255, 0.08);
}

.voice-player audio {
  display: none;
}

.voice-play-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 32px;
  height: 32px;
  min-width: 32px;
  border-radius: 50%;
  border: none;
  background: rgba(255, 255, 255, 0.9);
  color: var(--msg-accent);
  cursor: pointer;
  transition: transform 0.12s ease;
}

.voice-play-btn:active {
  transform: scale(0.92);
}

.conversation:not(.right) .voice-play-btn {
  background: linear-gradient(135deg, var(--msg-accent), var(--msg-accent-2));
  color: #fff;
}

.voice-player-body {
  flex: 1;
  min-width: 0;
}

.voice-waveform {
  display: flex;
  align-items: center;
  gap: 2px;
  height: 22px;
  cursor: pointer;
}

.voice-waveform .bar {
  flex: 1 1 auto;
  width: 2.5px;
  min-width: 2px;
  border-radius: 2px;
  background: rgba(255, 255, 255, 0.45);
  transform: scaleY(0.35);
  transition: background 0.15s ease;
}

.conversation:not(.right) .voice-waveform .bar {
  background: rgba(79, 124, 255, 0.35);
}

.voice-preview-player .voice-waveform .bar {
  background: rgba(79, 124, 255, 0.35);
}

.voice-preview-player .voice-waveform .bar.is-played {
  background: var(--msg-accent);
}

.voice-waveform .bar.is-played {
  background: #fff;
}

.conversation:not(.right) .voice-waveform .bar.is-played {
  background: var(--msg-accent);
}

/* animation d'idle très subtile pour rappeler que le message est audio */
.voice-player:not(.is-playing) .voice-waveform .bar,
.voice-preview-player:not(.is-playing) .voice-waveform .bar {
  animation: msg-wave-idle 2.8s ease-in-out infinite;
}

@keyframes msg-wave-idle {
  0%, 100% { transform: scaleY(0.35); }
  50% { transform: scaleY(0.5); }
}

/* pendant la lecture : léger mouvement façon égaliseur */
.voice-player.is-playing .voice-waveform .bar,
.voice-preview-player.is-playing .voice-waveform .bar {
  animation: msg-wave-live 0.9s ease-in-out infinite;
}

.voice-player.is-playing .voice-waveform .bar:nth-child(2n),
.voice-preview-player.is-playing .voice-waveform .bar:nth-child(2n) { animation-delay: 0.1s; }
.voice-player.is-playing .voice-waveform .bar:nth-child(3n),
.voice-preview-player.is-playing .voice-waveform .bar:nth-child(3n) { animation-delay: 0.2s; }
.voice-player.is-playing .voice-waveform .bar:nth-child(4n),
.voice-preview-player.is-playing .voice-waveform .bar:nth-child(4n) { animation-delay: 0.3s; }
.voice-player.is-playing .voice-waveform .bar:nth-child(5n),
.voice-preview-player.is-playing .voice-waveform .bar:nth-child(5n) { animation-delay: 0.15s; }

@keyframes msg-wave-live {
  0%, 100% { transform: scaleY(0.35); }
  50% { transform: scaleY(1); }
}

.voice-player-meta {
  display: flex;
  justify-content: space-between;
  margin-top: 3px;
  font-size: 10.5px;
  opacity: 0.85;
}

/* icône play/pause : on bascule juste une classe, pas de JS de layout */
.voice-play-btn .icon-play,
.voice-play-btn .icon-pause {
  display: block;
}

.voice-play-btn .icon-pause {
  display: none;
}

.voice-player.is-playing .voice-play-btn .icon-play,
.voice-preview-player.is-playing .voice-play-btn .icon-play {
  display: none;
}

.voice-player.is-playing .voice-play-btn .icon-pause,
.voice-preview-player.is-playing .voice-play-btn .icon-pause {
  display: block;
}

/* ---------- vitesse de lecture ---------- */
.voice-speed-btn {
  border: none;
  background: rgba(255, 255, 255, 0.18);
  color: inherit;
  font-size: 10px;
  font-weight: 700;
  padding: 1px 6px;
  border-radius: 999px;
  cursor: pointer;
  line-height: 1.6;
}

.conversation:not(.right) .voice-speed-btn {
  background: rgba(79, 124, 255, 0.12);
  color: var(--msg-accent);
}

/* ============================================================
   Header de conversation modernisé
   ============================================================ */
.panel-messages > .card-header,
.chat-widget .card-header {
  padding: 14px 18px;
  display: flex;
  align-items: center;
  gap: 12px;
}

.panel-messages > .card-header .row {
  width: 100%;
  align-items: center;
}

.panel-messages > .card-header a,
.panel-messages > .card-header span {
  font-weight: 600;
  color: var(--msg-bubble-in-text, inherit);
}

.panel-messages > .card-header .btn-light {
  background: var(--msg-surface-alt);
  border: 1px solid var(--msg-border);
  color: var(--msg-accent);
  transition: transform 0.12s ease, box-shadow 0.12s ease;
}

.panel-messages > .card-header .btn-light:hover {
  transform: translateY(-1px);
  box-shadow: 0 4px 12px var(--msg-accent-glow);
}

/* ============================================================
   Barre de saisie modernisée (icônes + textarea)
   ============================================================ */
.panel-messages .x-form-tools,
.chat-widget .x-form-tools {
  display: flex;
  align-items: center;
  gap: 4px;
}

.panel-messages .x-form-tools li,
.chat-widget .x-form-tools li {
  width: 34px;
  height: 34px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 50%;
  color: var(--msg-muted);
  cursor: pointer;
  transition: background 0.15s ease, color 0.15s ease, transform 0.1s ease;
}

.panel-messages .x-form-tools li:hover,
.chat-widget .x-form-tools li:hover {
  background: var(--msg-surface-alt);
  color: var(--msg-accent);
  transform: translateY(-1px);
}

.panel-messages .x-form-tools-post,
.chat-widget .x-form-tools-post {
  background: linear-gradient(135deg, var(--msg-accent), var(--msg-accent-2));
  color: #fff !important;
  box-shadow: 0 3px 10px var(--msg-accent-glow);
}

.panel-messages .x-form-tools-post:hover,
.chat-widget .x-form-tools-post:hover {
  color: #fff !important;
  filter: brightness(1.08);
}

/* ============================================================
   Overlay d'enregistrement (micro central animé + waveform live)
   ------------------------------------------------------------
   Construit par chat-modern.js par-dessus les boutons d'origine
   (toujours présents dans le DOM, juste masqués visuellement le
   temps que l'overlay est actif) — voir commentaires du JS.
   ============================================================ */
.voice-recording-wrapper {
  position: relative;
}

.btn-voice-start,
.btn-voice-stop {
  transition: opacity 0.15s ease;
}

.rec-overlay {
  display: none;
  flex-direction: column;
  align-items: center;
  gap: 14px;
  padding: 18px 16px 14px;
  border-radius: 20px;
  background: var(--msg-surface-alt);
  border: 1px solid var(--msg-border);
}

.rec-overlay.is-active {
  display: flex;
}

/* pendant que l'overlay est actif, on masque les anciens boutons texte
   (ils restent dans le DOM et fonctionnels, pilotés par les boutons
   de l'overlay) pour ne pas les dupliquer visuellement. Classe posée
   par chat-modern.js (plus fiable que :has() sur tous les navigateurs). */
.voice-recording-wrapper.mw-recording-active > .btn-voice-start,
.voice-recording-wrapper.mw-recording-active > .btn-voice-stop {
  display: none !important;
}

.rec-mic-circle {
  width: 68px;
  height: 68px;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 22px;
  color: #fff;
  background: linear-gradient(135deg, var(--msg-status-sent), #ff8a6b);
  box-shadow: 0 0 0 0 rgba(255, 93, 108, 0.5);
  animation: msg-mic-rec-pulse-lg 1.5s ease-in-out infinite;
}

.rec-overlay.is-paused .rec-mic-circle {
  background: linear-gradient(135deg, var(--msg-muted), var(--msg-border));
  animation: none;
  box-shadow: none;
}

@keyframes msg-mic-rec-pulse-lg {
  0%, 100% { box-shadow: 0 0 0 0 rgba(255, 93, 108, 0.45); }
  50% { box-shadow: 0 0 0 14px rgba(255, 93, 108, 0); }
}

.rec-waveform {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 3px;
  height: 36px;
  width: 100%;
  max-width: 280px;
}

.rec-waveform .bar {
  flex: 1 1 auto;
  width: 3px;
  min-width: 2px;
  max-width: 4px;
  border-radius: 3px;
  background: var(--msg-status-sent);
  transform: scaleY(0.08);
  transition: transform 0.08s linear;
}

.rec-overlay.is-paused .rec-waveform .bar {
  background: var(--msg-muted);
  transform: scaleY(0.08) !important;
  transition: none;
}

.rec-timer {
  font-variant-numeric: tabular-nums;
  font-weight: 700;
  font-size: 15px;
  letter-spacing: 0.02em;
}

.rec-actions {
  display: flex;
  align-items: center;
  gap: 18px;
}

.rec-btn {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 42px;
  height: 42px;
  border-radius: 50%;
  border: none;
  cursor: pointer;
  font-size: 15px;
  transition: transform 0.12s ease;
}

.rec-btn:active {
  transform: scale(0.92);
}

.rec-btn-delete {
  background: rgba(255, 93, 108, 0.12);
  color: var(--msg-status-sent);
  width: 36px;
  height: 36px;
  font-size: 13px;
}

.rec-btn-pause,
.rec-btn-resume {
  background: var(--msg-surface);
  border: 1.5px solid var(--msg-border);
  color: var(--msg-bubble-in-text);
}

.rec-btn-validate {
  background: linear-gradient(135deg, var(--msg-status-seen), #2fc76e);
  color: #fff;
  box-shadow: 0 3px 10px rgba(55, 214, 122, 0.4);
}

.rec-overlay.is-cancelling {
  opacity: 0.5;
  pointer-events: none;
}

/* ---------- responsive ---------- */
@media (max-width: 767.98px) {
  .panel-messages {
    border-radius: 0;
    border-left: none;
    border-right: none;
  }

  .voice-player {
    min-width: 160px;
  }

  .js_voice-success-message {
    flex-wrap: wrap;
    row-gap: 6px;
  }

  .js_voice-success-message > .float-end {
    margin-left: 0;
  }

  .rec-mic-circle {
    width: 56px;
    height: 56px;
    font-size: 18px;
  }

  .rec-actions {
    gap: 14px;
  }

  .panel-messages .x-form-tools li,
  .chat-widget .x-form-tools li {
    width: 30px;
    height: 30px;
  }
}

@media (min-width: 992px) {
  /* desktop : conversation centrée, plus aérée */
  .panel-messages {
    max-width: 900px;
    margin: 0 auto;
  }

  .panel-messages .chat-conversations {
    padding: 20px 32px;
  }

  .rec-mic-circle {
    width: 76px;
    height: 76px;
    font-size: 24px;
  }
}

/* ============================================================
   Messagerie mobile : afficher la liste des conversations par
   défaut plutôt que la cacher derrière l'icône menu.
   ------------------------------------------------------------
   Le site utilise un système "offcanvas" partagé par plusieurs
   pages (messages, admin, forums...) où, sur mobile, la barre
   latérale est masquée par défaut (left:-100%) tant qu'on n'a pas
   cliqué sur l'icône menu du header (qui ajoute la classe .active
   à .sg-offcanvas). Résultat sur la page Messages : quand aucune
   conversation n'est ouverte, l'utilisateur mobile atterrit sur
   "Aucune conversation sélectionnée" sans voir la liste du tout.

   Cette règle ne touche PAS au comportement partagé (les autres
   pages continuent de fonctionner comme avant) : elle ne s'active
   que sur la page Messages, et seulement quand aucune conversation
   n'est sélectionnée (classe .messages-no-conversation posée par
   messages.tpl). Dès qu'une conversation est ouverte, l'affichage
   redevient celui d'origine (conversation visible, liste accessible
   via l'icône menu comme avant). */
@media (max-width: 767px) {
  .sg-offcanvas.messages-no-conversation .sg-offcanvas-sidebar {
    left: 0 !important;
  }
  .sg-offcanvas.messages-no-conversation .sg-offcanvas-mainbar {
    left: 100% !important;
  }
}