(function(){
        // --- Restaura idiomas salvos antes de qualquer bind ---
        try {
            const from = localStorage.getItem('lastLangFrom');
            const to = localStorage.getItem('lastLangTo');
            if (from && document.getElementById('selLangFrom')) {
                document.getElementById('selLangFrom').value = from;
                window.FROM = from;
            }
            if (to && document.getElementById('selLangTo')) {
                document.getElementById('selLangTo').value = to;
                window.TO = to;
            }
        } catch(e){}
    // ===============================
    // CONTROLE DE TURNOS DINÂMICO PARA MODO DIÁLOGO
    // ===============================

    // Estado das listas de turnos
    window.dialogTurnLists = {
        human: [],
        system: []
    };

    /**
     * Inicializa as listas de turnos para o modo diálogo
     * @param {number} totalCards
     * @param {'human'|'system'} firstRole
     */
    window.initDialogTurnLists = function(totalCards, firstRole) {
        const human = [], system = [];
        for (let i = 0; i < totalCards; i++) {
            if (firstRole === 'human') {
                if (i % 2 === 0) human.push(i); else system.push(i);
            } else {
                if (i % 2 === 0) system.push(i); else human.push(i);
            }
        }
        window.dialogTurnLists.human = human;
        window.dialogTurnLists.system = system;
    };

    /**
     * Remove um índice da lista de turnos do papel correspondente
     * @param {'human'|'system'} role
     * @param {number} idx
     */
    window.removeDialogTurnIdx = function(role, idx) {
        const list = window.dialogTurnLists[role];
        const pos = list.indexOf(idx);
        if (pos !== -1) list.splice(pos, 1);
    };

    /**
     * Retorna o próximo índice do papel (humano/sistema) na lista dinâmica
     * @param {'human'|'system'} role
     * @returns {number|null}
     */
    window.getNextDialogTurnIdx = function(role) {
        const list = window.dialogTurnLists[role];
        for (let i = 0; i < list.length; i++) {
            const card = document.getElementById('card-' + list[i]);
            if (card && !card.classList.contains('ignored')) return list[i];
        }
        return null;
    };

    /**
     * Verifica se acabou o diálogo (todas as listas vazias)
     */
    window.isDialogFinished = function() {
        return window.dialogTurnLists.human.length === 0 && window.dialogTurnLists.system.length === 0;
    };

    // Exemplo de uso:
    // window.initDialogTurnLists(totalCards, 'human');
    // let idx = window.getNextDialogTurnIdx('human');
    // window.removeDialogTurnIdx('human', idx);

})();
(function(){
    // ===============================
    // CONTROLE ROBUSTO DE TURNOS PARA MODO DIÁLOGO
    // ===============================

    /**
     * Gera listas de índices dos cards do humano e do sistema, conforme quem começou.
     * @param {number} totalCards - Quantidade total de cards
     * @param {'human'|'system'} firstRole - Quem começou
     * @returns {{human: number[], system: number[]}}
     */
    window.getDialogTurnIndices = function(totalCards, firstRole) {
        const human = [], system = [];
        for (let i = 0; i < totalCards; i++) {
            if (firstRole === 'human') {
                if (i % 2 === 0) human.push(i); else system.push(i);
            } else {
                if (i % 2 === 0) system.push(i); else human.push(i);
            }
        }
        return { human, system };
    };

    /**
     * Retorna o próximo índice válido (não ignorado) para o papel (human/system), dado o índice atual.
     * @param {'human'|'system'} role
     * @param {number} currentIdx
     * @param {number[]} indicesList
     * @returns {number|null}
     */
    window.getNextDialogCardIdx = function(role, currentIdx, indicesList) {
        // Busca o próximo índice maior que o atual e não ignorado
        for (let i = 0; i < indicesList.length; i++) {
            if (indicesList[i] > currentIdx) {
                const card = document.getElementById('card-' + indicesList[i]);
                if (card && !card.classList.contains('ignored')) return indicesList[i];
            }
        }
        return null;
    };

    /**
     * Retorna o índice do próximo card do papel (human/system) a partir do início (para o primeiro turno)
     */
    window.getFirstDialogCardIdx = function(role, indicesList) {
        for (let i = 0; i < indicesList.length; i++) {
            const card = document.getElementById('card-' + indicesList[i]);
            if (card && !card.classList.contains('ignored')) return indicesList[i];
        }
        return null;
    };

    // Exemplo de uso:
    // const total = document.querySelectorAll('.card').length;
    // const {human, system} = getDialogTurnIndices(total, window.dialogState.firstRole);
    // let idx = getFirstDialogCardIdx('human', human);
    // let nextIdx = getNextDialogCardIdx('human', idx, human);

})();
(function(){
    // ===============================
    // SISTEMA DE DIÁLOGO IMPAR/PAR
    // ===============================

    /**
     * Estado do diálogo: quem começa, quem responde em cada card
     * dialogState = {
     *   started: false, // se o modo diálogo foi iniciado
     *   firstRole: null, // 'human' ou 'system' (quem iniciou)
     *   currentCard: 0,  // índice do card atual
     * }
     */
    window.dialogState = {
        started: false,
        firstRole: null, // 'human' ou 'system'
        currentCard: 0
    };

    /**
     * Determina o dono do card (quem deve responder/falar)
     * @param {number} idx Índice do card (0-based)
     * @returns {'human'|'system'}
     */
    window.getCardOwner = function(idx) {
        if (!window.dialogState.started || !window.dialogState.firstRole) return null;
        // Se quem começou foi o humano (microfone): ímpares são do humano, pares do sistema
        // Se quem começou foi o sistema (autofalante): ímpares do sistema, pares do humano
        if (window.dialogState.firstRole === 'human') {
            return (idx % 2 === 0) ? 'human' : 'system';
        } else {
            return (idx % 2 === 0) ? 'system' : 'human';
        }
    };

    /**
     * Inicia o diálogo, definindo quem começou (microfone/autofalante)
     * @param {'human'|'system'} who Quem iniciou
     */
    window.startDialog = function(who) {
        window.dialogState.started = true;
        window.dialogState.firstRole = who;
        window.dialogState.currentCard = 0;
    };

    /**
     * Avança para o próximo card no diálogo
     */
    window.nextDialogCard = function() {
        window.dialogState.currentCard++;
    };

    /**
     * Reseta o estado do diálogo
     */
    window.resetDialog = function() {
        window.dialogState.started = false;
        window.dialogState.firstRole = null;
        window.dialogState.currentCard = 0;
    };

    // Exemplo de uso (deve ser integrado aos handlers dos botões):
    // - Ao pressionar o microfone no primeiro card: startDialog('human')
    // - Ao pressionar o autofalante no primeiro card: startDialog('system')
    // - Para saber de quem é o card atual: getCardOwner(idx)
    // - Para avançar: nextDialogCard()
    // - Para resetar: resetDialog()

})();
// ===============================================================
// controller.events.js — VERSÃO FINAL CORRIGIDA
// Projeto: HEP Flashcards
// Descrição: Gerencia eventos de interface e interação do usuário.
// Com reinício automático do STT ao trocar idiomas
// + Correção para marcar o card atual (OK funciona corretamente)
// ===============================================================

