// ============================================================
// MERMAID DIAGRAMS — per-user clinical pathway editor.
// Source on the left, live SVG preview on the right. CRUD against
// /api/diagrams. Autosaves on quiet typing like Personal Notes.
// ============================================================

  var initialized = false;
  var mermaidReady = false;
  var library = [];
  var currentId = null;
  var currentTitle = '';
  var currentSource = '';
  var currentNotes = '';
  var saveTimer = null;
  var renderTimer = null;
  var renderToken = 0;

  document.addEventListener('tabChanged', function (e) {
    if (e.detail && e.detail.tab === 'diagrams') initIfNeeded();
  });

  function initIfNeeded() {
    if (initialized) {
      reloadLibrary();
      return;
    }
    var tabRoot = document.getElementById('diagrams-tab');
    if (!tabRoot || !tabRoot.querySelector('#diagrams-list')) {
      // Component HTML not yet injected — try again on the next tab activation.
      return;
    }
    initialized = true;
    bindEvents();
    ensureMermaid().then(reloadLibrary);
  }

  function ensureMermaid() {
    if (window.mermaid && mermaidReady) return Promise.resolve();
    return new Promise(function (resolve) {
      if (window.mermaid) {
        configureMermaid();
        resolve();
        return;
      }
      var script = document.createElement('script');
      script.src = '/vendor/mermaid.min.js';
      script.onload = function () {
        configureMermaid();
        resolve();
      };
      script.onerror = function () {
        showError('Failed to load Mermaid. Refresh and try again.');
        resolve();
      };
      document.head.appendChild(script);
    });
  }

  function configureMermaid() {
    if (!window.mermaid) return;
    window.mermaid.initialize({
      startOnLoad: false,
      securityLevel: 'strict',
      theme: 'default',
      flowchart: { useMaxWidth: true, htmlLabels: true },
    });
    mermaidReady = true;
  }

  function bindEvents() {
    var newBtn = document.getElementById('btn-diagram-new');
    var search = document.getElementById('diagram-search');
    var titleEl = document.getElementById('diagram-title');
    var sourceEl = document.getElementById('diagram-source');
    var deleteBtn = document.getElementById('btn-diagram-delete');
    var svgBtn = document.getElementById('btn-diagram-export-svg');
    var pngBtn = document.getElementById('btn-diagram-export-png');

    if (newBtn) newBtn.addEventListener('click', onNew);
    if (search) search.addEventListener('input', renderList);
    if (titleEl) titleEl.addEventListener('input', onTitleInput);
    if (sourceEl) sourceEl.addEventListener('input', onSourceInput);
    if (deleteBtn) deleteBtn.addEventListener('click', onDelete);
    if (svgBtn) svgBtn.addEventListener('click', exportSvg);
    if (pngBtn) pngBtn.addEventListener('click', exportPng);
  }

  // ── Library ────────────────────────────────────────────────
  function reloadLibrary() {
    return fetch('/api/diagrams', { credentials: 'include', headers: window.getAuthHeaders ? window.getAuthHeaders() : {} })
      .then(function (r) { return r.json(); })
      .then(function (data) {
        library = (data && data.diagrams) || [];
        renderList();
        if (currentId == null && library.length) {
          loadDiagram(library[0].id);
        } else if (!library.length) {
          showEmptyEditor();
        }
      })
      .catch(function () {
        var listEl = document.getElementById('diagrams-list');
        if (listEl) listEl.innerHTML = '<div class="diagrams-empty">Failed to load.</div>';
      });
  }

  function renderList() {
    var listEl = document.getElementById('diagrams-list');
    if (!listEl) return;
    var searchEl = document.getElementById('diagram-search');
    var q = searchEl ? String(searchEl.value || '').toLowerCase() : '';
    var rows = library.filter(function (d) {
      if (!q) return true;
      return String(d.title || '').toLowerCase().indexOf(q) !== -1;
    });
    if (!rows.length) {
      listEl.innerHTML = '<div class="diagrams-empty">' + (library.length ? 'No matches.' : 'No diagrams yet.') + '</div>';
      return;
    }
    listEl.innerHTML = rows.map(function (d) {
      return '<div class="diagram-row' + (d.id === currentId ? ' active' : '') + '" data-id="' + d.id + '">'
        + '<strong>' + escapeHtml(d.title || 'Untitled') + '</strong>'
        + '<span>' + formatDate(d.updated_at) + '</span>'
        + '</div>';
    }).join('');
    Array.prototype.forEach.call(listEl.querySelectorAll('.diagram-row'), function (row) {
      row.addEventListener('click', function () {
        loadDiagram(parseInt(row.getAttribute('data-id'), 10));
      });
    });
  }

  function showEmptyEditor() {
    currentId = null;
    setFields('', '', '');
    setStatus('');
    var preview = document.getElementById('diagram-preview');
    if (preview) preview.innerHTML = '';
    hideError();
  }

  // ── Diagram load / save ────────────────────────────────────
  function loadDiagram(id) {
    flushSaveIfPending();
    fetch('/api/diagrams/' + id, { credentials: 'include', headers: window.getAuthHeaders ? window.getAuthHeaders() : {} })
      .then(function (r) { return r.json(); })
      .then(function (data) {
        if (!data || !data.diagram) return;
        currentId = data.diagram.id;
        setFields(data.diagram.title || '', data.diagram.source || '', data.diagram.notes || '');
        setStatus('');
        renderList();
        scheduleRender(0);
      })
      .catch(function () { setStatus('Failed to load', 'error'); });
  }

  function setFields(title, source, notes) {
    currentTitle = title;
    currentSource = source;
    currentNotes = notes;
    var titleEl = document.getElementById('diagram-title');
    var sourceEl = document.getElementById('diagram-source');
    if (titleEl) titleEl.value = title;
    if (sourceEl) sourceEl.value = source;
  }

  function onNew() {
    flushSaveIfPending();
    var title = 'New diagram';
    var starter = 'graph TD\n  A[Start] --> B{Decision?}\n  B -->|Yes| C[Action]\n  B -->|No| D[End]';
    fetch('/api/diagrams', {
      method: 'POST',
      credentials: 'include',
      headers: window.getAuthHeaders ? window.getAuthHeaders() : { 'Content-Type': 'application/json' },
      body: JSON.stringify({ title: title, source: starter, notes: '' }),
    })
      .then(function (r) { return r.json(); })
      .then(function (data) {
        if (data && data.id) {
          return reloadLibrary().then(function () { loadDiagram(data.id); });
        }
      })
      .catch(function () {
        if (window.showToast) window.showToast('Could not create diagram', 'error');
      });
  }

  function onTitleInput(e) {
    currentTitle = e.target.value;
    scheduleSave();
    var row = document.querySelector('.diagram-row.active strong');
    if (row) row.textContent = currentTitle || 'Untitled';
  }

  function onSourceInput(e) {
    currentSource = e.target.value;
    scheduleSave();
    scheduleRender(220);
  }

  function scheduleSave() {
    if (currentId == null) return;
    setStatus('Saving…', 'saving');
    if (saveTimer) clearTimeout(saveTimer);
    saveTimer = setTimeout(saveNow, 700);
  }

  function flushSaveIfPending() {
    if (saveTimer) {
      clearTimeout(saveTimer);
      saveTimer = null;
      saveNow();
    }
  }

  function saveNow() {
    saveTimer = null;
    if (currentId == null) return;
    var id = currentId;
    var payload = JSON.stringify({ title: currentTitle, source: currentSource, notes: currentNotes });
    fetch('/api/diagrams/' + id, {
      method: 'PUT',
      credentials: 'include',
      headers: window.getAuthHeaders ? window.getAuthHeaders() : { 'Content-Type': 'application/json' },
      body: payload,
    })
      .then(function (r) {
        if (!r.ok) throw new Error('save failed');
        setStatus('Saved', 'saved');
        var item = library.find(function (d) { return d.id === id; });
        if (item) {
          item.title = currentTitle;
          item.source = currentSource;
          item.updated_at = new Date().toISOString();
        }
      })
      .catch(function () { setStatus('Save failed', 'error'); });
  }

  function onDelete() {
    if (currentId == null) return;
    var id = currentId;
    confirmDelete('Delete this diagram?', function () {
      fetch('/api/diagrams/' + id, {
        method: 'DELETE',
        credentials: 'include',
        headers: window.getAuthHeaders ? window.getAuthHeaders() : {},
      }).then(function () {
        currentId = null;
        return reloadLibrary();
      });
    });
  }

  function confirmDelete(message, onConfirm) {
    if (window.showConfirm) {
      window.showConfirm(message, onConfirm, { danger: true, confirmText: 'Delete' });
      return;
    }
    if (window.confirm(message)) onConfirm();
  }

  // ── Render ─────────────────────────────────────────────────
  function scheduleRender(delay) {
    if (renderTimer) clearTimeout(renderTimer);
    renderTimer = setTimeout(renderNow, delay || 0);
  }

  function renderNow() {
    renderTimer = null;
    var preview = document.getElementById('diagram-preview');
    if (!preview) return;
    var src = String(currentSource || '').trim();
    if (!src) {
      preview.innerHTML = '';
      hideError();
      return;
    }
    if (!window.mermaid || !mermaidReady) {
      ensureMermaid().then(renderNow);
      return;
    }
    var token = ++renderToken;
    var id = 'mermaid-render-' + token;
    Promise.resolve()
      .then(function () { return window.mermaid.render(id, src); })
      .then(function (result) {
        if (token !== renderToken) return;
        preview.innerHTML = result.svg;
        hideError();
      })
      .catch(function (err) {
        if (token !== renderToken) return;
        var msg = err && err.message ? err.message : String(err);
        showError(msg);
      });
  }

  function showError(msg) {
    var el = document.getElementById('diagram-error');
    if (!el) return;
    el.textContent = msg;
    el.classList.remove('hidden');
  }
  function hideError() {
    var el = document.getElementById('diagram-error');
    if (el) el.classList.add('hidden');
  }

  // ── Export ─────────────────────────────────────────────────
  function exportSvg() {
    var preview = document.getElementById('diagram-preview');
    var svg = preview && preview.querySelector('svg');
    if (!svg) {
      if (window.showToast) window.showToast('Render a diagram first', 'info');
      return;
    }
    var serializer = new XMLSerializer();
    var raw = serializer.serializeToString(svg);
    if (!/^<\?xml/.test(raw)) raw = '<?xml version="1.0" encoding="UTF-8"?>\n' + raw;
    var blob = new Blob([raw], { type: 'image/svg+xml' });
    triggerDownload(blob, fileBase() + '.svg');
  }

  function exportPng() {
    var preview = document.getElementById('diagram-preview');
    var svg = preview && preview.querySelector('svg');
    if (!svg) {
      if (window.showToast) window.showToast('Render a diagram first', 'info');
      return;
    }
    var serializer = new XMLSerializer();
    var raw = serializer.serializeToString(svg);
    var encoded = 'data:image/svg+xml;charset=utf-8,' + encodeURIComponent(raw);
    var img = new Image();
    img.onload = function () {
      var rect = svg.getBoundingClientRect();
      var scale = 2;
      var w = Math.max(1, Math.round(rect.width * scale));
      var h = Math.max(1, Math.round(rect.height * scale));
      var canvas = document.createElement('canvas');
      canvas.width = w; canvas.height = h;
      var ctx = canvas.getContext('2d');
      ctx.fillStyle = '#ffffff';
      ctx.fillRect(0, 0, w, h);
      ctx.drawImage(img, 0, 0, w, h);
      canvas.toBlob(function (blob) {
        if (blob) triggerDownload(blob, fileBase() + '.png');
      }, 'image/png');
    };
    img.onerror = function () {
      if (window.showToast) window.showToast('PNG export failed', 'error');
    };
    img.src = encoded;
  }

  function triggerDownload(blob, name) {
    var url = URL.createObjectURL(blob);
    var a = document.createElement('a');
    a.href = url;
    a.download = name;
    document.body.appendChild(a);
    a.click();
    a.remove();
    setTimeout(function () { URL.revokeObjectURL(url); }, 1000);
  }

  function fileBase() {
    var t = String(currentTitle || 'diagram').toLowerCase().replace(/[^a-z0-9]+/g, '-').replace(/^-|-$/g, '');
    return t || 'diagram';
  }

  // ── Helpers ────────────────────────────────────────────────
  function setStatus(text, kind) {
    var el = document.getElementById('diagram-status');
    if (!el) return;
    el.textContent = text || '';
    el.className = 'diagram-status' + (kind ? ' ' + kind : '');
  }

  function escapeHtml(s) {
    return String(s == null ? '' : s).replace(/[&<>"']/g, function (c) {
      return { '&': '&amp;', '<': '&lt;', '>': '&gt;', '"': '&quot;', "'": '&#39;' }[c];
    });
  }

  function formatDate(iso) {
    if (!iso) return '';
    try {
      var d = new Date(iso);
      return d.toLocaleDateString(undefined, { month: 'short', day: 'numeric' }) + ' ' + d.toLocaleTimeString(undefined, { hour: '2-digit', minute: '2-digit' });
    } catch (e) { return ''; }
  }

  // Save in-flight on tab switch / page hide so the user never loses keystrokes.
  window.addEventListener('beforeunload', flushSaveIfPending);
  document.addEventListener('visibilitychange', function () {
    if (document.visibilityState === 'hidden') flushSaveIfPending();
  });
