(function (global) {
  const app = (global.EpicrisisApp = global.EpicrisisApp || {});
  const STORAGE_KEY = "epicrisis:preparation-active-tab";
  const SECTION_LABELS = {
    diagnosticos: "diagnóstico",
    procedimientos: "procedimiento",
    medicamentos: "medicamento",
    ayudas_diagnosticas: "ayuda diagnóstica",
  };
  let sheetContext = null;
  let tabController = null;

  function normalizeSearch(value) {
    return String(value || "").normalize("NFD").replace(/[\u0300-\u036f]/g, "").toLocaleLowerCase("es").trim();
  }

  function rows(section) {
    return Array.from(document.querySelectorAll(`#${section}_list .pdf-list__row`));
  }

  function visibleRows(section) {
    return rows(section).filter((row) => !row.hidden);
  }

  function updateCounts() {
    let selectedTotal = 0;
    Object.keys(SECTION_LABELS).forEach((section) => {
      const sectionRows = rows(section);
      const selected = sectionRows.filter((row) => row.querySelector("input[type='checkbox']")?.checked).length;
      selectedTotal += selected;
      const counter = document.querySelector(`[data-count-for="${section}"]`);
      if (counter) counter.textContent = `${selected}/${sectionRows.length}`;
    });
    const summary = document.getElementById("pdf_selection_summary");
    if (summary) summary.textContent = `${selectedTotal} ${selectedTotal === 1 ? "elemento seleccionado" : "elementos seleccionados"}`;
  }

  function applyFilters(section) {
    const query = normalizeSearch(document.getElementById(`${section}_search`)?.value);
    const classification = document.getElementById("procedimientos_classification_filter")?.value || "todos";
    const group = document.getElementById("procedimientos_group_filter")?.value || "todos";
    const aidType = document.getElementById("ayudas_diagnosticas_filter")?.value || "todos";
    let visible = 0;
    rows(section).forEach((row) => {
      const matchesText = !query || normalizeSearch(`${row.dataset.searchText} ${row.textContent}`).includes(query);
      const matchesClassification = section !== "procedimientos" || classification === "todos" || row.dataset.classification === classification;
      const matchesGroup = section !== "procedimientos" || group === "todos" || (group === "con_grupo" ? Boolean(row.dataset.soatGroup) : !row.dataset.soatGroup);
      const matchesAid = section !== "ayudas_diagnosticas" || aidType === "todos" || row.dataset.aidType === aidType;
      row.hidden = !(matchesText && matchesClassification && matchesGroup && matchesAid);
      if (!row.hidden) visible += 1;
    });
    const empty = document.querySelector(`[data-empty-for="${section}"]`);
    if (empty) empty.hidden = visible !== 0;
  }

  function activateTab(section, { focus = false } = {}) {
    tabController?.activate(section, { focus });
  }

  function setAutosaveStatus(status) {
    const el = document.getElementById("pdf_autosave_status");
    if (!el) return;
    const labels = { saving: "Guardando cambios…", saved: "Todos los cambios guardados", error: "No se pudieron guardar los cambios" };
    el.textContent = labels[status] || labels.saved;
    el.dataset.status = status;
  }

  function itemAt(section, index) {
    return app.state.pdfSelectionData[section]?.[Number(index)];
  }

  function detailRows(item, section = "") {
    const sources = item?.fuentes || (item?.fuente ? [item.fuente] : []);
    const alerts = item?.alertas || [];
    const evidence = item?.evidencia || item?.razon_inclusion || item?.pertinencia?.justificacion_clinica || "Sin evidencia adicional disponible.";
    const evidenceItems = Array.isArray(item?.evidencias) ? item.evidencias : [];
    const popEvidence = evidenceItems.find((entry) => ["postoperatorio", "evolucion"].includes(String(entry?.section || "").toLocaleLowerCase("es"))) || null;
    const popSource = popEvidence ? [popEvidence.document_type, popEvidence.filename].filter(Boolean).join(" · ") : "Sin señal POP correlacionada";
    const diagnosisTrace = section === "diagnosticos" ? `
      <div><dt>Estado de codificación</dt><dd>${app.utils.escapeHtml(String(item?.estado_codificacion || "pendiente_validacion"))}</dd></div>
      <div><dt>Descripción original</dt><dd>${app.utils.escapeHtml(String(item?.descripcion_original || item?.diagnostico || item?.descripcion || "Sin descripción"))}</dd></div>
      <div><dt>Fuente documental</dt><dd>${app.utils.escapeHtml(String(item?.fuente_documental || sources.join(", ") || "Sin fuente informada"))}</dd></div>
      <div><dt>Página / sección</dt><dd>${app.utils.escapeHtml([item?.pagina ? `pág. ${item.pagina}` : "", item?.seccion].filter(Boolean).join(" · ") || "No informada")}</dd></div>
      ${item?.procedimiento_origen ? `<div><dt>Procedimiento origen</dt><dd>${app.utils.escapeHtml(String(item.procedimiento_origen))}</dd></div>` : ""}
      ${item?.evidencia_clinica ? `<div><dt>Extracto clínico original</dt><dd>${app.utils.escapeHtml(String(item.evidencia_clinica))}</dd></div>` : ""}
      ${item?.candidatos_rechazados?.length ? `<div><dt>Candidatos descartados</dt><dd>${app.utils.escapeHtml(item.candidatos_rechazados.map((candidate) => `${candidate.codigo || "sin código"}: ${candidate.razon || "sin razón"}`).join("; "))}</dd></div>` : ""}
    ` : "";
    return `<dl class="pdf-detail-list">
      <div><dt>Estado</dt><dd>${app.utils.escapeHtml(String(item?.estado_interpretacion || item?.status || item?.clasificacion || item?.estados?.[0] || "Publicable"))}</dd></div>
      ${diagnosisTrace}
      <div><dt>Estado documental</dt><dd>${app.utils.escapeHtml((item?.estado_documental || item?.estados || []).join(", ") || "Sin estado")}</dd></div>
      <div><dt>Fuentes</dt><dd>${app.utils.escapeHtml(sources.length ? sources.join(", ") : "Sin fuente informada")}</dd></div>
      <div><dt>Fuente POP</dt><dd>${app.utils.escapeHtml(popSource)}</dd></div>
      ${popEvidence ? `<div><dt>Página / sección</dt><dd>${app.utils.escapeHtml([popEvidence.page ? `pág. ${popEvidence.page}` : "", popEvidence.section].filter(Boolean).join(" · ") || "No informada")}</dd></div><div><dt>Extracto original</dt><dd>${app.utils.escapeHtml(popEvidence.excerpt || "Sin extracto")}</dd></div>` : ""}
      ${item?.estado_conciliacion || item?.razon_conciliacion ? `<div><dt>Conciliación</dt><dd>${app.utils.escapeHtml([item.estado_conciliacion, item.razon_conciliacion].filter(Boolean).join(" — "))}</dd></div>` : ""}
      <div><dt>Evidencia</dt><dd>${app.utils.escapeHtml(String(evidence))}</dd></div>
      ${(alerts.length || (item?.advertencias || []).length) ? `<div><dt>Alertas</dt><dd>${app.utils.escapeHtml([...alerts, ...(item?.advertencias || [])].join(", "))}</dd></div>` : ""}
    </dl>`;
  }

  function manualFields(section, item = {}) {
    if (section === "diagnosticos") return `<label>Código CIE-10<input name="codigo" value="${app.utils.escapeHtml(item.codigo || "")}" required></label><label>Descripción<input name="descripcion" value="${app.utils.escapeHtml(item.descripcion || "")}" required></label>`;
    if (section === "procedimientos") return `<label>Código CUPS<input name="codigo_cups" inputmode="numeric" pattern="[0-9]{6}" value="${app.utils.escapeHtml(item.codigo_cups || "")}" required></label><label>Descripción<input name="descripcion" value="${app.utils.escapeHtml(item.descripcion || "")}" required></label><label>Clasificación<select name="clasificacion" required><option value="">Selecciona</option><option value="quirurgico" ${item.clasificacion === "quirurgico" ? "selected" : ""}>Quirúrgico</option><option value="no_quirurgico" ${item.clasificacion === "no_quirurgico" ? "selected" : ""}>No quirúrgico</option></select></label>`;
    if (section === "medicamentos") return `<label>Nombre<input name="medicamento" value="${app.utils.escapeHtml(item.medicamento || item.nombre || "")}" required></label><label>Presentación<input name="presentacion" value="${app.utils.escapeHtml(item.presentacion || "")}"></label><label>Código<input name="codigo_referencia" value="${app.utils.escapeHtml(item.codigo_referencia || "")}"></label><label>Posología<input name="posologia" value="${app.utils.escapeHtml(item.posologia || "")}"></label><label>Dosis<input name="dosis" value="${app.utils.escapeHtml(item.dosis || "")}"></label><label>Cantidad<input name="cantidad" value="${app.utils.escapeHtml(item.cantidad || "")}"></label><label>Estado<select name="estado"><option value="administrado">Administrado</option><option value="formulado">Formulado</option><option value="ordenado">Ordenado</option><option value="facturado">Facturado</option></select></label>`;
    return `<label>Tipo<select name="tipo" required><option value="imagen">Imagen</option><option value="laboratorio" ${item.tipo === "laboratorio" ? "selected" : ""}>Laboratorio / examen de sangre</option><option value="procedimiento_diagnostico" ${item.tipo === "procedimiento_diagnostico" ? "selected" : ""}>Procedimiento diagnóstico</option></select></label><label>Nombre<input name="nombre" value="${app.utils.escapeHtml(item.nombre || "")}" required></label><label>Concepto<textarea name="concepto">${app.utils.escapeHtml(item.concepto || "")}</textarea></label>`;
  }

  function openSheet({ section, index = null, mode = "detail", opener }) {
    const dialog = document.getElementById("pdf_detail_sheet");
    const body = document.getElementById("pdf_sheet_body");
    const actions = document.getElementById("pdf_sheet_actions");
    const item = index == null ? {} : itemAt(section, index) || {};
    sheetContext = { section, index, mode, opener };
    document.getElementById("pdf-sheet-title").textContent = mode === "detail" ? `Detalle de ${SECTION_LABELS[section]}` : `${index == null ? "Agregar" : "Editar"} ${SECTION_LABELS[section]}`;
    if (mode === "edit") {
      body.innerHTML = `<div class="pdf-sheet__fields">${manualFields(section, item)}</div>`;
      actions.innerHTML = `${index != null ? '<button type="button" class="ui-button ui-button--ghost" data-delete-manual>Eliminar</button>' : ""}<button value="cancel" class="ui-button ui-button--ghost">Cancelar</button><button type="submit" value="default" class="ui-button ui-button--primary">Guardar</button>`;
    } else {
      let groupControl = "";
      if (section === "procedimientos" && item.clasificacion === "quirurgico") {
        if (item.grupo_soat_origen === "oficial") {
          groupControl = `<p class="pdf-workspace__note">Grupo SOAT oficial ${Number(item.grupo_soat_preparacion)}. Tiene precedencia y no puede editarse aquí.</p>`;
        } else {
          const options = Array.from({ length: 22 }, (_, i) => i + 2).map((value) => `<option value="${value}" ${Number(item.grupo_soat_preparacion) === value ? "selected" : ""}>Grupo ${value}</option>`).join("");
          groupControl = `<label>Grupo SOAT para organización visual<select id="pdf_manual_soat_group"><option value="">Sin grupo manual</option>${options}</select><small>Asignación manual para organización visual; sin efecto tarifario</small></label><button type="button" class="ui-button ui-button--secondary" data-save-soat-group>Guardar grupo visual</button>`;
        }
      }
      body.innerHTML = `${detailRows(item, section)}${groupControl}<div class="pdf-detail-links"><a href="#auditoria">Revisar en Auditoría</a><a href="#glosas">Revisar en Glosas</a></div>`;
      actions.innerHTML = `${item.manual ? '<button type="button" class="ui-button ui-button--secondary" data-edit-manual>Editar</button>' : ""}<button value="cancel" class="ui-button ui-button--primary">Cerrar</button>`;
    }
    if (!dialog.open) dialog.showModal();
    dialog.querySelector("input, select, textarea, button")?.focus();
  }

  function manualValue(section, item) {
    if (section === "diagnosticos") return [item.codigo, item.descripcion].filter(Boolean).join(" - ");
    if (section === "procedimientos") return [item.codigo_cups, item.descripcion].filter(Boolean).join(" - ");
    if (section === "medicamentos") return [item.medicamento, item.posologia, item.dosis, item.cantidad, item.estados?.[0]].filter(Boolean).join(" | ");
    return [item.tipo, item.nombre, item.concepto].filter(Boolean).join(" | ");
  }

  function syncManualDraft(section) {
    const items = app.state.pdfSelectionData[section].filter((item) => item?.manual);
    const draft = app.state.data.pdfDraft || (app.state.data.pdfDraft = {});
    if (section === "diagnosticos") {
      draft.manual_diagnostico_entries = items.map((item) => ({ key: item.key, value: manualValue(section, item) }));
      document.getElementById("diagnosticos_extra").value = draft.manual_diagnostico_entries.map((entry) => entry.value).join("\n");
    } else if (section === "procedimientos") {
      draft.manual_procedure_entries = items.map((item) => ({ key: item.key, value: manualValue(section, item) }));
    } else if (section === "medicamentos") {
      draft.manual_medicamento_entries = items.map((item) => ({ ...item, value: manualValue(section, item) }));
      document.getElementById("medicamentos_extra").value = draft.manual_medicamento_entries.map((entry) => entry.value).join("\n");
    } else {
      draft.manual_ayudas_diagnosticas = items.map((item) => ({ ...item, key: item.key }));
      document.getElementById("ayudas_diagnosticas_extra").value = items.map((item) => manualValue(section, item)).join("\n");
    }
  }

  function saveManual() {
    const { section, index } = sheetContext;
    const form = document.getElementById("pdf_sheet_form");
    if (!form.reportValidity()) return false;
    const values = Object.fromEntries(new FormData(form).entries());
    const previous = index == null ? {} : itemAt(section, index) || {};
    const key = previous.key || `manual:${section}:${global.crypto?.randomUUID?.() || `${Date.now()}-${Math.random()}`}`;
    let item = { ...previous, ...values, key, manual: true, fuentes: ["manual_pdf"] };
    if (section === "diagnosticos") item.texto_presentacion = manualValue(section, item);
    if (section === "procedimientos") Object.assign(item, { texto_manual: manualValue(section, item), clasificacion_automatica: "sin_clasificar", clasificacion_manual: true, soporte_clinico: true });
    if (section === "medicamentos") item.estados = [values.estado || "administrado"];
    if (section === "ayudas_diagnosticas") Object.assign(item, { exportable: true, fuente: "manual_pdf", estado_interpretacion: "pendiente_revision" });
    if (index == null) app.state.pdfSelectionData[section].push(item);
    else app.state.pdfSelectionData[section][index] = item;
    syncManualDraft(section);
    app.selection.renderSeccionSeleccion(section, app.state.pdfSelectionData[section]);
    app.draft.programarPersistenciaDraft();
    return true;
  }

  function deleteManual() {
    const { section, index } = sheetContext;
    if (index == null || !itemAt(section, index)?.manual) return;
    app.state.pdfSelectionData[section].splice(index, 1);
    syncManualDraft(section);
    app.selection.renderSeccionSeleccion(section, app.state.pdfSelectionData[section]);
    app.draft.programarPersistenciaDraft();
    document.getElementById("pdf_detail_sheet").close();
  }

  async function saveSoatGroup(button) {
    const item = itemAt(sheetContext.section, sheetContext.index);
    const raw = document.getElementById("pdf_manual_soat_group")?.value || "";
    button.disabled = true;
    try {
      const response = await fetch(`/api/epicrisis/cases/${encodeURIComponent(app.selection.obtenerEpicrisisCaseKeyDesdeUrl())}/preparation-metadata`, { method: "PATCH", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ procedure_key: item.key, group: raw ? Number(raw) : null }) });
      const data = await response.json();
      if (!response.ok) throw new Error(data.detail || "No se pudo guardar el grupo visual");
      app.state.data.pdfPreparationProcedimientos = data.pdf_preparation_procedimientos;
      app.state.data.pdfPreparationUserMetadata = data.pdf_preparation_user_metadata;
      app.state.pdfSelectionData.procedimientos = data.pdf_preparation_procedimientos;
      app.selection.renderSeccionSeleccion("procedimientos", data.pdf_preparation_procedimientos);
      document.getElementById("pdf_detail_sheet").close();
      AppToast.show("Grupo visual guardado.", { type: "success" });
    } catch (error) {
      AppToast.show(error.message, { type: "error" });
    } finally {
      button.disabled = false;
    }
  }

  function init() {
    const workspace = document.getElementById("seleccion_pdf_card");
    if (!workspace) return;
    tabController = app.tabs.create({
      root: workspace,
      tabSelector: "[data-preparation-tab]",
      panelSelector: "[data-preparation-panel]",
      tabDataKey: "preparationTab",
      panelDataKey: "preparationPanel",
      defaultTab: "diagnosticos",
      storageKey: STORAGE_KEY,
    });
    ["diagnosticos", "procedimientos", "medicamentos", "ayudas_diagnosticas"].forEach((section) => {
      document.getElementById(`${section}_search`)?.addEventListener("input", () => applyFilters(section));
    });
    ["procedimientos_classification_filter", "procedimientos_group_filter"].forEach((id) => document.getElementById(id)?.addEventListener("change", () => applyFilters("procedimientos")));
    document.getElementById("ayudas_diagnosticas_filter")?.addEventListener("change", () => applyFilters("ayudas_diagnosticas"));
    workspace.addEventListener("click", (event) => {
      const bulk = event.target.closest("[data-select-visible], [data-clear-visible]");
      if (bulk) {
        const section = bulk.dataset.selectVisible || bulk.dataset.clearVisible;
        const checked = Boolean(bulk.dataset.selectVisible);
        visibleRows(section).forEach((row) => { const checkbox = row.querySelector("input[type='checkbox']:not(:disabled)"); if (checkbox) checkbox.checked = checked; });
        updateCounts(); app.draft.programarPersistenciaDraft(); return;
      }
      const add = event.target.closest("[data-add-manual]");
      if (add) { openSheet({ section: add.dataset.addManual, mode: "edit", opener: add }); return; }
      const detail = event.target.closest("[data-detail-section]");
      if (detail) openSheet({ section: detail.dataset.detailSection, index: Number(detail.dataset.index), mode: "detail", opener: detail });
    });
    workspace.addEventListener("change", (event) => { if (event.target.matches(".pdf-list__row input[type='checkbox']")) updateCounts(); });
    document.addEventListener("epicrisis:selection-rendered", (event) => { applyFilters(event.detail.section); updateCounts(); });
    const dialog = document.getElementById("pdf_detail_sheet");
    dialog.addEventListener("close", () => sheetContext?.opener?.focus());
    dialog.addEventListener("click", (event) => { if (event.target === dialog) dialog.close(); });
    dialog.addEventListener("click", (event) => {
      if (event.target.closest("[data-edit-manual]")) openSheet({ ...sheetContext, mode: "edit" });
      if (event.target.closest("[data-delete-manual]")) deleteManual();
      const groupButton = event.target.closest("[data-save-soat-group]");
      if (groupButton) saveSoatGroup(groupButton);
    });
    document.addEventListener("click", (event) => {
      const link = event.target.closest("#seleccion_pdf_card a[href='#auditoria'], #pdf_detail_sheet a[href='#auditoria'], #pdf_detail_sheet a[href='#glosas']");
      if (!link) return;
      event.preventDefault();
      const target = link.getAttribute("href").slice(1);
      if (dialog.open) dialog.close();
      app.subviews.activate(target);
      global.history.pushState(null, "", `#${target}`);
      document.getElementById(`tab-${target}`)?.focus();
    });
    document.getElementById("pdf_sheet_form").addEventListener("submit", (event) => {
      if (sheetContext?.mode !== "edit" || event.submitter?.value === "cancel") return;
      event.preventDefault();
      if (saveManual()) dialog.close();
    });
    Object.keys(SECTION_LABELS).forEach(applyFilters);
    updateCounts();
  }

  app.preparation = { init, normalizeSearch, applyFilters, activateTab, updateCounts, setAutosaveStatus };
})(globalThis);