(function(){

    function qs(sel){ return document.querySelector(sel); }

    // ===============================================================
    // Reinício automático do STT ao mudar idiomas
    // ===============================================================
    function restartMic(){
        if (SttEngine?.enabled){
            SttEngine.stop();
            setTimeout(()=> SttEngine.start(LANGS_BCP[window.TO]), 250);
        }
    }

    // ===============================================================
    // BIND PRINCIPAL
    // ===============================================================
    window.bindUIEvents = function(){

      // ------------------------------------------------------------
      // RESET TOP
      // ------------------------------------------------------------
      const btnResetTop = qs("#btnResetTop");
      if (btnResetTop){
          btnResetTop.addEventListener("click", ()=>{
              if (window.AutoPlayer) AutoPlayer.stop();
              if (window.TtsEngine?.cancel) TtsEngine.cancel();
              if (window.SttEngine?.stop)   SttEngine.stop();

              UI.getAllCards().forEach(c=>{
                  c.classList.remove("hit","blue","ignored","spoken","autoplay-current","card-speaking","card-spoken");
                  // Limpa estilos inline de borda, outline e box-shadow
                  c.style.borderColor = "";
                  c.style.borderWidth = "";
                  c.style.outline = "";
                  c.style.boxShadow = "";
                  const r = c.querySelector(".card-recognized");
                  if (r) r.textContent = "";
              });

              UI.updateStats();
              UI.toast("🔄 Reiniciado...");
          });
      }

            // Sempre que mudar o modo de leitura ou pressionar Auto, zera contagem
            function resetHitTargetToDefault() {
                const sel = document.getElementById('selHitTarget');
                if (sel) {
                    // Força o valor para '-' (primeiro option)
                    sel.value = '';
                    // Garante que o evento change será disparado mesmo se já estiver em '-'
                    sel.dispatchEvent(new Event('change', { bubbles: true }));
                }
            }
    // --- Manter contador em '-' se Auto ativo ou modo diálogo ---
    window.forceHitTargetIfNeeded = function() {
        const sel = document.getElementById('selHitTarget');
        const modoDialogo = document.getElementById('chkNodoDialogo');
        const isAuto = window.AutoPlayer && window.AutoPlayer.running;
        const dialogoAtivo = !!(modoDialogo && modoDialogo.checked);
        if (!sel) return;
        if (isAuto || dialogoAtivo) {
            if (sel.value !== '') {
                sel.value = '';
                sel.dispatchEvent(new Event('change', { bubbles: true }));
            }
        }
    }
    // Monitorar mudanças de Auto
    if (window.AutoPlayer) {
        const origStart = window.AutoPlayer.start;
        const origStop = window.AutoPlayer.stop;
        window.AutoPlayer.start = function() {
            origStart.apply(this, arguments);
            setTimeout(forceHitTargetIfNeeded, 10);
        };
        window.AutoPlayer.stop = function() {
            origStop.apply(this, arguments);
            setTimeout(forceHitTargetIfNeeded, 10);
        };
    }
    // (Removido: monitoramento do combobox de leitura)
    // Monitorar mudanças manuais no contador
    const selHitTarget = document.getElementById('selHitTarget');
    if (selHitTarget) {
        selHitTarget.addEventListener('change', function() {
            setTimeout(forceHitTargetIfNeeded, 10);
        });
    }
    // Garantir estado correto ao carregar
    setTimeout(forceHitTargetIfNeeded, 100);
      // ------------------------------------------------------------
      // MENU MOBILE
      // ------------------------------------------------------------
      const btnMenu = qs(".menu-button");
      const panel   = qs(".controls");

      if (btnMenu && panel){
          btnMenu.addEventListener("click", e=>{
              e.stopPropagation();
              panel.classList.toggle("open");
          });

          document.addEventListener("click", ev=>{
              if (!panel.contains(ev.target) && !btnMenu.contains(ev.target)){
                  panel.classList.remove("open");
              }
          });
      }

      // ------------------------------------------------------------
      // CONTROLES DO MENU
      // ------------------------------------------------------------
      const chkShowPT    = qs("#chkShowPT");
      const chkShowLang  = qs("#chkShowLang");
      const chkSpeakFrom = qs("#chkSpeakFrom");

      const selFrom      = qs("#selLangFrom");
      const selTo        = qs("#selLangTo");
      const selInterval  = qs("#selAutoInterval");
      const selRate      = qs("#selTtsRate");
      const selTheme     = qs("#selTheme");

      const btnMic       = qs("#btnMic");
      const btnReset     = qs("#btnReset");
      const btnAuto      = qs("#btnAuto");
      const btnShuffle   = qs("#btnShuffle");


      // MOSTRAR PT
      if (chkShowPT){
          chkShowPT.addEventListener("change", e=>{
              UI.updateShowPT(e.target.checked);
          });
      }

      // MOSTRAR IDIOMA
      if (chkShowLang){
          chkShowLang.addEventListener("change", e=>{
              UI.updateShowLang(e.target.checked);
          });
      }

      // SPEAK FROM FIRST
      if (chkSpeakFrom){
          chkSpeakFrom.addEventListener("change", e=>{
              window._speakFromFirst = !!e.target.checked;
          });
      }

      // Desabilita combos de idioma se modo diálogo ativo
      const modoDialogo = document.getElementById('chkNodoDialogo');
            function updateLangCombosAndShuffleDisabled() {
                const selFrom = qs("#selLangFrom");
                const selTo = qs("#selLangTo");
                const btnShuffle = qs("#btnShuffle");
                const dialogoAtivo = !!(modoDialogo && modoDialogo.checked);
                if (selFrom) selFrom.disabled = dialogoAtivo;
                if (selTo) selTo.disabled = dialogoAtivo;
                if (btnShuffle) btnShuffle.disabled = dialogoAtivo;
            }
            if (modoDialogo) {
                modoDialogo.addEventListener('change', updateLangCombosAndShuffleDisabled);
                // Garante estado correto ao carregar
                setTimeout(updateLangCombosAndShuffleDisabled, 100);
            }
            // Também reabilita combos/botão ao resetar
            if (btnReset) {
                btnReset.addEventListener('click', function() {
                    setTimeout(updateLangCombosAndShuffleDisabled, 100);
                });
            }

      // ===========================================================
      // TROCA IDIOMA FROM — REDESENHA E REINICIA STT
      // ===========================================================
      if (selFrom){
          selFrom.addEventListener("change", e=>{
              window.FROM = e.target.value;
              redrawCards();
              restartMic();   // idioma mudou → reinicia STT
          });
      }

      // ===========================================================
      // TROCA IDIOMA TO — REDESENHA E REINICIA STT
      // ===========================================================
      if (selTo){
          selTo.addEventListener("change", e=>{
              window.TO = e.target.value;
              redrawCards();
              restartMic();   // idioma mudou → reinicia STT
          });
      }

      // INTERVALO AUTOPLAY
      if (selInterval){
          AutoPlayer.setInterval(parseInt(selInterval.value));
          selInterval.addEventListener("change", e=>{
              AutoPlayer.setInterval(parseInt(e.target.value));
          });
      }

      // TTS RATE
      if (selRate){
          selRate.addEventListener("change",()=>{});
      }

      // TEMA
      if (selTheme){
          selTheme.addEventListener("change", function(){
              qs("#themeCSS").href = "css/themes/" + this.value + ".css";
          });
      }

      // ===========================================================
      // MICROFONE GLOBAL
      // ===========================================================
// ===========================================================
// MICROFONE GLOBAL — CORREÇÃO DEFINITIVA
// ===========================================================
if (btnMic){
    btnMic.addEventListener("click", () =>{
        if (!SttEngine.isSupported()){
              UI.toast("STT Não suportado.");
            return;
        }
        if (!SttEngine.enabled){
            SttEngine.start(LANGS_BCP[window.TO]);
            btnMic.textContent = "⏹️ Microfone";
            updateMicStatus(true);   // ATIVAR ÍCONE
            window.MIC_MENU_ENABLED = true;
            window.MIC_PERMANENT = true;
            return;
        }
        // Desligando permanentemente
        SttEngine.stop();
        btnMic.textContent = "🎤 Microfone";
        updateMicStatus(false);      // DESATIVAR ÍCONE
        window.MIC_MENU_ENABLED = false;
        window.MIC_PERMANENT = false;
    });
}
    

      // RESET LOCAL
      if (btnReset){
          btnReset.addEventListener("click", ()=>{
              window.location.reload();
          });
      }

      // AUTO PLAYER
      if (btnAuto){
          btnAuto.addEventListener("click", ()=>{
              if (!AutoPlayer.running){
                  AutoPlayer.start();
                  btnAuto.textContent = "⏸️ Auto (Pausar)";
              } else {
                  AutoPlayer.stop();
                  btnAuto.textContent = "▶️ Auto (Iniciar)";
              }
          });
      }

      // EMBARALHAR
      if (btnShuffle){
          btnShuffle.addEventListener("click", ()=>{
              CardsRepo.shuffle();
              redrawCards();
              UI.toast("🔀 Embaralhado.");
          });
      }

      // ===========================================================
      // CLIQUES NOS CARDS — CORREÇÃO DO "OK"
      // ===========================================================
      const container = qs("#cardsContainer");

      if (container){
          container.addEventListener("click", ev=>{
              const el = ev.target.closest("[data-role]");
              if (!el) return;

              const role   = el.dataset.role;
              const cardId = el.dataset.card;
              const card   = document.getElementById(cardId);
              if (!card) return;

              if (AutoPlayer.running) AutoPlayer.stop();

              // 🔥 CORREÇÃO ESSENCIAL: MARCAR CARD COMO ATUAL
              UI.setManualCurrent(card);

              if (role === "speak"){ 
                  speakCardText(card); 
                  return; 
              }

              if (role === "pt-toggle"){
                  const pt = card.querySelector(".card-pt");
                  if (pt) pt.classList.toggle("hidden");
                  return;
              }

              if (role === "ignore"){
                  card.classList.toggle("ignored");
                  // Se modo diálogo ativo, considerar como acerto
                  if (window.dialogState && window.dialogState.started) {
                      card.classList.add("hit");
                      card.classList.remove("blue");
                      // Avança o turno normalmente: sistema fala o próximo dele, humano fala o próximo dele, sem pular
                      const idx = parseInt(card.id.replace("card-", ""));
                      // Próximo do sistema
                      let sysIdx = idx + 1;
                      while (true) {
                          const nextOwner = window.getCardOwner ? window.getCardOwner(sysIdx) : null;
                          const nextCard = document.getElementById('card-' + sysIdx);
                          if (!nextCard) break;
                          if (nextOwner === 'system' && !nextCard.classList.contains('ignored')) {
                              setTimeout(() => {
                                  // Fala do sistema, e só depois ativa o microfone do humano
                                  window.speakCardText(nextCard).then(() => {
                                      let humanIdx = sysIdx + 1;
                                      while (true) {
                                          const nextOwnerH = window.getCardOwner ? window.getCardOwner(humanIdx) : null;
                                          const nextHumanCard = document.getElementById('card-' + humanIdx);
                                          if (!nextHumanCard) break;
                                          if (nextOwnerH === 'human' && !nextHumanCard.classList.contains('ignored')) {
                                              setTimeout(() => {
                                                  if (window.SttEngine && window.SttEngine.stop) window.SttEngine.stop();
                                                  window.handleCardMic(nextHumanCard);
                                              }, 700);
                                              break;
                                          }
                                          humanIdx++;
                                      }
                                  });
                              }, 600);
                              break;
                          }
                          sysIdx++;
                      }
                  }
                  UI.updateStats();
                  return;
              }

              if (role === "reset"){
                  resetCardLocal(card);
                  return;
              }

              if (role === "mic"){
                  handleCardMic(card);
                  return;
              }

          });
      }

    }; // fim bindUIEvents()

    // ------------------------------------------------------------
    // RESET LOCAL DO CARD
    // ------------------------------------------------------------
    window.resetCardLocal = function(card){
        card.classList.remove("hit","blue","ignored","spoken","autoplay-current","card-speaking","card-spoken");
        card.style.borderColor = "";
        card.style.borderWidth = "";
        card.style.outline = "";
        card.style.boxShadow = "";

        const r = card.querySelector(".card-recognized");
        if (r) r.textContent = "";

        const index = parseInt(card.id.replace("card-",""));
        const obj   = window.CARDS_DATA[index];
        if (obj) obj._count = 0;

        UI.refreshCounters?.();
        UI.updateStats();
    };

})();
